Как написать собственный онлайн-редактор уценки в 9102

JavaScript

Онлайн-редактор Markdown

опубликовать первымАдрес редактора, охватывающий большинство сокращенных операций синтаксиса уценки, компиляцию в реальном времени и предварительный просмотр в реальном времени, поддержку прямого экспорта файлов формата md и поддержку изображений Weibo. Чистая интерфейсная реализация, не нужно беспокоиться о хранении данных в фоновом режиме. Он не был адаптирован для мобильного терминала, и его рекомендуется использовать на ПК. Приветствую всех, у кого есть потребность в письменной форме, чтобы попробовать и высказать ценные мнения.

Предыстория и предисловие

Некоторые редакторы md на рынке имеют предварительный просмотр в реальном времени, например Nuggets, но нет кнопок управления (есть сочетания клавиш), что не очень удобно в использовании, а некоторые кнопки управления Jianshu ограничены количеством сверла Цзяньшу. На самом деле md редактор Youdao Dictionary делает очень хорошую работу, но в последнее время у меня проблемы с лагом и трудностями при вводе китайского, поэтому я от него отказался.
Так что просто хлопните себя, чтобы удовлетворить потребности вашего собственного письма.Даже если вы делаете что-то сложное в использовании, вам приходится страдать
Поскольку под рукой нет устройства Windows, измените стиль полосы прокрутки самостоятельно.


Технология

vue less iview markdown-it iconfont


плагин

markdown-it-markОтметить функцию
markdown-it-emojiАнализ выражений эмодзи
highligh.jsподсветка кода
markdown-it-task-checkboxФункция флажка
markdown-it-footnoteФункция сноски


эффект плагина

==Маркер выделения==
:smiling_imp:

Наггетсы не имеют поддержки标记а такжеemoji, вставьте изображение.

принцип

в компоненте ввода редактораwatchКогда входное содержимое изменяется, оно будет вызываться в режиме реального времени, если есть изменениеmarkdown-itизrenderфункцию, а вlocalStorageКопия обновляется в режиме реального времени, чтобы предотвратить содержимое, которое было написано так усердно, когда неправильная работа страницы выпрыгивает, а затем возвращается. В то же время он также может удовлетворить требование, чтобы в этот раз страница была закрыта, а в следующий раз она была открыта для продолжения записи.Черновики будут удалены после экспорта файла. Поскольку интерфейс не вызывается для хранения данных, и не выполняется функция антивибрационной обработки, если вам нужно ее внедрить, добавьте ее самостоятельно.Адрес кровати карты Weibo был взят со страницы инструмента.Я чувствую, что брат, который написал этот инструмент, также взял его из других мест, ха-ха (шутка), и разместил адрес инструмента:Инструмент рисования


Скачать пакет

git clone git@github.com:ch957869975/md-editor.git
npm run devилиnpm run buildОткройте порт 8080, чтобы увидеть превью


интересный момент

При этом я столкнулся с несколькими более интересными моментами, отмечу.

Вставить символ в позицию курсора

т.е. поддержкаdocument.selection, в то время как большинство браузеров поддерживаютselectionStartа такжеselectionEndдва свойства. Используйте эти два свойства, чтобы добавить строкуsubstringМетоды динамически соединяются вместе.Здесь следует отметить, что строка, объединенная этим методом, не запускает двустороннюю привязку переменной, поэтому здесь я запускаю ее вручную.textareaВходное событие, как показано ниже:

 document.querySelector('textarea').dispatchEvent(new Event('input'))

Файл создается и загружается на интерфейсе

Скачивание не редкость во front-end разработке, а вот с записью файлов можно столкнуться нечасто, если бы я не написал эту штуку, то никогда бы не занимался генерацией файлов.код показывает, как показано ниже:

if (!this.editorContent || !window.localStorage.getItem('MarkdownDraft')) {
     return this.$Notice.error({ title: '你还没有写内容' })
 }
const content = this.editorContent
const elem = document.createElement('a');
elem.download = 'draft.md';
elem.style.display = 'none';
const blob = new Blob([content], { type: 'text/plain' });
elem.href = URL.createObjectURL(blob)
document.body.appendChild(elem);
elem.click();
document.body.removeChild(elem);
setTimeout(() => {
   this.editorContent = ''
   window.localStorage.removeItem('MarkdownDraft')
}, 300)

Идея все еще относительно ясна: генерировать только тогда, когда есть ценность,Избегайте создания пустого файла. использоватьBlobПосле того, как объект сгенерирует соответствующий контент, создайте другойНевидимыйaэтикетка иhrefа такжеdownloadАтрибут добавляется, а метка удаляется после запуска события клика вручную. Но нужно учитывать совместимость.вотa.downloadСитуация с поддержкой, т.е. не поддерживает! ! ! .

Нет возможности, давайте судить.

 if (!('download' in document.createElement('a'))) return this.$Notice.error({ title: '浏览器不支持' })

Может быть, вы сказали, что делать с ie?
Ответ: все 9102 года вы все еще пользуетесь т.е. кто не бросит вас бросит? ?


компонент связи

Связь между компонентами, из-за лени, используетсяbus.js, фактический код состоит из двух строк

import Vue from 'vue'
export default new Vue()

ПринципКомпоненты, смонтированные в одном и том же экземпляре, могут инициировать события в этом экземпляре., теоретически связь между любыми компонентами может быть достигнута, игнорируя иерархию компонентов. но,Этот подход не рекомендуется, потому что это заставит вашу логику слишком сильно прыгать Конкретное проявление в том, что ваш код - это молот и палка События, связанные с компонентом А на шине, часто не могут быть запущены, а компонент Б Инициированное событие не может быть найдено там, где оно связано, и его сложнее поддерживать.


Суммировать

Простые функции, простая технология, простой пользовательский интерфейс и простое развертывание. Простой маленький проект, все зависит от того, хотите вы его делать или нет.

разместил здесьАдрес редактораа такжеАдрес источника.Чики просит звезду.адрес блога

Не все возможно, но все стоит попробовать. Ну давай же!

ps: Следующие две сноски относятся к демонстрации эффекта плагина, неважно.


  1. Сноска 1↩︎

  2. Сноска 2↩︎