哇塞!居然用這個框架開發(fā)了一款這么好用的 Markdown 編輯器
今天,我們來使用Strve.js來搭建一款 Markdown 編輯器,沒錯!你沒聽錯。我們需要創(chuàng)建了一個實(shí)時 Markdown 編輯器,用戶可以在 textarea 中輸入 Markdown 文本,然后實(shí)時顯示轉(zhuǎn)換后的 HTML。你可能會說使用 Strve.js 開發(fā)會不會寫的特別復(fù)雜難懂啊,還不如用 Vue.js 呢!
好,滿足你的好奇心。首先,我們不搞那些工程化的東西,我們就是新建一個 html 文件。
就像這樣。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Markdown Editor</title>
</head>
<body></body>
</html>
好,我們到此就開發(fā)完成了~ 謝謝閱讀~
……
開玩笑的!我們這么嚴(yán)謹(jǐn)?shù)拈_發(fā)人員怎么會這么敷衍。
我們說使用Strve.js開發(fā)應(yīng)用,那么我們就先引入Strve.js。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Markdown Editor</title>
</head>
<body>
<script src="https://unpkg.com/strve-js@5.1.1/dist/strve.full.js"></script>
</body>
</html>
哇塞!引入就這么簡單?是的,就這么簡單的。另外,我們引入的版本是UMD,UMD 叫做通用模塊定義規(guī)范(Universal Module Definition)。也是隨著大前端的趨勢所誕生,它可以通過運(yùn)行時或者編譯時讓同一個代碼模塊在使用 CommonJs、CMD 甚至是 AMD 的項(xiàng)目中運(yùn)行。簡單來說,就像我們之前使用 Jquery 那樣,引入直接使用,然后直接打開html文件看效果,不需要自己搭建本地文件服務(wù)器啥的。省心省力??!
好家伙,下一步我們就開始寫靜態(tài)頁面了??!不要忘記自己是一個切圖仔。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Markdown Editor</title>
</head>
<body>
<script src="https://unpkg.com/strve-js@5.1.1/dist/strve.full.js"></script>
<script>
const { h, createApp } = Strve;
function App() {
return h/*html*/`
<textarea class="input" placeholder="input..." @input="${update}"></textarea>
<div class="output" $key="output"></div>
`;
}
createApp(App).mount("#app");
</script>
</body>
</html>
這就寫完了?怎么沒有在 body 標(biāo)簽內(nèi)寫 html 標(biāo)簽啊,我只看到了模版字符串中寫的,這是什么操作?JSX?別急啊,這是Strve.js最大特性呀!可以將模版字符串轉(zhuǎn)化成我們看到的 html 視圖。你可能又會說這不跟 JSX 思想差不多呢!是的,我開發(fā)這個框架的動機(jī)就是受 JSX 語法的影響。
到這里,我們只是寫了頁面但是沒有寫樣式。那么,下面我們就開整樣式。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Markdown Editor</title>
<style>
html,
body,
#app {
margin: 0;
height: 100%;
font-family: "Helvetica Neue", Arial, sans-serif;
color: #333;
}
#app {
display: flex;
}
.input,
.output {
width: 50%;
box-sizing: border-box;
}
.input {
border: none;
border-right: 1px solid #ccc;
resize: none;
outline: none;
background-color: #f6f6f6;
font-size: 14px;
font-family: "Monaco", courier, monospace;
padding: 20px;
}
.output {
padding: 0 20px;
}
</style>
</head>
<body>
<script src="https://unpkg.com/strve-js@5.1.1/dist/strve.full.js"></script>
<script>
const { h, createApp } = Strve;
function App() {
return h/*html*/`
<textarea class="input" placeholder="input..." @input="${update}"></textarea>
<div class="output" $key="output"></div>
`;
}
createApp(App).mount("#app");
</script>
</body>
</html>
你可能會說,樣式有了,頁面結(jié)構(gòu)也有了,我想看看效果。先忍??!我們得先賦予他靈魂,好事不怕晚。
下面,我們就開始寫業(yè)務(wù)邏輯了。我們要實(shí)現(xiàn)的效果就是用戶可以在 textarea 中輸入 Markdown 文本,然后實(shí)時顯示轉(zhuǎn)換后的 HTML。你可能會說,啥意思?就是左側(cè)我們寫Markdown 文本,然后右側(cè)就是顯示 Markdown 轉(zhuǎn)換后的文本了。
好了,廢話不多說了?。ㄟ€算有點(diǎn)自知之明)
完整源碼如下:(相信我,你還會回來的?。?/p>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Markdown Editor</title>
<link
rel="stylesheet"
/>
<style>
html,
body,
#app {
margin: 0;
height: 100%;
font-family: "Helvetica Neue", Arial, sans-serif;
color: #333;
}
#app {
display: flex;
}
.input,
.output {
width: 50%;
box-sizing: border-box;
}
.input {
border: none;
border-right: 1px solid #ccc;
resize: none;
outline: none;
background-color: #f6f6f6;
font-size: 14px;
font-family: "Monaco", courier, monospace;
padding: 20px;
}
.output {
padding: 0 20px;
}
</style>
</head>
<body>
<script src="https://unpkg.com/strve-js@5.1.1/dist/strve.full.js"></script>
<script src="https://unpkg.com/marked@2.1.3/lib/marked.js"></script>
<script src="https://unpkg.com/marked-highlight@2.0.1/lib/index.umd.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/highlight.min.js"></script>
<script src="https://unpkg.com/lodash@4.17.21/lodash.min.js"></script>
<script>
const { h, setData, createApp, domInfo, nextTick } = Strve;
// Highlight code blocks
marked.use(
markedHighlight.markedHighlight({
langPrefix: "hljs language-",
highlight(code, lang) {
const language = hljs.getLanguage(lang) ? lang : "plaintext";
return hljs.highlight(code, { language }).value;
},
})
);
let input = "";
function compiledMarkdown() {
return marked(input);
}
const debouncedUpdate = _.debounce(function (e) {
setData(() => {
input = e.target.value;
});
nextTick(() => {
domInfo.output.innerHTML = compiledMarkdown();
});
}, 100);
function update(e) {
debouncedUpdate(e);
}
function App() {
return h/*html*/ `
<textarea class="input" placeholder="input..." @input="${update}"></textarea>
<div class="output" $key="output"></div>
`;
}
createApp(App).mount("#app");
</script>
</body>
</html>
我去!咋一下子多出了這么多代碼!你這是逗我嗎?
別著急嘛!我會對你負(fù)責(zé)的,我既然一下子寫了這么多代碼,肯定會解釋清楚的。
下面,我們要正經(jīng)起來了!我們既然需要開發(fā)一款 Markdown 編輯器,我們需要的依賴庫有下面幾種:
- Strve-js: 一個輕量級的 JavaScript 框架,用于構(gòu)建用戶界面;
- Marked: 一個將 Markdown 轉(zhuǎn)換為 HTML的庫;
- Highlight: 讓網(wǎng)頁上的代碼高亮美化的免費(fèi)開源工具庫;
- Lodash: 一個實(shí)用的 JavaScript 工具庫;
那么你就會看我們引入了這些庫。
<script src="https://unpkg.com/strve-js@5.1.1/dist/strve.full.js"></script>
<script src="https://unpkg.com/marked@2.1.3/lib/marked.js"></script>
<script src="https://unpkg.com/marked-highlight@2.0.1/lib/index.umd.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/highlight.min.js"></script>
<script src="https://unpkg.com/lodash@4.17.21/lodash.min.js"></script>
另外,需要再引入一個css文件,用于 Markdown 中代碼高亮的樣式。
<link
rel="stylesheet"
/>
外部引入的文件,我們已經(jīng)介紹完了,那么我們再集中講解下核心業(yè)務(wù)邏輯代碼。
定義一個名為 input 的變量用于存儲用戶輸入的 Markdown 文本。然后定義一個名為 compiledMarkdown 的函數(shù),該函數(shù)使用 Marked 庫將 input 變量中的 Markdown 文本轉(zhuǎn)換為 HTML。然后再定義一個名為 update 的函數(shù),該函數(shù)在用戶輸入時調(diào)用。它使用 Lodash 的 debounce 函數(shù)來防止頻繁觸發(fā),提高性能。當(dāng)用戶輸入時,它會更新 input 變量并將轉(zhuǎn)換后的 HTML 插入到輸出 <div> 中。定義一個名為 App 的組件,該組件包含一個 textarea 用于輸入 Markdown 文本,以及一個 <div> 用于顯示轉(zhuǎn)換后的HTML。<textarea> 上有一個input 事件監(jiān)聽器,當(dāng)用戶輸入時調(diào)用 update 函數(shù)。輸出 <div> 使用 $key 屬性設(shè)置 Strve 的引用名稱為"output"。使用 Strve 的 createApp 函數(shù)創(chuàng)建一個 App 實(shí)例并掛載到 id 為app的元素上。
核心邏輯講完了,那么我們欣賞下這款 Markdown 編輯器完整代碼吧!
下面,我們來看下這款Markdown 編輯器的真正面目吧!
額~ 真簡約啊!你可能會問能不能這樣,能不能那樣?。《疾恍?,真垃圾呀!
哈哈哈……
讓您失望了!
扯了這么多!你的動機(jī)到底是啥?
當(dāng)然是為了分享這個簡約實(shí)用的項(xiàng)目??!
另外,也是為了推廣我的框架:Strve.js,值得高興的一件事,ChatGPT 居然給我這個框架定義為一個輕量級的 JavaScript 框架,用于構(gòu)建用戶界面。
好了,到這里就結(jié)束了,謝謝大家聽我的閑扯!
別走別走!看這!歡迎大家的小手手點(diǎn)擊下哦!
Strve.js 中文文檔:https://maomincoding.gitee.io/strve-doc-zh/
Strve.js 源碼倉庫:https://github.com/maomincoding/strve