Warning: error_log(/data/www/wwwroot/hmttv.cn/caches/error_log.php): failed to open stream: Permission denied in /data/www/wwwroot/hmttv.cn/phpcms/libs/functions/global.func.php on line 537 Warning: error_log(/data/www/wwwroot/hmttv.cn/caches/error_log.php): failed to open stream: Permission denied in /data/www/wwwroot/hmttv.cn/phpcms/libs/functions/global.func.php on line 537 亚洲成人在线视频观看,亚洲欧洲日本天天堂在线观看,亚洲视频精品在线

          整合營銷服務商

          電腦端+手機端+微信端=數據同步管理

          免費咨詢熱線:

          Typora輸入代碼塊、數學公式、繪制流程圖并導出為html

          ypora 是一款支持實時預覽的 Markdown 文本編輯器。它有 OS X、Windows、Linux 三個平臺的版本,目前完全免費

          https://typora.io/#

          Markdown是一種輕量級標記語言,創始人為約翰·格魯伯(英語:John Gruber)。 它允許人們使用易讀易寫的純文本格式編寫文檔,然后轉換成有效的XHTML(或者HTML)文檔。這種語言吸收了很多在電子郵件中已有的純文本標記的特性。

          由于Markdown的輕量化、易讀易寫特性,并且對于圖片,圖表、數學式都有支持,目前許多網站都廣泛使用Markdown來撰寫幫助文檔或是用于論壇上發表消息。 如GitHub、Reddit、Diaspora、Stack Exchange、OpenStreetMap 、SourceForge、簡書等,甚至還能被使用來撰寫電子書。

          在使用Dreamweaver編寫網頁時,遇到需要插入代碼塊、流程圖、數學公式時,總是顯得很無力,效率很低,效果不好,使用Typora會讓這些問題迎刃而解,且輕便,簡單。

          直接看一個demo:

          導出為html:

          html網頁源代碼:

          其可以導出的格式有:

          流程圖樣式包括:

          1、標準流程圖源碼格式(橫向):

          ```flow
          st=>start: 開始框
          op=>operation: 處理框
          cond=>condition: 判斷框(是或否?)
          sub1=>subroutine: 子流程
          io=>inputoutput: 輸入輸出框
          e=>end: 結束框
          st(right)->op(right)->cond
          cond(yes)->io(bottom)->e
          cond(no)->sub1(right)->op
          ```

          2 mermaid語言庫繪流程圖

          Mermaid 是一個用于畫流程圖、狀態圖、時序圖、甘特圖的庫,使用 JS 進行本地渲染,廣泛集成于許多 Markdown 編輯器中。

          Mermaid 作為一個使用 JS 渲染的庫,生成的不是一個“圖片”,而是一段 HTML 代碼,因此安全許多。

          官網:https://mermaidjs.github.io/
          Github 項目地址:https://github.com/knsv/mermaid

          2.1 橫向流程圖源碼格式:

          graph LR
          A[方形] -->B(圓角)
              B --> C{條件a}
              C -->|a=1| D[結果1]
              C -->|a=2| E[結果2]

          2.2 豎向流程圖源碼格式:

          sequenceDiagram
          Title: 標題:復雜使用
          對象A->對象B: 對象B你好嗎?(請求)
          Note right of 對象B: 對象B的描述
          Note left of 對象A: 對象A的描述(提示)
          對象B-->對象A: 我很好(響應)
          對象B->小三: 你好嗎
          小三-->>對象A: 對象B找我了
          對象A->對象B: 你真的好嗎?
          Note over 小三,對象B: 我們是朋友
          participant C
          Note right of C: 沒人陪我玩

          2.3 時序圖源碼復雜樣例

                  gantt
                  dateFormat  YYYY-MM-DD
                  title 軟件開發甘特圖
                  section 設計
                  需求                      :done,    des1, 2014-01-06,2014-01-08
                  原型                      :active,  des2, 2014-01-09, 3d
                  UI設計                     :         des3, after des2, 5d
              未來任務                     :         des4, after des3, 5d
                  section 開發
                  學習準備理解需求                      :crit, done, 2014-01-06,24h
                  設計框架                             :crit, done, after des2, 2d
                  開發                                 :crit, active, 3d
                  未來任務                              :crit, 5d
                  耍                                   :2d
                  section 測試
                  功能測試                              :active, a1, after des3, 3d
                  壓力測試                               :after a1  , 20h
                  測試報告                               : 48h

          2.4 甘特圖樣例:

                  gantt
                  dateFormat  YYYY-MM-DD
                  title 軟件開發甘特圖
                  section 設計
                  需求                      :done,    des1, 2014-01-06,2014-01-08
                  原型                      :active,  des2, 2014-01-09, 3d
                  UI設計                     :         des3, after des2, 5d
              未來任務                     :         des4, after des3, 5d
                  section 開發
                  學習準備理解需求                      :crit, done, 2014-01-06,24h
                  設計框架                             :crit, done, after des2, 2d
                  開發                                 :crit, active, 3d
                  未來任務                              :crit, 5d
                  耍                                   :2d
                  section 測試
                  功能測試                              :active, a1, after des3, 3d
                  壓力測試                               :after a1  , 20h
                  測試報告                               : 48h


          教程:

          Markdown 高級技巧 | 菜鳥教程(使用 Typora 編輯器講解 Markdown 的語法)

          https://www.runoob.com/markdown/md-advance.html

          ref

          1 Typora 完全使用詳解

          https://sspai.com/post/54912/

          2 用什么軟件畫流程圖好?-悟空問答

          https://www.wukong.com/question/6809962012198568195/

          3 Mermaid 實用教程

          https://blog.csdn.net/fenghuizhidao/article/details/79440583

          -End-

          js2flowchart 是一個可視化庫,可將任何JavaScript代碼轉換為漂亮的SVG流程圖。你可以輕松地利用它學習其他代碼、設計你的代碼、重構代碼、解釋代碼。這樣一個強大的神器,真的值得你擁有,看下面截圖就知道了,有沒有很強大。

          Github

          https://github.com/Bogdan-Lyashenko/js-code-to-svg-flowchart

          安裝使用

          • 安裝
          yarn add js2flowchart
          
          • 使用

          index.html

          <!DOCTYPE html>
          <html lang="en">
          <head>
           <meta charset="UTF-8">
           <meta name="viewport" content="width=device-width, initial-scale=1.0">
           <meta http-equiv="X-UA-Compatible" content="ie=edge">
           <title>fly測試</title>
          </head>
          <body>
           <div style="width:50%;float:left">
           <p id="svgImage"></p>
           </div>
           <div style="width:50%;float:left">
           <textarea name="" id="jsContent" style="width: 90%;height:900px" oninput="createSVG()">
           </textarea>
           </div>
           <script src="./node_modules/js2flowchart/dist/js2flowchart.js"></script>
           <script src="./index.js"></script>
          </body>
          </html>
          

          index.js

          createSVG = () => {
           document.getElementById("svgImage").innerHTML = null;
           let code = document.getElementById("jsContent").value;
           const { createFlowTreeBuilder, createSVGRender } = js2flowchart;
           const flowTreeBuilder = createFlowTreeBuilder(),
           svgRender = createSVGRender();
           const flowTree = flowTreeBuilder.build(code),
           shapesTree = svgRender.buildShapesTree(flowTree);
           const svg = shapesTree.print();
           document.getElementById("svgImage").innerHTML = svg;
          };
          createSVG();
          

          我們直接在文本域中輸入自己的代碼,如下,左邊會直接生成流程圖,這只是一個簡單的示例:

          js2flowchart的特性以及適用場景(來自官網翻譯)

          js2flowchart獲取您的JS代碼并返回SVG流程圖,適用于客戶端/服務器,支持ES6。

          主要特點:

          • 定義抽象級別以僅渲染導入/導出,類/函數名稱,函數依賴性以逐步學習/解釋代碼。
          • 自定義抽象級別支持創建自己的抽象級別
          • 表示生成器,以生成不同抽象級別的SVG列表
          • 定義流樹修改器以映射眾所周知的API,例如[] .map,[]。forEach,[] .filter到方案上的循環結構等。
          • 銷毀修飾符,用于在方案上用一個形狀替換代碼塊
          • 自定義流樹修改器支持創建自己的流修改器
          • 流樹忽略過濾器完全省略一些代碼節點,如日志行
          • 聚焦節點或整個代碼邏輯分支突出顯示方案的重要部分
          • 模糊節點或整個代碼邏輯分支以隱藏不太重要的東西
          • 定義的樣式主題支持選擇您喜歡的樣式
          • 自定義主題支持創建自己的主題,更好地適合您的上下文顏色
          • 自定義顏色和樣式支持提供方便的API來更改特定樣式而無需樣板

          用例場景:

          • 通過流程圖解釋/記錄您的代碼
          • 通過視覺理解學習其他代碼
          • 為有效JS語法簡單描述的任何進程創建流程圖

          以上所有功能可以直接到github上詳細了解,用法太多,這里就不在介紹了!

          vscode擴展

          這么強大的東西,有人肯定說如果在開發的時候實時看到流程圖有助于理解代碼,官網提供了插件(我在最新版中測試失效了,不知道是否是我使用的有問題還是插件本身的問題),如果感興趣的可以到擴展商店搜索code-flowchart。如果測試成功,歡迎到評論區分享。以下是我vscode版本和官網的插件使用截圖。

          如果利用好這個插件,可以開發出Chrome插件,以及其他JavaScript編輯器或者IDEA的插件,由于官方github已經幾個月沒更新了,所以還不知道未來會不會支持!

          總結

          js2flowchart是一個比較實用的Javascript插件,可以用來做很多事情,不管是自己寫代碼。還是閱讀別人的代碼,都無疑是一大助力,能夠幫助我們提升我們的代碼能力,更容易的閱讀代碼,這樣學習起來就快了,希望對你有所幫助!如果有什么好的建議,也可以到評論區分享!

          起幫助文檔,想必大家都會想到 VuePress等,我也體驗了一下,但是感覺和我的思路不太一樣,我希望的是那種可以直接在線編輯文檔,然后無需編譯就可以直接發布的方式,另外可以在線寫(修改)代碼并且運行的效果。

          VuePress 是“靜態網站生成器”,需要我們自行編寫文檔,然后交給VuePress變成網站,VuePress 并沒有提供編寫環境,我知道有很多編寫 Markdown 的方式,但是我還是喜歡編寫、瀏覽合為“一體”的方式。

          似乎沒有,那么 —— 自己動手豐衣足食吧,開干!

          技術棧

          • vite: ^2.7.0
          • vue: ^3.2.23
          • axios: ^0.25.0 獲取json格式的配置和文檔(CDN方式引入)
          • element-plus: ^2.0.2 UI庫
          • nf-ui-elp": ^0.1.0 二次封裝的UI庫
          • @element-plus/icons-vue: ^0.2.4 圖標
          • @kangc/v-md-editor:"^2.3.13 md 編輯器
          • vite-plugin-prismjs: ^0.0.8 代碼高亮
          • nf-state": ^0.2.4 狀態管理
          • nf-web-storage": ^0.2.3 訪問 indexedDB

          建立庫項目(@naturefw/press-edit)實現文檔的編寫、瀏覽功能

          首先使用 vite2 建立一個 Vue3 的項目:

          • 安裝 elementPlus 實現頁面效果;
          • 安裝 v-md-editor 實現 Markdown 的編輯和顯示;
          • 安裝 @naturefw/storage 操作 indexedDB ,實現幫助文檔的存儲;
          • 安裝 @naturefw/nf-state 實現狀態管理;
          • 安裝axios 用于加載 json文件,實現導入功能。
          • 用node寫一個后端API,實現寫入json文件的功能。

          注意:庫項目需要安裝以上插件,幫助文檔項目只需要安裝 @naturefw/press-edit 即可。

          基本功能就是這樣,心急的可以先看在線演示和源碼。

          • 在線演示:

          在線編寫幫助文檔

          https://nfpress.gitee.io/nf-press-edit/

          • 源碼:

          nf-press-edit_幫助文檔的管理平臺: 在線文檔的編輯環境,可以編寫文檔。

          https://gitee.com/nfpress/nf-press-edit

          • 編輯頁面

          • 瀏覽頁面

          兩個狀態:編輯和瀏覽

          一開始做了兩個項目,分別實現編輯文檔和顯示文檔的功能,但是后來發現,內部代碼大部分是相同的,維護的時候有點麻煩,所以改為在編輯文檔的項目里加入“瀏覽”的狀態,然后設置切換的功能,這樣便于內部代碼的維護,以后成熟了可能會分為兩個單獨的項目。

          編輯狀態的功能

          • 菜單維護
          • 文檔維護
          • 文檔展示
          • 導入導出
          • 在線編寫/執行代碼

          我喜歡在線編輯的方式,這樣更省心,于是我用 el-menu 實現導航和左側的菜單,然后加上了維護功能。使用 v-md-editor 實現 Markdown 的編輯和顯示。然后用node寫了一個后端API,實現保存 json文件的功能,這樣就完美了。

          瀏覽狀態的功能

          • 導航
          • 菜單
          • 文檔展示
          • 執行代碼

          就是在編輯狀態的功能的基礎上,去掉一些功能。或者其實可以反過來思考。

          實現導航

          首先參考 VuePress 設置一個json文件,用于加載和保存網站信息、導航信息。

          /public/docs/.nfpress/project.json

          {
            "projectId": "1000",
            "title": "nf-press-edit !",
            "description": "這是一個在線編輯、展示文檔的小工具",
            "navi": [
              {
                "naviId": "1010",
                "text": "指南",
                "link": "menu"
              },
              {
                "naviId": "1020",
                "text": "組件",
                "link": "menu"
              },
              {
                "naviId": "1380",
                "text": "Gitee",
                "link": "幫助文檔/nf-press-edit_幫助文檔的管理平臺"
              },
              {
                "naviId": "1390",
                "text": "在線演示",
                "link": "在線編寫幫助文檔"
              },
              {
                "naviId": "1395",
                "text": "我要提意見",
                "link": "Issues · 幫助文檔/nf-press-edit_幫助文檔的管理平臺 - Gitee.com"
              }
            ]
          }
          • projectId:項目ID,可以用于區分不同的幫助文檔項目。
          • navi: 存放導航項。
          • naviId: 關聯到菜單。
          • text: 導航上顯示的文字。
          • link: 連接方式或鏈接地址。menu:表示要打開對應的菜單;URL:在新頁面里打開連接。

          然后做一個組件,用 el-menu 綁定數據渲染出來即可實現導航效果。

          /lib/navi/navi.vue

          <el-menu
              :default-active="activeIndex2"
              class="el-menu-demo"
              mode="horizontal"
              v-bind="$attrs"
              :background-color="backgroundColor"
              @select="handleSelect"
            >
              <el-menu-item
                v-for="(item, index) in naviList"
                :key="index"
                :index="item.naviId"
              >
                {{item.text}}
              </el-menu-item>
            </el-menu>

          可以是多級的導航,暫時沒有實現在線維護功能。


            import { ref } from 'vue'
            import { ElMenu, ElMenuItem } from 'element-plus'
            import { state } from '@naturefw/nf-state'
             
            const props = defineProps({
              'background-color': { // 默認背景色
                type: String,
                default: '#ece5d9'
              },
              itemProps: Object
            })
          
            // 獲取狀態和導航內容
            const { current, naviList } = state
            // 激活第一個導航項
            const activeIndex2 = ref(naviList[0].naviId)
            
            const handleSelect = (key, keyPath) => {
              const navi = naviList.find((item) => item.naviId === key)
              if (navi.link === 'menu') {
                // 打開菜單
                current.naviId = key
              } else {
                // 打開連接
                window.open(Navi Link, '_blank')
              }
            }
          
          • @naturefw/nf-state

          自己寫的一個輕量級狀態管理,可以當做大號 reactive 來使用,通過狀態管理加載 project.json 然后綁定渲染。

          • naviList

          導航列表,由狀態管理加載。

          • current

          當前激活的各種信息,比如“current.naviId”表示激活的導航項。

          實現菜單

          和導航類似,只是需要增加兩個功能:n級分組和維護。

          首先參考 VuePress 設置一個json文件,保存菜單信息。

          /public/docs/.nfpress/menu.json

          [
            {
              "naviId": "1010",
              "menus": [
                {
                  "menuId": "110100",
                  "text": "介紹",
                  "description": "描述",
                  "icon": "FolderOpened",
                  "children": []
                },
                {
                  "menuId": "111100",
                  "text": "快速上手",
                  "description": "描述",
                  "icon": "FolderOpened",
                  "children": [
                    {
                      "menuId": 111120,
                      "text": "編輯文檔項目",
                      "description": "",
                      "icon": "UserFilled",
                      "children": []
                    },
                    {
                      "menuId": 111130,
                      "text": "展示文檔項目",
                      "description": "",
                      "icon": "UserFilled"
                    }
                  ]
                } 
              ],
              "ver": 1.6
            },
            {
              "naviId": "1020",
              "menus": [
                {
                  "menuId": "21000",
                  "text": "導航(docNavi)",
                  "description": "描述",
                  "icon": "Star",
                  "children": []
                } 
              ],
              "ver": 1.5
            }
          ]
          • naviId: 關聯導航項ID,可以是數字,也可以是其他字符。需要和導航項ID對應。
          • menus: 導航項對應的菜單項集合。
          • menuId: 菜單項ID,關聯一個文檔,可以是數字或者英文。
          • text: 菜單項名稱。
          • description: 描述,考慮以后用于查詢。
          • icon: 菜單使用的圖標名稱。
          • children: 子菜單項目,沒有的話可以去掉。
          • ver: 版本號,便于更新文檔。

          然后用 el-menu 綁定數據渲染,因為要實現n級分組,所以做一個遞歸組件實現n級菜單的效果。


          實現n級分組菜單

          做一個遞歸組件實現n級分組的功能:

          /lib/menu/menu-sub-edit.vue

          <template v-for="(item, index) in subMenu">
              <!--樹枝-->
              <template v-if="item.children && item.children.length > 0">
                <el-sub-menu 
                  :key="item.menuId + '_' + index"
                  :index="item.menuId"
                  style="vertical-align: middle;"
                >
                  <template #title>
                    <div style="display:inline;width: 100%;">
                      <component
                        :is="$icon[item.icon]"
                        style="width: 1.5em; height: 1.5em; margin-right: 8px;vertical-align: middle;"
                      >
                      </component>
                      <span>{{item.text}}</span>
                    </div>
                  </template>
                  <!--遞歸子菜單-->
                  <my-sub-menu2
                    :subMenu="item.children"
                    :dialogAddInfo="dialogAddInfo"
                    :dialogModInfo="dialogModInfo"
                  />
                </el-sub-menu>
              </template>
              <!--樹葉-->
              <el-menu-item v-else
                :index="item.menuId"
                :key="item.menuId + 'son_' + index"
              >
                <template #title>
                  <div style="display:inline;width: 100%;">
                    <span style="float: left;">
                      <component
                        :is="$icon[item.icon]"
                        style="width: 1.5em; height: 1.5em; margin-right: 8px;vertical-align: middle;"
                      >
                      </component>
                      <span >{{item.text}}</span>
                    </span>
                  </div>
                </template>
              </el-menu-item>
            </template>
            import { ElMenuItem, ElSubMenu } from 'element-plus'
            // 展示子菜單 - 遞歸
            import mySubMenu2 from './menu-sub.vue'
          
            const props = defineProps({
              subMenu: Array, // 要顯示的菜單,可以n級
              dialogAddInfo: Object, // 添加菜單
              dialogModInfo: Object // 修改菜單
            })
          
          • subMenu 要顯示的子菜單項
          • dialogAddInfo 添加菜單的信息
          • dialogModInfo 修改菜單的信息


          實現菜單的維護功能

          這個就比較簡單了,做個表單實現菜單的增刪改即可,篇幅有限跳過。

          實現 Markdown 的編輯

          使用 v-md-editor 實現 Markdown 的編輯和展示,首先該插件非常好用,其次支持VuePress的主題。

          建立 /lib/md/md-edit.vue 實現編輯 Markdown 的功能:

            <v-md-editor
              :toolbar="toolbar"
              left-toolbar="undo redo clear | tip emoji code | h bold italic strikethrough quote | ul ol table hr | link image  | save | customToolbar"
              :include-level="[1, 2, 3, 4]"
              v-model="current.docInfo.md"
              :height="editHeight + 'px'"
              @save="mySave"
            >
            </v-md-editor>


           import { watch,ref  } from 'vue'
            import { ElMessage, ElRadioGroup, ElRadioButton } from 'element-plus'
            import mdController from '../service/md.js'
            
            // 狀態
            import { state } from '@naturefw/nf-state'
          
            // 獲取當前激活的信息
            const current = state.current
            // 文檔的加載和保存
            const { loadDocById, saveDoc } = mdController()
            
            // 可見的高度
            const editHeight = document.documentElement.clientHeight - 200
          
            // 單擊 保存 按鈕,實現保存功能
            const mySave = (text, html) => {
              saveDoc(current)
            }
            // 定時保存
            let timeout = null
            let isSaved = true
            const timeSave = () => {
              if (isSaved) {
                // 保存過了,重新計時
                isSaved = false
              } else {
                return // 有計時,退出
              }
          
              timeout = setTimeout(() => {
                // 保存文檔
                saveDoc(current).then(() => {
                  ElMessage({
                    message: '自動保存文檔成功!',
                    type: 'success',
                  })
                })
                isSaved = true
              }, 10000)
            }
          
            // 定時保存文檔
            watch(() => current.docInfo.md, () => {
              timeSave()
            })
          
            // 根據激活的菜單項,加載對應的文檔
            watch( () => current.menuId, async (id) => {
              const ver = current.ver
              loadDocById(id, ver).then((res) => {
                // 找到了文檔
                Object.assign(current.docInfo, res)
              }).catch((res) => {
                // 沒有文檔
                Object.assign(current.docInfo, res)
              })
            })
          
          • mdController 實現文檔的增刪改查的controller
          • timeSave 定時保存文檔,避免忘記點保存按鈕

          是不是挺簡單的。


          實現在線編寫代碼并且運行的功能

          因為是基于Vue3建立的項目,而且也是為了寫vue3相關的幫助文檔,那么就有一個很實用的要求:在線寫代碼并且可以運行

          個人感覺這個功能還是很實用的,我知道有第三方網站提供了這種功能,但是網速有點慢,另外有一種大炮打蚊子的感覺,我只需要實現簡單的代碼演示。

          于是我基于 vue 的 defineAsyncComponent 寫了一個簡單版的在線編寫代碼且運行的功能:

          /lib/runCode/run.vue

          <div style="padding: 5px; border: 1px solid #ccc!important;">
              <async-comp></async-comp>
            </div>
            import {
              defineAsyncComponent,
              ref, reactive,...
              // 其他常用的vue內置指令
            } from 'vue'
          
            // 使用 eval編譯js代碼
            const mysetup = `
              (function setup () {
                {{code}}
              })
            `
            
            // 通過屬性傳入需要運行的代碼和模板
            const props = defineProps({
              code: {
                type: Object,
                default: () => {
                  return {
                    js: '',
                    template: '',
                    style: ''
                  }
                }
              }
            })
          
            const code = props.code
          
            // 使用 defineAsyncComponent 讓代碼運行起來
            const AsyncComp = defineAsyncComponent(
              () => new Promise((resolve, reject) => {
                  resolve({
                    template: code.template, // 設置模板
                    style: [code.style], // 大概是樣式設置,但是好像沒啥效果
                    setup: (props, ctx) => {
                      const tmpJs = code.js // 獲取js代碼
                      let fun = null // 轉換后的函數
                      try {
                        if (tmpJs)
                          fun = eval(mysetup.replace('{{code}}', tmpJs)) // 用 eval 把 字符串 變成 函數
                      } catch (error) {
                        console.error('轉換出現異常:', error)
                      }
          
                      const re = typeof fun === 'function' ? fun : () => {}
          
                      return {
                        ...re(props, ctx) // 運行函數,解構返回對象
                      }
                    }
                  })
                })
            )
          
          • defineAsyncComponent

          實用 defineAsyncComponent 加載組件,需要設置三個部分:模板、setup和style。

          • template: 字符串形式,可以直接傳入
          • setup: js代碼,可以用eval的方式進行動態編譯。
          • style: 可以設置樣式。

          這樣即可讓在線編寫的代碼運行起來,當然功能有限,只能用于一些簡單的代碼演示。


          導出

          以上這些功能都是基于 indexedDB 進行的,想要發布的話,需要先導出為json文件。

          因為瀏覽器里不能直接寫文件,所以需要使用折中的方式:

          • 復制粘貼
          • 下載
          • 導出


          復制粘貼

          這個簡單,用文本域顯示json即可。

          下載

          使用 chrome 瀏覽器提供的下載功能下載文件。

           const uri = 'data:text/json;charset=utf-8,\ufeff' + encodeURIComponent(show.navi)
          
            //通過創建a標簽實現
            var link = document.createElement("a")
            link.href = uri
            //對下載的文件命名
            link.download = fileName
            document.body.appendChild(link)
            link.click()
            document.body.removeChild(link)
          

          以上介紹的是內部原理,如果只是想簡單使用的話,可以跳過,直接看下面的介紹。


          用后端寫文件

          以上兩種都不太方便,于是用node做了個簡單的后端API,用于實現寫入json文件的功能。

          代碼放在了 api文件夾里,可以使用 ```yarn api```運行。當然需要在 package.json 里做一下設置。

           "scripts": {
              "dev": "vite",
              "build": "vite build --mode project",
              "lib": "vite build --mode lib",
              "serve": "vite preview",
              "api": "node api/server.js"
            },

          實現一個幫助文檔的項目

          上面介紹的是庫項目的基本原理,我們要做幫助文檔的時候,并不需要那么復雜。

          使用 vite2 建立一個vue3的項目,然后安裝 @naturefw/press-edit,使用提供的組件即可方便的實現。

          main.js

          首先需要在 main.js 里面做一些設置。

          import { createApp } from 'vue'
          import App from './App.vue'
          
          // 設置 axios 的 baseUrl
          const baseUrl = (document.location.host.includes('.gitee.io')) ?
            '/doc-ui-core/' :  '/'
          
          // 輕量級狀態
          // 設置 indexedDB 數據庫,存放文檔的各種信息。
          import { setupIndexedDB, setupStore } from '@naturefw/press-edit'
          // 初始化 indexedDB 數據庫
          setupIndexedDB(baseUrl)
            
          // UI庫
          import ElementPlus from 'element-plus'
          // import 'element-plus/lib/theme-chalk/index.css'
          // import 'dayjs/locale/zh-cn'
          import zhCn from 'element-plus/es/locale/lang/zh-cn'
          
          // 二次封裝
          import { nfElementPlus } from '@naturefw/ui-elp'
          // 設置icon
          import installIcon from './icon/index.js'
          
          // 設置 Markdown 的配置函數
          import setMarkDown from './main-md.js'
          
          // 主題
          import vuepressTheme from '@kangc/v-md-editor/lib/theme/vuepress.js'
          
          const {
            VueMarkdownEditor, // Markdown 的編輯器
            VMdPreview // Markdown 的瀏覽器
          } = setMarkDown(vuepressTheme)
          
          const app = createApp(App)
          app.config.globalProperties.$ELEMENT = {
            locale: zhCn,
            size: 'small'
          }
          
          app.use(setupStore) // 狀態管理
            .use(nfElementPlus) // 二次封裝的組件
            .use(installIcon) // 注冊全局圖標
            .use(ElementPlus, { locale: zhCn, size: 'small' }) // UI庫
            .use(VueMarkdownEditor) // markDown編輯器
            .use(VMdPreview) // markDown 顯示
            .mount('#app')
          
          • baseUrl: 根據發布平臺的情況進行設置,比如這里需要設置為:“/doc-ui-core/”
          • setupIndexedDB: 初始化 indexedDB 數據庫
          • setupStore: 設置狀態
          • element-plus:element-plus 可以不掛載,但是css需要 import 進來,這里采用CDN的方式引入。
          • nfElementPlus: 二次封裝的組件,便于實現增刪改查。
          • setMarkDown: 加載 v-md-editor ,以及需要的插件。
          • vuepressTheme: 設置主題。

          設置 Markdown

          因為 v-md-editor 相關設置比較多,所以設置了一個單獨文件進行管理:

          /src/main-md.js

          // Markdown 編輯器
          import VueMarkdownEditor from '@kangc/v-md-editor'
          import '@kangc/v-md-editor/lib/style/base-editor.css'
          // 在這里引入,不被識別?
          // import vuepressTheme from '@kangc/v-md-editor/lib/theme/vuepress.js'
          import '@kangc/v-md-editor/lib/theme/style/vuepress.css'
          
          // 代碼高亮
          import Prism from 'prismjs'
          
          
          // emoji
          import createEmojiPlugin from '@kangc/v-md-editor/lib/plugins/emoji/index'
          import '@kangc/v-md-editor/lib/plugins/emoji/emoji.css'
          
          // 流程圖
          // import createMermaidPlugin from '@kangc/v-md-editor/lib/plugins/mermaid/cdn'
          // import '@kangc/v-md-editor/lib/plugins/mermaid/mermaid.css'
          
          // todoList
          import createTodoListPlugin from '@kangc/v-md-editor/lib/plugins/todo-list/index'
          import '@kangc/v-md-editor/lib/plugins/todo-list/todo-list.css'
          
          // 代碼行號
          import createLineNumbertPlugin from '@kangc/v-md-editor/lib/plugins/line-number/index';
          
          // 高亮代碼行
          import createHighlightLinesPlugin from '@kangc/v-md-editor/lib/plugins/highlight-lines/index'
          import '@kangc/v-md-editor/lib/plugins/highlight-lines/highlight-lines.css'
          
          // 復制代碼
          import createCopyCodePlugin from '@kangc/v-md-editor/lib/plugins/copy-code/index'
          import '@kangc/v-md-editor/lib/plugins/copy-code/copy-code.css'
          
          
          // markdown 顯示器
          import VMdPreview from '@kangc/v-md-editor/lib/preview'
          // import '@kangc/v-md-editor/lib/style/preview.css'
          
          
          /**
           * 設置 Markdown 編輯器 和瀏覽器
           * @param {*} vuepressTheme 
           * @returns 
           */
          export default function setMarkDown (vuepressTheme) {
          
            // 設置 vuePress 主題
            VueMarkdownEditor.use(vuepressTheme,
              {
                Prism,
                extend(md) {
                  // md為 markdown-it 實例,可以在此處進行修改配置,并使用 plugin 進行語法擴展
                  // md.set(option).use(plugin);
                },
              }
            )
            
            // 預覽
            VMdPreview.use(vuepressTheme,
              {
                Prism,
                extend(md) {
                  // md為 markdown-it 實例,可以在此處進行修改配置,并使用 plugin 進行語法擴展
                  // md.set(option).use(plugin);
                },
              }
            )
            
            // emoji
            VueMarkdownEditor.use(createEmojiPlugin())
            // 流程圖
            // VueMarkdownEditor.use(createMermaidPlugin())
            // todoList
            VueMarkdownEditor.use(createTodoListPlugin())
            // 代碼行號
            VueMarkdownEditor.use(createLineNumbertPlugin())
            // 高亮代碼行
            VueMarkdownEditor.use(createHighlightLinesPlugin())
            // 復制代碼
            VueMarkdownEditor.use(createCopyCodePlugin())
            
          
            // 預覽的插件
            VMdPreview.use(createEmojiPlugin())
            VMdPreview.use(createTodoListPlugin())
            VMdPreview.use(createLineNumbertPlugin())
            VMdPreview.use(createHighlightLinesPlugin())
            VMdPreview.use(createCopyCodePlugin())
            
            return {
              VueMarkdownEditor,
              VMdPreview
            }
          
          }
          


          不多介紹了,可以根據需要選擇插件。

          布局

          在App.vue文件里面進行整體布局

           <el-container>
              <el-header>
                <!--導航-->
                <div style="float: left;">
                  <!--寫網站logo、標題等-->
                  <h1>nf-press</h1>
                </div>
                <div style="float: right;min-width: 100px;height: 60px;padding-top: 13px;">
                  <!--寫網站logo、標題等-->
                  <el-switch v-model="$state.current.isView" v-bind="itemProps"></el-switch>
                </div>
                <div style="float: right;min-width: 600px;height: 60px;">
                  <!--網站導航-->
                  <doc-navi ></doc-navi>
                </div>
              </el-header>
              <el-container>
                <!--左側邊欄-->
                <el-aside width="330px">
                  <!--菜單-->
                  <doc-menu ></doc-menu>
                </el-aside>
                <el-main>
                  <!--文檔區域-->
                  <component
                    :is="docControl[$state.current.isView]"
                  />
                </el-main>
              </el-container>
            </el-container>
            import { reactive, defineAsyncComponent } from 'vue'
            import { ElHeader, ElContainer ,ElAside, ElMain } from 'element-plus'
            import { docMenu, docNavi, config } from '@naturefw/press-edit' // 菜單 導航
            import docView from './views/doc.vue' // 顯示文檔
          
            // 加載菜單子控件
            const docControl = {
              true: docView,
              false: defineAsyncComponent(() => import('./views/main.vue')) // 修改文檔
            }
          
            const itemProps = reactive({
              'inline-prompt': true,
              'active-text': '看',
              'inactive-text': '寫',
              'active-color': '#378FEB',
              'inactive-color': '#EA9712'
            })
          


          • $state:全局狀態,$state.current.isView 設置是否是瀏覽狀態。
          • doc-navi:導航組件
          • doc-menu:菜單組件
          • docControl:根據狀態選擇加載顯示組件或者編輯組件的字典。

          這種方式雖然有點麻煩,但是比較靈活,可以根據需要進行各種靈活設置,比如添加版權信息、備案信息、廣告等內容。

          導航、菜單、編輯和瀏覽

          直接使用組件實現,比較簡單不搬運了,直接看源碼即可。

          打包發布與版本管理

          需要打包的情況分為兩種:第一次打包、修改代碼(非在線編輯的代碼)后打包。

          如果只是文檔內容有變化的話,只需要直接上傳json文件即可,不需要再次打包。

          內置了一個簡單的版本管理功能,可以通過 ver.json文件里的版本號實現更新功能。


          主站蜘蛛池模板: 91久久精品午夜一区二区| 成人免费一区二区三区| 日韩av片无码一区二区三区不卡| 国产成人久久一区二区三区| 亚洲福利一区二区| 国产精品自在拍一区二区不卡| 亚洲熟妇无码一区二区三区| 在线精品亚洲一区二区三区| 免费一区二区无码视频在线播放| 无码日韩人妻av一区免费| 一区二区视频在线观看| 看电影来5566一区.二区| 国产高清精品一区| 国产在线观看一区二区三区四区| 无码中文字幕人妻在线一区二区三区 | 国产伦理一区二区三区| 在线精品亚洲一区二区| 韩国一区二区视频| 国产99视频精品一区| 麻豆高清免费国产一区| 午夜天堂一区人妻| 日韩人妻一区二区三区蜜桃视频| 国产AV一区二区三区无码野战| 国产亚洲欧洲Aⅴ综合一区| 好吊视频一区二区三区| 精品无码综合一区| 国产无套精品一区二区| 国产一区二区三区在线看| 国产在线一区二区| 亚洲乱码国产一区三区| 亚洲A∨无码一区二区三区| 久久青草国产精品一区| 亚洲乱码一区av春药高潮| 国产精品揄拍一区二区久久| 欧美一区内射最近更新| 国产无吗一区二区三区在线欢 | 狠狠做深爱婷婷综合一区| 亚洲片一区二区三区| 无码国产精品一区二区免费模式| 日韩免费视频一区二区| 成人精品一区二区户外勾搭野战|