{
  "v": 2,
  "b": [
    {
      "kind": "h",
      "n": [
        {
          "kind": "t",
          "t": "Документ как дерево, а не строка"
        }
      ]
    },
    {
      "kind": "p",
      "n": [
        {
          "kind": "t",
          "t": "Перед вами "
        },
        {
          "kind": "t",
          "t": "живой документ",
          "b": true
        },
        {
          "kind": "t",
          "t": ". Каждый абзац — "
        },
        {
          "kind": "t",
          "t": "типизированный узел",
          "i": true
        },
        {
          "kind": "t",
          "t": " дерева "
        },
        {
          "kind": "t",
          "t": "DocNode",
          "c": true
        },
        {
          "kind": "t",
          "t": ", а не мешок HTML-тегов. Слева от каждого блока — кнопка "
        },
        {
          "kind": "t",
          "t": "+",
          "b": true
        },
        {
          "kind": "t",
          "t": " для вставки нового."
        }
      ]
    },
    {
      "kind": "cl",
      "n": [
        {
          "kind": "t",
          "t": "Источник истины — JSON. Откройте вкладку "
        },
        {
          "kind": "t",
          "t": "json",
          "c": true
        },
        {
          "kind": "t",
          "t": " справа: структура обновляется синхронно с каждым нажатием клавиши."
        }
      ]
    },
    {
      "kind": "h",
      "l": 2,
      "n": [
        {
          "kind": "t",
          "t": "Inline-слой"
        }
      ]
    },
    {
      "kind": "p",
      "n": [
        {
          "kind": "t",
          "t": "Выделите фрагмент — появится тулбар: "
        },
        {
          "kind": "t",
          "t": "жирный",
          "b": true
        },
        {
          "kind": "t",
          "t": " / "
        },
        {
          "kind": "t",
          "t": "курсив",
          "i": true
        },
        {
          "kind": "t",
          "t": " / "
        },
        {
          "kind": "t",
          "t": "подчёркнутый",
          "u": true
        },
        {
          "kind": "t",
          "t": " / "
        },
        {
          "kind": "t",
          "t": "зачёркнутый",
          "s": true
        },
        {
          "kind": "t",
          "t": " / "
        },
        {
          "kind": "t",
          "t": "inline-код",
          "c": true
        },
        {
          "kind": "t",
          "t": " и "
        },
        {
          "kind": "a",
          "u": "https://nevelgrad.ru/сообщество/статья/01КР22ТДЧБ9ЦЖ3АДД379А3НУТВ",
          "ch": [
            {
              "kind": "t",
              "t": "ссылки"
            }
          ]
        },
        {
          "kind": "t",
          "t": "."
        }
      ]
    },
    {
      "kind": "q",
      "n": [
        {
          "kind": "t",
          "t": "Простота — предпосылка надёжности."
        }
      ],
      "au": "Эдсгер Дейкстра"
    },
    {
      "kind": "h",
      "l": 2,
      "n": [
        {
          "kind": "t",
          "t": "Блочные структуры"
        }
      ]
    },
    {
      "kind": "li",
      "o": true,
      "n": [
        {
          "kind": "t",
          "t": "Enter делит блок надвое по позиции каретки"
        }
      ]
    },
    {
      "kind": "li",
      "o": true,
      "n": [
        {
          "kind": "t",
          "t": "Backspace в начале строки склеивает с предыдущим"
        }
      ]
    },
    {
      "kind": "li",
      "n": [
        {
          "kind": "t",
          "t": "Tab / Shift+Tab — вложенность списков"
        }
      ]
    },
    {
      "kind": "li",
      "lv": 1,
      "n": [
        {
          "kind": "t",
          "t": "Вложенный пункт первого уровня"
        }
      ]
    },
    {
      "kind": "li",
      "lv": 2,
      "n": [
        {
          "kind": "t",
          "t": "Вложенный пункт второго уровня"
        }
      ]
    },
    {
      "kind": "cd",
      "la": "csharp",
      "co": "public sealed record CalloutBlock : BlockNode, ITextBlock\r\n{\r\n    public string Type { get; set; } = \"info\";\r\n    public List<InlineNode> Inlines { get; set; } = new();\r\n}"
    },
    {
      "kind": "img",
      "sr": "https://nevelgrad.ru/файлы/01КСТХЧМЦПК3МР5БФИ347К08ИГ",
      "al": "Изображение для демо",
      "ar": "16:9"
    },
    {
      "kind": "tb",
      "c": 3,
      "r": [
        [
          [
            {
              "kind": "t",
              "t": "Слой",
              "b": true
            }
          ],
          [
            {
              "kind": "t",
              "t": "Формат",
              "b": true
            }
          ],
          [
            {
              "kind": "t",
              "t": "Кто владеет",
              "b": true
            }
          ]
        ],
        [
          [
            {
              "kind": "t",
              "t": "Редактирование"
            }
          ],
          [
            {
              "kind": "t",
              "t": "DOM (contenteditable)"
            }
          ],
          [
            {
              "kind": "t",
              "t": "JS — между рендерами"
            }
          ]
        ],
        [
          [
            {
              "kind": "t",
              "t": "Модель"
            }
          ],
          [
            {
              "kind": "t",
              "t": "DocNode → BlockNode → InlineNode"
            }
          ],
          [
            {
              "kind": "t",
              "t": ".NET — источник истины"
            }
          ]
        ],
        [
          [
            {
              "kind": "t",
              "t": "Хранение"
            }
          ],
          [
            {
              "kind": "t",
              "t": "JSON / ASTB"
            }
          ],
          [
            {
              "kind": "t",
              "t": "БД / localStorage"
            }
          ]
        ]
      ]
    },
    {
      "kind": "hr"
    },
    {
      "kind": "cl",
      "ty": "success",
      "n": [
        {
          "kind": "t",
          "t": "Правая панель пересчитывается на каждый ввод — без перезагрузки и без JS-фреймворков."
        }
      ]
    },
    {
      "kind": "cl",
      "ty": "warn",
      "n": [
        {
          "kind": "t",
          "t": "Демо хранит документ в "
        },
        {
          "kind": "t",
          "t": "localStorage",
          "c": true
        },
        {
          "kind": "t",
          "t": " браузера. Кнопка «сбросить автосохранение» вернёт исходный документ."
        }
      ]
    },
    {
      "kind": "h",
      "l": 2,
      "n": [
        {
          "kind": "t",
          "t": "Экспорт и импорт"
        }
      ]
    },
    {
      "kind": "p",
      "n": [
        {
          "kind": "t",
          "t": "Используйте кнопки "
        },
        {
          "kind": "t",
          "t": "⇥ экспорт",
          "b": true
        },
        {
          "kind": "t",
          "t": " и "
        },
        {
          "kind": "t",
          "t": "⇤ импорт",
          "b": true
        },
        {
          "kind": "t",
          "t": " в тулбаре. Поддерживаемые форматы: "
        },
        {
          "kind": "t",
          "t": "JSON",
          "c": true
        },
        {
          "kind": "t",
          "t": ", "
        },
        {
          "kind": "t",
          "t": "ASTB",
          "c": true
        },
        {
          "kind": "t",
          "t": " (бинарный), "
        },
        {
          "kind": "t",
          "t": "HTML",
          "c": true
        },
        {
          "kind": "t",
          "t": ", "
        },
        {
          "kind": "t",
          "t": "Markdown",
          "c": true
        },
        {
          "kind": "t",
          "t": ", "
        },
        {
          "kind": "t",
          "t": "Plain Text",
          "c": true
        },
        {
          "kind": "t",
          "t": "."
        }
      ]
    }
  ]
}