diff --git a/.gitignore b/.gitignore
index dd94e6efce..d46e704e74 100644
--- a/.gitignore
+++ b/.gitignore
@@ -28,3 +28,5 @@ public/uploads/*
!public/uploads/.gitkeep
/.nyc_output
/coverage/
+
+.vscode/settings.json
\ No newline at end of file
diff --git a/.nvmrc b/.nvmrc
new file mode 100644
index 0000000000..fc5e4cfe99
--- /dev/null
+++ b/.nvmrc
@@ -0,0 +1 @@
+v10.20.1
diff --git a/app.js b/app.js
index 24e6b62bf7..4980d45d02 100644
--- a/app.js
+++ b/app.js
@@ -280,12 +280,18 @@ models.sequelize.sync().then(function () {
} else {
throw new Error('server still not ready after db synced')
}
+}).catch(err => {
+ logger.error('Can\'t sync database')
+ logger.error(err.stack)
+ logger.error('Process will exit now.')
+ process.exit(1)
})
// log uncaught exception
process.on('uncaughtException', function (err) {
logger.error('An uncaught exception has occured.')
logger.error(err)
+ console.error(err)
logger.error('Process will exit now.')
process.exit(1)
})
diff --git a/deployments/docker-compose.yml b/deployments/docker-compose.yml
index 5fe0ac7572..b5f2a4d20a 100644
--- a/deployments/docker-compose.yml
+++ b/deployments/docker-compose.yml
@@ -10,8 +10,11 @@ services:
- "database-data:/var/lib/postgresql/data"
restart: always
codimd:
- # you can use image or custom build below
- image: nabo.codimd.dev/hackmdio/hackmd:2.0.0
+ # you can use image or custom build below,
+ # if you need CJK character with exported PDF files,
+ # please change the image tag with `cjk` postfix version
+ image: nabo.codimd.dev/hackmdio/hackmd:2.1.0
+ # image: nabo.codimd.dev/hackmdio/hackmd:2.1.0-cjk
# build:
# context: ..
# dockerfile: ./deployments/Dockerfile
diff --git a/lib/auth/gitlab/index.js b/lib/auth/gitlab/index.js
index 72ab0cde42..ab4f6900a8 100644
--- a/lib/auth/gitlab/index.js
+++ b/lib/auth/gitlab/index.js
@@ -18,8 +18,8 @@ const gitlabAuthStrategy = new GitlabStrategy({
callbackURL: config.serverURL + '/auth/gitlab/callback'
}, passportGeneralCallback)
-if (process.env['https_proxy']) {
- const httpsProxyAgent = new HttpsProxyAgent(process.env['https_proxy'])
+if (process.env.https_proxy) {
+ const httpsProxyAgent = new HttpsProxyAgent(process.env.https_proxy)
gitlabAuthStrategy._oauth2.setAgent(httpsProxyAgent)
}
diff --git a/lib/history/index.js b/lib/history/index.js
index 3826ce98aa..ab8b423228 100644
--- a/lib/history/index.js
+++ b/lib/history/index.js
@@ -131,7 +131,7 @@ function historyPost (req, res) {
if (req.isAuthenticated()) {
var noteId = req.params.noteId
if (!noteId) {
- if (typeof req.body['history'] === 'undefined') return response.errorBadRequest(req, res)
+ if (typeof req.body.history === 'undefined') return response.errorBadRequest(req, res)
if (config.debug) { logger.info('SERVER received history from [' + req.user.id + ']: ' + req.body.history) }
try {
var history = JSON.parse(req.body.history)
@@ -147,7 +147,7 @@ function historyPost (req, res) {
return response.errorBadRequest(req, res)
}
} else {
- if (typeof req.body['pinned'] === 'undefined') return response.errorBadRequest(req, res)
+ if (typeof req.body.pinned === 'undefined') return response.errorBadRequest(req, res)
getHistory(req.user.id, function (err, history) {
if (err) return response.errorInternalError(req, res)
if (!history) return response.errorNotFound(req, res)
diff --git a/lib/imageRouter/filesystem.js b/lib/imageRouter/filesystem.js
index 53ecc9d424..49a811ef49 100644
--- a/lib/imageRouter/filesystem.js
+++ b/lib/imageRouter/filesystem.js
@@ -1,10 +1,39 @@
'use strict'
+
+const crypto = require('crypto')
+const fs = require('fs')
const URL = require('url').URL
const path = require('path')
const config = require('../config')
const logger = require('../logger')
+/**
+ * generate a random filename for uploaded image
+ */
+function randomFilename () {
+ const buf = crypto.randomBytes(16)
+ return `upload_${buf.toString('hex')}`
+}
+
+/**
+ * pick a filename not exist in filesystem
+ * maximum attempt 5 times
+ */
+function pickFilename (defaultFilename) {
+ let retryCounter = 5
+ let filename = defaultFilename
+ const extname = path.extname(defaultFilename)
+ while (retryCounter-- > 0) {
+ if (fs.existsSync(path.join(config.uploadsPath, filename))) {
+ filename = `${randomFilename()}${extname}`
+ continue
+ }
+ return filename
+ }
+ throw new Error('file exists.')
+}
+
exports.uploadImage = function (imagePath, callback) {
if (!imagePath || typeof imagePath !== 'string') {
callback(new Error('Image path is missing or wrong'), null)
@@ -16,11 +45,24 @@ exports.uploadImage = function (imagePath, callback) {
return
}
+ let filename = path.basename(imagePath)
+ try {
+ filename = pickFilename(path.basename(imagePath))
+ } catch (e) {
+ return callback(e, null)
+ }
+
+ try {
+ fs.copyFileSync(imagePath, path.join(config.uploadsPath, filename))
+ } catch (e) {
+ return callback(e, null)
+ }
+
let url
try {
- url = (new URL(path.basename(imagePath), config.serverURL + '/uploads/')).href
+ url = (new URL(filename, config.serverURL + '/uploads/')).href
} catch (e) {
- url = config.serverURL + '/uploads/' + path.basename(imagePath)
+ url = config.serverURL + '/uploads/' + filename
}
callback(null, url)
diff --git a/lib/imageRouter/index.js b/lib/imageRouter/index.js
index 9b0c40289c..5af005bc15 100644
--- a/lib/imageRouter/index.js
+++ b/lib/imageRouter/index.js
@@ -1,5 +1,6 @@
'use strict'
+const fs = require('fs')
const Router = require('express').Router
const formidable = require('formidable')
@@ -15,10 +16,6 @@ imageRouter.post('/uploadimage', function (req, res) {
form.keepExtensions = true
- if (config.imageUploadType === 'filesystem') {
- form.uploadDir = config.uploadsPath
- }
-
form.parse(req, function (err, fields, files) {
if (err || !files.image || !files.image.path) {
response.errorForbidden(req, res)
@@ -29,6 +26,8 @@ imageRouter.post('/uploadimage', function (req, res) {
const uploadProvider = require('./' + config.imageUploadType)
uploadProvider.uploadImage(files.image.path, function (err, url) {
+ // remove temporary upload file, and ignore any error
+ fs.unlink(files.image.path, () => {})
if (err !== null) {
logger.error(err)
return res.status(500).end('upload image error')
diff --git a/lib/models/note.js b/lib/models/note.js
index 8030be0059..d7109d4449 100644
--- a/lib/models/note.js
+++ b/lib/models/note.js
@@ -367,8 +367,13 @@ module.exports = function (sequelize, DataTypes) {
Note.extractNoteTags = function (meta, $) {
var tags = []
var rawtags = []
+ var metaTags
if (meta.tags && (typeof meta.tags === 'string' || typeof meta.tags === 'number')) {
- var metaTags = ('' + meta.tags).split(',')
+ metaTags = ('' + meta.tags).split(',')
+ } else if (meta.tags && (Array.isArray(meta.tags))) {
+ metaTags = meta.tags
+ }
+ if (metaTags) {
for (let i = 0; i < metaTags.length; i++) {
var text = metaTags[i].trim()
if (text) rawtags.push(text)
diff --git a/lib/note/index.js b/lib/note/index.js
index b9b7c9e351..a387b59dba 100644
--- a/lib/note/index.js
+++ b/lib/note/index.js
@@ -2,10 +2,9 @@
const config = require('../config')
const logger = require('../logger')
-
const { Note, User } = require('../models')
-const { newCheckViewPermission, errorForbidden, responseCodiMD, errorNotFound } = require('../response')
+const { newCheckViewPermission, errorForbidden, responseCodiMD, errorNotFound, errorInternalError } = require('../response')
const { updateHistory } = require('../history')
const { actionPublish, actionSlide, actionInfo, actionDownload, actionPDF, actionGist, actionRevision, actionPandoc } = require('./noteActions')
@@ -121,6 +120,7 @@ async function showPublishNote (req, res) {
const data = {
title: title,
description: meta.description || (markdown ? Note.generateDescription(markdown) : null),
+ image: meta.image,
viewcount: note.viewcount,
createtime: createTime,
updatetime: updateTime,
@@ -190,6 +190,49 @@ async function noteActions (req, res) {
}
}
+async function getMyNoteList (userId, callback) {
+ const myNotes = await Note.findAll({
+ where: {
+ ownerId: userId
+ }
+ })
+ if (!myNotes) {
+ return callback(null, null)
+ }
+ try {
+ const myNoteList = myNotes.map(note => ({
+ id: Note.encodeNoteId(note.id),
+ text: note.title,
+ tags: Note.parseNoteInfo(note.content).tags,
+ createdAt: note.createdAt,
+ lastchangeAt: note.lastchangeAt,
+ shortId: note.shortid
+ }))
+ if (config.debug) {
+ logger.info('Parse myNoteList success: ' + userId)
+ }
+ return callback(null, myNoteList)
+ } catch (err) {
+ logger.error('Parse myNoteList failed')
+ return callback(err, null)
+ }
+}
+
+function listMyNotes (req, res) {
+ if (req.isAuthenticated()) {
+ getMyNoteList(req.user.id, (err, myNoteList) => {
+ if (err) return errorInternalError(req, res)
+ if (!myNoteList) return errorNotFound(req, res)
+ res.send({
+ myNotes: myNoteList
+ })
+ })
+ } else {
+ return errorForbidden(req, res)
+ }
+}
+
exports.showNote = showNote
exports.showPublishNote = showPublishNote
exports.noteActions = noteActions
+exports.listMyNotes = listMyNotes
diff --git a/lib/routes.js b/lib/routes.js
index f4345039d7..48ac61f3dc 100644
--- a/lib/routes.js
+++ b/lib/routes.js
@@ -70,6 +70,8 @@ appRouter.get('/s/:shortid/:action', response.publishNoteActions)
appRouter.get('/p/:shortid', response.showPublishSlide)
// publish slide actions
appRouter.get('/p/:shortid/:action', response.publishSlideActions)
+// gey my note list
+appRouter.get('/api/notes/myNotes', noteController.listMyNotes)
// get note by id
appRouter.get('/:noteId', wrap(noteController.showNote))
// note actions
diff --git a/locales/zh-CN.json b/locales/zh-CN.json
index 93e1c86f82..667f457fe2 100644
--- a/locales/zh-CN.json
+++ b/locales/zh-CN.json
@@ -1,117 +1,121 @@
{
"Collaborative markdown notes": "Markdown 协作笔记",
- "Realtime collaborative markdown notes on all platforms.": "使用 Markdown 的跨平台即时协作笔记",
- "Best way to write and share your knowledge in markdown.": "您使用 Markdown 写作与分享知识的最佳方式",
+ "Realtime collaborative markdown notes on all platforms.": "使用 Markdown 的跨平台即时协作笔记。",
+ "Best way to write and share your knowledge in markdown.": "写作与分享 Markdown 的最佳平台。",
"Intro": "简介",
"History": "历史",
- "New guest note": "建立访客笔记",
- "Collaborate with URL": "使用网址协作",
+ "New guest note": "新建访客笔记",
+ "Collaborate with URL": "实时协作",
"Support charts and MathJax": "支持图表与 MathJax",
- "Support slide mode": "支持简报模式",
+ "Support slide mode": "支持幻灯模式",
"Sign In": "登录",
"Below is the history from browser": "以下为来自浏览器的历史",
"Welcome!": "欢迎!",
- "New note": "建立笔记",
+ "New note": "新建笔记",
"or": "或",
"Sign Out": "登出",
"Explore all features": "探索所有功能",
"Select tags...": "选择标签...",
"Search keyword...": "搜索关键字...",
- "Sort by title": "用标题排序",
+ "Sort by title": "按标题排序",
"Title": "标题",
- "Sort by time": "用时间排序",
+ "Sort by time": "按时间排序",
"Time": "时间",
"Export history": "导出历史",
"Import history": "导入历史",
"Clear history": "清空历史",
"Refresh history": "刷新历史",
- "No history": "没有历史",
+ "No history": "无历史记录",
"Import from browser": "从浏览器导入",
"Releases": "版本",
- "Are you sure?": "你确定吗?",
- "Do you really want to delete this note?": "确定要删除这个文件吗?",
- "All users will lose their connection.": "所有用户将失去连接",
+ "Are you sure?": "您确定吗?",
+ "Do you really want to delete this note?": "您确定要删除这篇笔记吗?",
+ "All users will lose their connection.": "所有用户将失去连接。",
"Cancel": "取消",
- "Yes, do it!": "没错,就这样办!",
+ "Yes, do it!": "是的,就这样做!",
"Choose method": "选择方式",
"Sign in via %s": "通过 %s 登录",
- "New": "新增",
+ "New": "新建",
"Publish": "发表",
- "Extra": "增益",
+ "Extra": "附加功能",
"Revision": "修订版本",
- "Slide Mode": "简报模式",
+ "Slide Mode": "幻灯模式",
"Export": "导出",
"Import": "导入",
"Clipboard": "剪贴板",
"Download": "下载",
- "Raw HTML": "纯 HTML",
+ "Raw HTML": "原始 HTML",
"Edit": "编辑",
- "View": "检视",
+ "View": "预览",
"Both": "双栏",
"Help": "帮助",
"Upload Image": "上传图片",
"Menu": "菜单",
- "This page need refresh": "此页面需要重新整理",
- "You have an incompatible client version.": "您使用的是不相容的客户端",
- "Refresh to update.": "请重新整理来更新",
- "New version available!": "新版本来了!",
- "See releases notes here": "请由此查阅更新纪录",
- "Refresh to enjoy new features.": "请重新整理来享受最新功能",
- "Your user state has changed.": "您的使用者状态已变更",
- "Refresh to load new user state.": "请重新整理来载入新的使用者状态",
- "Refresh": "重新整理",
- "Contacts": "联络方式",
+ "This page need refresh": "此页面需要刷新",
+ "You have an incompatible client version.": "您的客户端版本不兼容。",
+ "Refresh to update.": "刷新页面以更新。",
+ "New version available!": "新版本可用!",
+ "See releases notes here": "在此查看更新记录",
+ "Refresh to enjoy new features.": "刷新页面以体验新功能。",
+ "Your user state has changed.": "您的用户状态已变更。",
+ "Refresh to load new user state.": "刷新页面以加载新的用户状态。",
+ "Refresh": "刷新",
+ "Contacts": "联系我们",
"Report an issue": "报告问题",
"Meet us on %s": "在 %s 上联系我们",
- "Send us email": "寄信给我们",
- "Documents": "文件",
- "Features": "功能简介",
- "YAML Metadata": "YAML Metadata",
- "Slide Example": "简报范例",
- "Cheatsheet": "快速简表",
+ "Send us email": "给我们发送电子邮件",
+ "Documents": "文档",
+ "Features": "功能",
+ "YAML Metadata": "YAML 元数据",
+ "Slide Example": "幻灯范例",
+ "Cheatsheet": "速查表",
"Example": "范例",
"Syntax": "语法",
"Header": "标题",
- "Unordered List": "无序清单",
- "Ordered List": "有序清单",
- "Todo List": "待办事项",
+ "Unordered List": "无序列表",
+ "Ordered List": "有序列表",
+ "Todo List": "清单",
"Blockquote": "引用",
"Bold font": "粗体",
"Italics font": "斜体",
"Strikethrough": "删除线",
- "Inserted text": "插入文字",
- "Marked text": "标记文字",
+ "Inserted text": "下划线文字",
+ "Marked text": "高亮文字",
"Link": "链接",
"Image": "图片",
"Code": "代码",
- "Externals": "外部",
- "This is a alert area.": "这是警告区块",
+ "Externals": "外部扩展",
+ "This is a alert area.": "这是一个警告区块。",
"Revert": "还原",
"Import from clipboard": "从剪贴板导入",
- "Paste your markdown or webpage here...": "在这里贴上 Markdown 或是网页内容...",
+ "Paste your markdown or webpage here...": "在这里粘贴 Markdown 或网页内容...",
"Clear": "清除",
- "This note is locked": "此份笔记已被锁定",
- "Sorry, only owner can edit this note.": "抱歉,只有拥有者可以编辑此笔记",
+ "This note is locked": "这篇笔记已被锁定",
+ "Sorry, only owner can edit this note.": "抱歉,只有所有者可以编辑这篇笔记。",
"OK": "好的",
- "Reach the limit": "到达上限",
- "Sorry, you've reached the max length this note can be.": "抱歉,您已使用到此份笔记可用的最大长度",
- "Please reduce the content or divide it to more notes, thank you!": "请减少内容或是将内容切成更多笔记,谢谢!",
+ "Reach the limit": "达到上限",
+ "Sorry, you've reached the max length this note can be.": "抱歉,您的这篇笔记已达到可用的最大长度。",
+ "Please reduce the content or divide it to more notes, thank you!": "请减少笔记的内容。",
"Import from Gist": "从 Gist 导入",
- "Paste your gist url here...": "在这里贴上 gist 网址...",
+ "Paste your gist url here...": "在这里粘贴 Gist 网址...",
"Import from Snippet": "从 Snippet 导入",
"Select From Available Projects": "从可用的项目中选择",
"Select From Available Snippets": "从可用的 Snippets 中选择",
- "OR": "或是",
+ "OR": "或",
"Export to Snippet": "导出到 Snippet",
"Select Visibility Level": "选择可见层级",
"Night Theme": "夜间主题",
- "Follow us on %s and %s.": "在%s和%s上关注我们",
- "Privacy": "隐私政策",
+ "Follow us on %s and %s.": "在 %s 和 %s 上关注我们",
+ "Privacy": "隐私",
"Terms of Use": "使用条款",
- "Do you really want to delete your user account?": "你确定真的想要删除帐户?",
- "This will delete your account, all notes that are owned by you and remove all references to your account from other notes.": "我们将会删除你的帐户、你所拥有的笔记、以及你在别人笔记里的作者纪录。",
+ "Do you really want to delete your user account?": "您确定要删除帐户吗?",
+ "This will delete your account, all notes that are owned by you and remove all references to your account from other notes.": "您的帐户、您所拥有的笔记、他人笔记中对您帐户的引用都将被删除。",
"Delete user": "删除帐户",
- "Export user data": "汇出使用者资料",
- "Help us translating on %s": "来 %s 帮我们翻译",
- "Source Code": "源码"
-}
\ No newline at end of file
+ "Export user data": "导出用户数据",
+ "Help us translating on %s": "在 %s 上帮我们翻译",
+ "Source Code": "源代码",
+ "Powered by %s": "由 %s 驱动",
+ "Register": "注册",
+ "Export with pandoc": "使用 Pandoc 导出",
+ "Select output format": "选择输出格式"
+}
diff --git a/package-lock.json b/package-lock.json
index 19377a7af6..8bb4481ffe 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -1,6 +1,6 @@
{
"name": "codimd",
- "version": "2.1.0",
+ "version": "2.2.0",
"lockfileVersion": 1,
"requires": true,
"dependencies": {
@@ -1085,6 +1085,266 @@
"@types/node": "*"
}
},
+ "@types/d3": {
+ "version": "5.7.2",
+ "resolved": "https://registry.npmjs.org/@types/d3/-/d3-5.7.2.tgz",
+ "integrity": "sha512-7/wClB8ycneWGy3jdvLfXKTd5SoTg9hji7IdJ0RuO9xTY54YpJ8zlcFADcXhY1J3kCBwxp+/1jeN6a5OMwgYOw==",
+ "dev": true,
+ "requires": {
+ "@types/d3-array": "^1",
+ "@types/d3-axis": "*",
+ "@types/d3-brush": "*",
+ "@types/d3-chord": "*",
+ "@types/d3-collection": "*",
+ "@types/d3-color": "*",
+ "@types/d3-contour": "*",
+ "@types/d3-dispatch": "*",
+ "@types/d3-drag": "*",
+ "@types/d3-dsv": "*",
+ "@types/d3-ease": "*",
+ "@types/d3-fetch": "*",
+ "@types/d3-force": "*",
+ "@types/d3-format": "*",
+ "@types/d3-geo": "*",
+ "@types/d3-hierarchy": "*",
+ "@types/d3-interpolate": "*",
+ "@types/d3-path": "*",
+ "@types/d3-polygon": "*",
+ "@types/d3-quadtree": "*",
+ "@types/d3-random": "*",
+ "@types/d3-scale": "*",
+ "@types/d3-scale-chromatic": "*",
+ "@types/d3-selection": "*",
+ "@types/d3-shape": "*",
+ "@types/d3-time": "*",
+ "@types/d3-time-format": "*",
+ "@types/d3-timer": "*",
+ "@types/d3-transition": "*",
+ "@types/d3-voronoi": "*",
+ "@types/d3-zoom": "*"
+ }
+ },
+ "@types/d3-array": {
+ "version": "1.2.7",
+ "resolved": "https://registry.npmjs.org/@types/d3-array/-/d3-array-1.2.7.tgz",
+ "integrity": "sha512-51vHWuUyDOi+8XuwPrTw3cFqyh2Slg9y8COYkRfjCPG9TfYqY0hoNPzv/8BrcAy0FeQBzqEo/D/8Nk2caOQJnA==",
+ "dev": true
+ },
+ "@types/d3-axis": {
+ "version": "1.0.12",
+ "resolved": "https://registry.npmjs.org/@types/d3-axis/-/d3-axis-1.0.12.tgz",
+ "integrity": "sha512-BZISgSD5M8TgURyNtcPAmUB9sk490CO1Thb6/gIn0WZTt3Y50IssX+2Z0vTccoqZksUDTep0b+o4ofXslvNbqg==",
+ "dev": true,
+ "requires": {
+ "@types/d3-selection": "*"
+ }
+ },
+ "@types/d3-brush": {
+ "version": "1.1.1",
+ "resolved": "https://registry.npmjs.org/@types/d3-brush/-/d3-brush-1.1.1.tgz",
+ "integrity": "sha512-Exx14trm/q2cskHyMjCrdDllOQ35r1/pmZXaOIt8bBHwYNk722vWY3VxHvN0jdFFX7p2iL3+gD+cGny/aEmhlw==",
+ "dev": true,
+ "requires": {
+ "@types/d3-selection": "*"
+ }
+ },
+ "@types/d3-chord": {
+ "version": "1.0.9",
+ "resolved": "https://registry.npmjs.org/@types/d3-chord/-/d3-chord-1.0.9.tgz",
+ "integrity": "sha512-UA6lI9CVW5cT5Ku/RV4hxoFn4mKySHm7HEgodtfRthAj1lt9rKZEPon58vyYfk+HIAm33DtJJgZwMXy2QgyPXw==",
+ "dev": true
+ },
+ "@types/d3-collection": {
+ "version": "1.0.8",
+ "resolved": "https://registry.npmjs.org/@types/d3-collection/-/d3-collection-1.0.8.tgz",
+ "integrity": "sha512-y5lGlazdc0HNO0F3UUX2DPE7OmYvd9Kcym4hXwrJcNUkDaypR5pX+apuMikl9LfTxKItJsY9KYvzBulpCKyvuQ==",
+ "dev": true
+ },
+ "@types/d3-color": {
+ "version": "1.2.2",
+ "resolved": "https://registry.npmjs.org/@types/d3-color/-/d3-color-1.2.2.tgz",
+ "integrity": "sha512-6pBxzJ8ZP3dYEQ4YjQ+NVbQaOflfgXq/JbDiS99oLobM2o72uAST4q6yPxHv6FOTCRC/n35ktuo8pvw/S4M7sw==",
+ "dev": true
+ },
+ "@types/d3-contour": {
+ "version": "1.3.0",
+ "resolved": "https://registry.npmjs.org/@types/d3-contour/-/d3-contour-1.3.0.tgz",
+ "integrity": "sha512-AUCUIjEnC5lCGBM9hS+MryRaFLIrPls4Rbv6ktqbd+TK/RXZPwOy9rtBWmGpbeXcSOYCJTUDwNJuEnmYPJRxHQ==",
+ "dev": true,
+ "requires": {
+ "@types/d3-array": "*",
+ "@types/geojson": "*"
+ }
+ },
+ "@types/d3-dispatch": {
+ "version": "1.0.8",
+ "resolved": "https://registry.npmjs.org/@types/d3-dispatch/-/d3-dispatch-1.0.8.tgz",
+ "integrity": "sha512-lCDtqoYez0TgFN3FljBXrz2icqeSzD0gufGook6DPBia+NOh2TBfogjHIsmNa/a+ZOewlHtq4cgLY80O1uLymw==",
+ "dev": true
+ },
+ "@types/d3-drag": {
+ "version": "1.2.3",
+ "resolved": "https://registry.npmjs.org/@types/d3-drag/-/d3-drag-1.2.3.tgz",
+ "integrity": "sha512-rWB5SPvkYVxW3sqUxHOJUZwifD0KqvKwvt1bhNqcLpW6Azsd0BJgRNcyVW8GAferaAk5r8dzeZnf9zKlg9+xMQ==",
+ "dev": true,
+ "requires": {
+ "@types/d3-selection": "*"
+ }
+ },
+ "@types/d3-dsv": {
+ "version": "1.0.36",
+ "resolved": "https://registry.npmjs.org/@types/d3-dsv/-/d3-dsv-1.0.36.tgz",
+ "integrity": "sha512-jbIWQ27QJcBNMZbQv0NSQMHnBDCmxghAxePxgyiPH1XPCRkOsTBei7jcdi3fDrUCGpCV3lKrSZFSlOkhUQVClA==",
+ "dev": true
+ },
+ "@types/d3-ease": {
+ "version": "1.0.9",
+ "resolved": "https://registry.npmjs.org/@types/d3-ease/-/d3-ease-1.0.9.tgz",
+ "integrity": "sha512-U5ADevQ+W6fy32FVZZC9EXallcV/Mi12A5Tkd0My5MrC7T8soMQEhlDAg88XUWm0zoCQlB4XV0en/24LvuDB4Q==",
+ "dev": true
+ },
+ "@types/d3-fetch": {
+ "version": "1.1.5",
+ "resolved": "https://registry.npmjs.org/@types/d3-fetch/-/d3-fetch-1.1.5.tgz",
+ "integrity": "sha512-o9c0ItT5/Gl3wbNuVpzRnYX1t3RghzeWAjHUVLuyZJudiTxC4f/fC0ZPFWLQ2lVY8pAMmxpV8TJ6ETYCgPeI3A==",
+ "dev": true,
+ "requires": {
+ "@types/d3-dsv": "*"
+ }
+ },
+ "@types/d3-force": {
+ "version": "1.2.1",
+ "resolved": "https://registry.npmjs.org/@types/d3-force/-/d3-force-1.2.1.tgz",
+ "integrity": "sha512-jqK+I36uz4kTBjyk39meed5y31Ab+tXYN/x1dn3nZEus9yOHCLc+VrcIYLc/aSQ0Y7tMPRlIhLetulME76EiiA==",
+ "dev": true
+ },
+ "@types/d3-format": {
+ "version": "1.3.1",
+ "resolved": "https://registry.npmjs.org/@types/d3-format/-/d3-format-1.3.1.tgz",
+ "integrity": "sha512-KAWvReOKMDreaAwOjdfQMm0HjcUMlQG47GwqdVKgmm20vTd2pucj0a70c3gUSHrnsmo6H2AMrkBsZU2UhJLq8A==",
+ "dev": true
+ },
+ "@types/d3-geo": {
+ "version": "1.11.1",
+ "resolved": "https://registry.npmjs.org/@types/d3-geo/-/d3-geo-1.11.1.tgz",
+ "integrity": "sha512-Ox8WWOG3igDRoep/dNsGbOiSJYdUG3ew/6z0ETvHyAtXZVBjOE0S96zSSmzgl0gqQ3RdZjn2eeJOj9oRcMZPkQ==",
+ "dev": true,
+ "requires": {
+ "@types/geojson": "*"
+ }
+ },
+ "@types/d3-hierarchy": {
+ "version": "1.1.6",
+ "resolved": "https://registry.npmjs.org/@types/d3-hierarchy/-/d3-hierarchy-1.1.6.tgz",
+ "integrity": "sha512-vvSaIDf/Ov0o3KwMT+1M8+WbnnlRiGjlGD5uvk83a1mPCTd/E5x12bUJ/oP55+wUY/4Kb5kc67rVpVGJ2KUHxg==",
+ "dev": true
+ },
+ "@types/d3-interpolate": {
+ "version": "1.3.1",
+ "resolved": "https://registry.npmjs.org/@types/d3-interpolate/-/d3-interpolate-1.3.1.tgz",
+ "integrity": "sha512-z8Zmi08XVwe8e62vP6wcA+CNuRhpuUU5XPEfqpG0hRypDE5BWNthQHB1UNWWDB7ojCbGaN4qBdsWp5kWxhT1IQ==",
+ "dev": true,
+ "requires": {
+ "@types/d3-color": "*"
+ }
+ },
+ "@types/d3-path": {
+ "version": "1.0.8",
+ "resolved": "https://registry.npmjs.org/@types/d3-path/-/d3-path-1.0.8.tgz",
+ "integrity": "sha512-AZGHWslq/oApTAHu9+yH/Bnk63y9oFOMROtqPAtxl5uB6qm1x2lueWdVEjsjjV3Qc2+QfuzKIwIR5MvVBakfzA==",
+ "dev": true
+ },
+ "@types/d3-polygon": {
+ "version": "1.0.7",
+ "resolved": "https://registry.npmjs.org/@types/d3-polygon/-/d3-polygon-1.0.7.tgz",
+ "integrity": "sha512-Xuw0eSjQQKs8jTiNbntWH0S+Xp+JyhqxmQ0YAQ3rDu6c3kKMFfgsaGN7Jv5u3zG6yVX/AsLP/Xs/QRjmi9g43Q==",
+ "dev": true
+ },
+ "@types/d3-quadtree": {
+ "version": "1.0.7",
+ "resolved": "https://registry.npmjs.org/@types/d3-quadtree/-/d3-quadtree-1.0.7.tgz",
+ "integrity": "sha512-0ajFawWicfjsaCLh6NzxOyVDYhQAmMFbsiI3MPGLInorauHFEh9/Cl6UHNf+kt/J1jfoxKY/ZJaKAoDpbvde5Q==",
+ "dev": true
+ },
+ "@types/d3-random": {
+ "version": "1.1.2",
+ "resolved": "https://registry.npmjs.org/@types/d3-random/-/d3-random-1.1.2.tgz",
+ "integrity": "sha512-Jui+Zn28pQw/3EayPKaN4c/PqTvqNbIPjHkgIIFnxne1FdwNjfHtAIsZIBMKlquQNrrMjFzCrlF2gPs3xckqaA==",
+ "dev": true
+ },
+ "@types/d3-scale": {
+ "version": "2.2.0",
+ "resolved": "https://registry.npmjs.org/@types/d3-scale/-/d3-scale-2.2.0.tgz",
+ "integrity": "sha512-oQFanN0/PiR2oySHfj+zAAkK1/p4LD32Nt1TMVmzk+bYHk7vgIg/iTXQWitp1cIkDw4LMdcgvO63wL+mNs47YA==",
+ "dev": true,
+ "requires": {
+ "@types/d3-time": "*"
+ }
+ },
+ "@types/d3-scale-chromatic": {
+ "version": "1.5.0",
+ "resolved": "https://registry.npmjs.org/@types/d3-scale-chromatic/-/d3-scale-chromatic-1.5.0.tgz",
+ "integrity": "sha512-9/D7cOBKdZdTCPc6re0HeSUFBM0aFzdNdmYggUWT9SRRiYSOa6Ys2xdTwHKgc1WS3gGfwTMatBOdWCS863REsg==",
+ "dev": true
+ },
+ "@types/d3-selection": {
+ "version": "1.4.2",
+ "resolved": "https://registry.npmjs.org/@types/d3-selection/-/d3-selection-1.4.2.tgz",
+ "integrity": "sha512-ksY8UxvTXpzD91Dy3D9zZg98yF2ZEPMKJd8ZQJlZt1QH3Xxr08s6fESEdC2l0Kbe6Xd9VhaoJX06cRaMR1lEnA==",
+ "dev": true
+ },
+ "@types/d3-shape": {
+ "version": "1.3.2",
+ "resolved": "https://registry.npmjs.org/@types/d3-shape/-/d3-shape-1.3.2.tgz",
+ "integrity": "sha512-LtD8EaNYCaBRzHzaAiIPrfcL3DdIysc81dkGlQvv7WQP3+YXV7b0JJTtR1U3bzeRieS603KF4wUo+ZkJVenh8w==",
+ "dev": true,
+ "requires": {
+ "@types/d3-path": "*"
+ }
+ },
+ "@types/d3-time": {
+ "version": "1.0.10",
+ "resolved": "https://registry.npmjs.org/@types/d3-time/-/d3-time-1.0.10.tgz",
+ "integrity": "sha512-aKf62rRQafDQmSiv1NylKhIMmznsjRN+MnXRXTqHoqm0U/UZzVpdrtRnSIfdiLS616OuC1soYeX1dBg2n1u8Xw==",
+ "dev": true
+ },
+ "@types/d3-time-format": {
+ "version": "2.1.1",
+ "resolved": "https://registry.npmjs.org/@types/d3-time-format/-/d3-time-format-2.1.1.tgz",
+ "integrity": "sha512-tJSyXta8ZyJ52wDDHA96JEsvkbL6jl7wowGmuf45+fAkj5Y+SQOnz0N7/H68OWmPshPsAaWMQh+GAws44IzH3g==",
+ "dev": true
+ },
+ "@types/d3-timer": {
+ "version": "1.0.9",
+ "resolved": "https://registry.npmjs.org/@types/d3-timer/-/d3-timer-1.0.9.tgz",
+ "integrity": "sha512-WvfJ3LFxBbWjqRGz9n7GJt08RrTHPJDVsIwwoCMROlqF+iDacYiAFjf9oqnq0mXpb2juA2N/qjKP+MKdal3YNQ==",
+ "dev": true
+ },
+ "@types/d3-transition": {
+ "version": "1.1.6",
+ "resolved": "https://registry.npmjs.org/@types/d3-transition/-/d3-transition-1.1.6.tgz",
+ "integrity": "sha512-/F+O2r4oz4G9ATIH3cuSCMGphAnl7VDx7SbENEK0NlI/FE8Jx2oiIrv0uTrpg7yF/AmuWbqp7AGdEHAPIh24Gg==",
+ "dev": true,
+ "requires": {
+ "@types/d3-selection": "*"
+ }
+ },
+ "@types/d3-voronoi": {
+ "version": "1.1.9",
+ "resolved": "https://registry.npmjs.org/@types/d3-voronoi/-/d3-voronoi-1.1.9.tgz",
+ "integrity": "sha512-DExNQkaHd1F3dFPvGA/Aw2NGyjMln6E9QzsiqOcBgnE+VInYnFBHBBySbZQts6z6xD+5jTfKCP7M4OqMyVjdwQ==",
+ "dev": true
+ },
+ "@types/d3-zoom": {
+ "version": "1.7.4",
+ "resolved": "https://registry.npmjs.org/@types/d3-zoom/-/d3-zoom-1.7.4.tgz",
+ "integrity": "sha512-5jnFo/itYhJeB2khO/lKe730kW/h2EbKMOvY0uNp3+7NdPm4w63DwPEMxifQZ7n902xGYK5DdU67FmToSoy4VA==",
+ "dev": true,
+ "requires": {
+ "@types/d3-interpolate": "*",
+ "@types/d3-selection": "*"
+ }
+ },
"@types/estree": {
"version": "0.0.39",
"resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.39.tgz",
@@ -1116,6 +1376,12 @@
"integrity": "sha512-mky/O83TXmGY39P1H9YbUpjV6l6voRYlufqfFCvel8l1phuy8HRjdWc1rrPuN53ITBJlbyMSV6z3niOySO5pgQ==",
"dev": true
},
+ "@types/geojson": {
+ "version": "7946.0.7",
+ "resolved": "https://registry.npmjs.org/@types/geojson/-/geojson-7946.0.7.tgz",
+ "integrity": "sha512-wE2v81i4C4Ol09RtsWFAqg3BUitWbHSpSlIo+bNdsCJijO9sjme+zm+73ZMCa/qMC8UEERxzGbvmr1cffo2SiQ==",
+ "dev": true
+ },
"@types/http-assert": {
"version": "1.5.1",
"resolved": "https://registry.npmjs.org/@types/http-assert/-/http-assert-1.5.1.tgz",
@@ -4665,6 +4931,15 @@
"d3-dsv": "1"
}
},
+ "d3-flextree": {
+ "version": "2.1.1",
+ "resolved": "https://registry.npmjs.org/d3-flextree/-/d3-flextree-2.1.1.tgz",
+ "integrity": "sha512-P0SK6bRm0PT5ZZON8Lh/aOcFfr4rO53kaYCXCgwBCvsHJcYjtOb8fNrgmpOmCMCgfrT9EczXzD8wqEO8mlkBrA==",
+ "dev": true,
+ "requires": {
+ "d3-hierarchy": "^1.1.5"
+ }
+ },
"d3-force": {
"version": "1.2.1",
"resolved": "https://registry.npmjs.org/d3-force/-/d3-force-1.2.1.tgz",
@@ -7159,28 +7434,28 @@
"dependencies": {
"abbrev": {
"version": "1.1.1",
- "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz",
+ "resolved": false,
"integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==",
"dev": true,
"optional": true
},
"ansi-regex": {
"version": "2.1.1",
- "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz",
+ "resolved": false,
"integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=",
"dev": true,
"optional": true
},
"aproba": {
"version": "1.2.0",
- "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz",
+ "resolved": false,
"integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==",
"dev": true,
"optional": true
},
"are-we-there-yet": {
"version": "1.1.5",
- "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.5.tgz",
+ "resolved": false,
"integrity": "sha512-5hYdAkZlcG8tOLujVDTgCT+uPX0VnpAH28gWsLfzpXYm7wP6mp5Q/gYyR7YQ0cKVJcXJnl3j2kpBan13PtQf6w==",
"dev": true,
"optional": true,
@@ -7191,14 +7466,14 @@
},
"balanced-match": {
"version": "1.0.0",
- "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz",
+ "resolved": false,
"integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=",
"dev": true,
"optional": true
},
"brace-expansion": {
"version": "1.1.11",
- "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
+ "resolved": false,
"integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
"dev": true,
"optional": true,
@@ -7209,42 +7484,42 @@
},
"chownr": {
"version": "1.1.3",
- "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.3.tgz",
+ "resolved": false,
"integrity": "sha512-i70fVHhmV3DtTl6nqvZOnIjbY0Pe4kAUjwHj8z0zAdgBtYrJyYwLKCCuRBQ5ppkyL0AkN7HKRnETdmdp1zqNXw==",
"dev": true,
"optional": true
},
"code-point-at": {
"version": "1.1.0",
- "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz",
+ "resolved": false,
"integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=",
"dev": true,
"optional": true
},
"concat-map": {
"version": "0.0.1",
- "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
+ "resolved": false,
"integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=",
"dev": true,
"optional": true
},
"console-control-strings": {
"version": "1.1.0",
- "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz",
+ "resolved": false,
"integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=",
"dev": true,
"optional": true
},
"core-util-is": {
"version": "1.0.2",
- "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz",
+ "resolved": false,
"integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=",
"dev": true,
"optional": true
},
"debug": {
"version": "3.2.6",
- "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz",
+ "resolved": false,
"integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==",
"dev": true,
"optional": true,
@@ -7254,28 +7529,28 @@
},
"deep-extend": {
"version": "0.6.0",
- "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz",
+ "resolved": false,
"integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==",
"dev": true,
"optional": true
},
"delegates": {
"version": "1.0.0",
- "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz",
+ "resolved": false,
"integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=",
"dev": true,
"optional": true
},
"detect-libc": {
"version": "1.0.3",
- "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-1.0.3.tgz",
+ "resolved": false,
"integrity": "sha1-+hN8S9aY7fVc1c0CrFWfkaTEups=",
"dev": true,
"optional": true
},
"fs-minipass": {
"version": "1.2.7",
- "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-1.2.7.tgz",
+ "resolved": false,
"integrity": "sha512-GWSSJGFy4e9GUeCcbIkED+bgAoFyj7XF1mV8rma3QW4NIqX9Kyx79N/PF61H5udOV3aY1IaMLs6pGbH71nlCTA==",
"dev": true,
"optional": true,
@@ -7285,14 +7560,14 @@
},
"fs.realpath": {
"version": "1.0.0",
- "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz",
+ "resolved": false,
"integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=",
"dev": true,
"optional": true
},
"gauge": {
"version": "2.7.4",
- "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz",
+ "resolved": false,
"integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=",
"dev": true,
"optional": true,
@@ -7309,7 +7584,7 @@
},
"glob": {
"version": "7.1.6",
- "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz",
+ "resolved": false,
"integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==",
"dev": true,
"optional": true,
@@ -7324,14 +7599,14 @@
},
"has-unicode": {
"version": "2.0.1",
- "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz",
+ "resolved": false,
"integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=",
"dev": true,
"optional": true
},
"iconv-lite": {
"version": "0.4.24",
- "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz",
+ "resolved": false,
"integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==",
"dev": true,
"optional": true,
@@ -7341,7 +7616,7 @@
},
"ignore-walk": {
"version": "3.0.3",
- "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-3.0.3.tgz",
+ "resolved": false,
"integrity": "sha512-m7o6xuOaT1aqheYHKf8W6J5pYH85ZI9w077erOzLje3JsB1gkafkAhHHY19dqjulgIZHFm32Cp5uNZgcQqdJKw==",
"dev": true,
"optional": true,
@@ -7351,7 +7626,7 @@
},
"inflight": {
"version": "1.0.6",
- "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz",
+ "resolved": false,
"integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=",
"dev": true,
"optional": true,
@@ -7362,21 +7637,21 @@
},
"inherits": {
"version": "2.0.4",
- "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz",
+ "resolved": false,
"integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==",
"dev": true,
"optional": true
},
"ini": {
"version": "1.3.5",
- "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz",
+ "resolved": false,
"integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==",
"dev": true,
"optional": true
},
"is-fullwidth-code-point": {
"version": "1.0.0",
- "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz",
+ "resolved": false,
"integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=",
"dev": true,
"optional": true,
@@ -7386,14 +7661,14 @@
},
"isarray": {
"version": "1.0.0",
- "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz",
+ "resolved": false,
"integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=",
"dev": true,
"optional": true
},
"minimatch": {
"version": "3.0.4",
- "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz",
+ "resolved": false,
"integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==",
"dev": true,
"optional": true,
@@ -7403,14 +7678,14 @@
},
"minimist": {
"version": "0.0.8",
- "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz",
+ "resolved": false,
"integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=",
"dev": true,
"optional": true
},
"minipass": {
"version": "2.9.0",
- "resolved": "https://registry.npmjs.org/minipass/-/minipass-2.9.0.tgz",
+ "resolved": false,
"integrity": "sha512-wxfUjg9WebH+CUDX/CdbRlh5SmfZiy/hpkxaRI16Y9W56Pa75sWgd/rvFilSgrauD9NyFymP/+JFV3KwzIsJeg==",
"dev": true,
"optional": true,
@@ -7421,7 +7696,7 @@
},
"minizlib": {
"version": "1.3.3",
- "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-1.3.3.tgz",
+ "resolved": false,
"integrity": "sha512-6ZYMOEnmVsdCeTJVE0W9ZD+pVnE8h9Hma/iOwwRDsdQoePpoX56/8B6z3P9VNwppJuBKNRuFDRNRqRWexT9G9Q==",
"dev": true,
"optional": true,
@@ -7431,7 +7706,7 @@
},
"mkdirp": {
"version": "0.5.1",
- "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz",
+ "resolved": false,
"integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=",
"dev": true,
"optional": true,
@@ -7441,14 +7716,14 @@
},
"ms": {
"version": "2.1.2",
- "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz",
+ "resolved": false,
"integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==",
"dev": true,
"optional": true
},
"needle": {
"version": "2.4.0",
- "resolved": "https://registry.npmjs.org/needle/-/needle-2.4.0.tgz",
+ "resolved": false,
"integrity": "sha512-4Hnwzr3mi5L97hMYeNl8wRW/Onhy4nUKR/lVemJ8gJedxxUyBLm9kkrDColJvoSfwi0jCNhD+xCdOtiGDQiRZg==",
"dev": true,
"optional": true,
@@ -7460,7 +7735,7 @@
},
"node-pre-gyp": {
"version": "0.14.0",
- "resolved": "https://registry.npmjs.org/node-pre-gyp/-/node-pre-gyp-0.14.0.tgz",
+ "resolved": false,
"integrity": "sha512-+CvDC7ZttU/sSt9rFjix/P05iS43qHCOOGzcr3Ry99bXG7VX953+vFyEuph/tfqoYu8dttBkE86JSKBO2OzcxA==",
"dev": true,
"optional": true,
@@ -7479,7 +7754,7 @@
},
"nopt": {
"version": "4.0.1",
- "resolved": "https://registry.npmjs.org/nopt/-/nopt-4.0.1.tgz",
+ "resolved": false,
"integrity": "sha1-0NRoWv1UFRk8jHUFYC0NF81kR00=",
"dev": true,
"optional": true,
@@ -7490,7 +7765,7 @@
},
"npm-bundled": {
"version": "1.1.1",
- "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-1.1.1.tgz",
+ "resolved": false,
"integrity": "sha512-gqkfgGePhTpAEgUsGEgcq1rqPXA+tv/aVBlgEzfXwA1yiUJF7xtEt3CtVwOjNYQOVknDk0F20w58Fnm3EtG0fA==",
"dev": true,
"optional": true,
@@ -7500,14 +7775,14 @@
},
"npm-normalize-package-bin": {
"version": "1.0.1",
- "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-1.0.1.tgz",
+ "resolved": false,
"integrity": "sha512-EPfafl6JL5/rU+ot6P3gRSCpPDW5VmIzX959Ob1+ySFUuuYHWHekXpwdUZcKP5C+DS4GEtdJluwBjnsNDl+fSA==",
"dev": true,
"optional": true
},
"npm-packlist": {
"version": "1.4.7",
- "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-1.4.7.tgz",
+ "resolved": false,
"integrity": "sha512-vAj7dIkp5NhieaGZxBJB8fF4R0078rqsmhJcAfXZ6O7JJhjhPK96n5Ry1oZcfLXgfun0GWTZPOxaEyqv8GBykQ==",
"dev": true,
"optional": true,
@@ -7518,7 +7793,7 @@
},
"npmlog": {
"version": "4.1.2",
- "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz",
+ "resolved": false,
"integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==",
"dev": true,
"optional": true,
@@ -7531,21 +7806,21 @@
},
"number-is-nan": {
"version": "1.0.1",
- "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz",
+ "resolved": false,
"integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=",
"dev": true,
"optional": true
},
"object-assign": {
"version": "4.1.1",
- "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz",
+ "resolved": false,
"integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=",
"dev": true,
"optional": true
},
"once": {
"version": "1.4.0",
- "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
+ "resolved": false,
"integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=",
"dev": true,
"optional": true,
@@ -7555,21 +7830,21 @@
},
"os-homedir": {
"version": "1.0.2",
- "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz",
+ "resolved": false,
"integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=",
"dev": true,
"optional": true
},
"os-tmpdir": {
"version": "1.0.2",
- "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz",
+ "resolved": false,
"integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=",
"dev": true,
"optional": true
},
"osenv": {
"version": "0.1.5",
- "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.5.tgz",
+ "resolved": false,
"integrity": "sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==",
"dev": true,
"optional": true,
@@ -7580,21 +7855,21 @@
},
"path-is-absolute": {
"version": "1.0.1",
- "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz",
+ "resolved": false,
"integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=",
"dev": true,
"optional": true
},
"process-nextick-args": {
"version": "2.0.1",
- "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz",
+ "resolved": false,
"integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==",
"dev": true,
"optional": true
},
"rc": {
"version": "1.2.8",
- "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz",
+ "resolved": false,
"integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==",
"dev": true,
"optional": true,
@@ -7607,7 +7882,7 @@
"dependencies": {
"minimist": {
"version": "1.2.0",
- "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz",
+ "resolved": false,
"integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=",
"dev": true,
"optional": true
@@ -7616,7 +7891,7 @@
},
"readable-stream": {
"version": "2.3.6",
- "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz",
+ "resolved": false,
"integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==",
"dev": true,
"optional": true,
@@ -7632,7 +7907,7 @@
},
"rimraf": {
"version": "2.7.1",
- "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz",
+ "resolved": false,
"integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==",
"dev": true,
"optional": true,
@@ -7642,49 +7917,49 @@
},
"safe-buffer": {
"version": "5.1.2",
- "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz",
+ "resolved": false,
"integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==",
"dev": true,
"optional": true
},
"safer-buffer": {
"version": "2.1.2",
- "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
+ "resolved": false,
"integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==",
"dev": true,
"optional": true
},
"sax": {
"version": "1.2.4",
- "resolved": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz",
+ "resolved": false,
"integrity": "sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==",
"dev": true,
"optional": true
},
"semver": {
"version": "5.7.1",
- "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz",
+ "resolved": false,
"integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==",
"dev": true,
"optional": true
},
"set-blocking": {
"version": "2.0.0",
- "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz",
+ "resolved": false,
"integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=",
"dev": true,
"optional": true
},
"signal-exit": {
"version": "3.0.2",
- "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz",
+ "resolved": false,
"integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=",
"dev": true,
"optional": true
},
"string-width": {
"version": "1.0.2",
- "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz",
+ "resolved": false,
"integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=",
"dev": true,
"optional": true,
@@ -7696,7 +7971,7 @@
},
"string_decoder": {
"version": "1.1.1",
- "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz",
+ "resolved": false,
"integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==",
"dev": true,
"optional": true,
@@ -7706,7 +7981,7 @@
},
"strip-ansi": {
"version": "3.0.1",
- "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz",
+ "resolved": false,
"integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=",
"dev": true,
"optional": true,
@@ -7716,14 +7991,14 @@
},
"strip-json-comments": {
"version": "2.0.1",
- "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz",
+ "resolved": false,
"integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=",
"dev": true,
"optional": true
},
"tar": {
"version": "4.4.13",
- "resolved": "https://registry.npmjs.org/tar/-/tar-4.4.13.tgz",
+ "resolved": false,
"integrity": "sha512-w2VwSrBoHa5BsSyH+KxEqeQBAllHhccyMFVHtGtdMpF4W7IRWfZjFiQceJPChOeTsSDVUpER2T8FA93pr0L+QA==",
"dev": true,
"optional": true,
@@ -7739,14 +8014,14 @@
},
"util-deprecate": {
"version": "1.0.2",
- "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz",
+ "resolved": false,
"integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=",
"dev": true,
"optional": true
},
"wide-align": {
"version": "1.1.3",
- "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.3.tgz",
+ "resolved": false,
"integrity": "sha512-QGkOQc8XL6Bt5PwnsExKBPuMKBxnGxWWW3fU55Xt4feHozMUhdUMaBCk290qpm/wG5u/RSKzwdAC4i51YigihA==",
"dev": true,
"optional": true,
@@ -7756,14 +8031,14 @@
},
"wrappy": {
"version": "1.0.2",
- "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
+ "resolved": false,
"integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=",
"dev": true,
"optional": true
},
"yallist": {
"version": "3.1.1",
- "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz",
+ "resolved": false,
"integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==",
"dev": true,
"optional": true
@@ -8888,6 +9163,12 @@
"integrity": "sha1-YTObbyR1/Hcv2cnYP1yFddwVSuE=",
"dev": true
},
+ "is-docker": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-2.0.0.tgz",
+ "integrity": "sha512-pJEdRugimx4fBMra5z2/5iRdZ63OhYV0vr0Dwm5+xtW4D1FvRkB8hamMIhnWfyJeDdyr/aa7BDyNbtG38VxgoQ==",
+ "dev": true
+ },
"is-dotfile": {
"version": "1.0.3",
"resolved": "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz",
@@ -10180,6 +10461,63 @@
"resolved": "https://registry.npmjs.org/marked/-/marked-0.6.3.tgz",
"integrity": "sha512-Fqa7eq+UaxfMriqzYLayfqAE40WN03jf+zHjT18/uXNuzjq3TY0XTbrAoPeqSJrAmPz11VuUA+kBPYOhHt9oOQ=="
},
+ "markmap-lib": {
+ "version": "0.4.2",
+ "resolved": "https://registry.npmjs.org/markmap-lib/-/markmap-lib-0.4.2.tgz",
+ "integrity": "sha512-/1ITvE8HiI+8GLgL//ggH2LNy19Kg3nNcOijK/DcKtH7grJ1TO6k4No/IqCSiM8JjiQbxYDosSHGZKqp6Lyj1A==",
+ "dev": true,
+ "requires": {
+ "@babel/runtime": "^7.9.2",
+ "@types/d3": "^5.7.2",
+ "commander": "^5.0.0",
+ "d3": "^5.15.0",
+ "d3-flextree": "^2.1.1",
+ "open": "^7.0.3",
+ "remarkable": "^2.0.0"
+ },
+ "dependencies": {
+ "@babel/runtime": {
+ "version": "7.9.2",
+ "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.9.2.tgz",
+ "integrity": "sha512-NE2DtOdufG7R5vnfQUTehdTfNycfUANEtCa9PssN9O/xmTzP4E08UI797ixaei6hBEVL9BI/PsdJS5x7mWoB9Q==",
+ "dev": true,
+ "requires": {
+ "regenerator-runtime": "^0.13.4"
+ }
+ },
+ "autolinker": {
+ "version": "3.14.1",
+ "resolved": "https://registry.npmjs.org/autolinker/-/autolinker-3.14.1.tgz",
+ "integrity": "sha512-yvsRHIaY51EYDml6MGlbqyJGfl4n7zezGYf+R7gvM8c5LNpRGc4SISkvgAswSS8SWxk/OrGCylKV9mJyVstz7w==",
+ "dev": true,
+ "requires": {
+ "tslib": "^1.9.3"
+ }
+ },
+ "commander": {
+ "version": "5.0.0",
+ "resolved": "https://registry.npmjs.org/commander/-/commander-5.0.0.tgz",
+ "integrity": "sha512-JrDGPAKjMGSP1G0DUoaceEJ3DZgAfr/q6X7FVk4+U5KxUSKviYGM2k6zWkfyyBHy5rAtzgYJFa1ro2O9PtoxwQ==",
+ "dev": true
+ },
+ "regenerator-runtime": {
+ "version": "0.13.5",
+ "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.5.tgz",
+ "integrity": "sha512-ZS5w8CpKFinUzOwW3c83oPeVXoNsrLsaCoLtJvAClH135j/R77RuymhiSErhm2lKcwSCIpmvIWSbDkIfAqKQlA==",
+ "dev": true
+ },
+ "remarkable": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/remarkable/-/remarkable-2.0.0.tgz",
+ "integrity": "sha512-3gvKFAgL4xmmVRKAMNm6UzDo/rO2gPVkZrWagp6AXEA4JvCcMcRx9aapYbb7AJAmLLvi/u06+EhzqoS7ha9qOg==",
+ "dev": true,
+ "requires": {
+ "argparse": "^1.0.10",
+ "autolinker": "^3.11.0"
+ }
+ }
+ }
+ },
"math-interval-parser": {
"version": "1.1.0",
"resolved": "https://registry.npmjs.org/math-interval-parser/-/math-interval-parser-1.1.0.tgz",
@@ -11490,6 +11828,24 @@
}
}
},
+ "open": {
+ "version": "7.0.3",
+ "resolved": "https://registry.npmjs.org/open/-/open-7.0.3.tgz",
+ "integrity": "sha512-sP2ru2v0P290WFfv49Ap8MF6PkzGNnGlAwHweB4WR4mr5d2d0woiCluUeJ218w7/+PmoBy9JmYgD5A4mLcWOFA==",
+ "dev": true,
+ "requires": {
+ "is-docker": "^2.0.0",
+ "is-wsl": "^2.1.1"
+ },
+ "dependencies": {
+ "is-wsl": {
+ "version": "2.1.1",
+ "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-2.1.1.tgz",
+ "integrity": "sha512-umZHcSrwlDHo2TGMXv0DZ8dIUGunZ2Iv68YZnrmCiBPkZ4aaOhtv7pXJKeki9k3qJ3RJr0cDyitcl5wEH3AYog==",
+ "dev": true
+ }
+ }
+ },
"openid": {
"version": "2.0.6",
"resolved": "https://registry.npmjs.org/openid/-/openid-2.0.6.tgz",
@@ -11668,6 +12024,12 @@
"integrity": "sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw==",
"dev": true
},
+ "papaparse": {
+ "version": "5.2.0",
+ "resolved": "https://registry.npmjs.org/papaparse/-/papaparse-5.2.0.tgz",
+ "integrity": "sha512-ylq1wgUSnagU+MKQtNeVqrPhZuMYBvOSL00DHycFTCxownF95gpLAk1HiHdUW77N8yxRq1qHXLdlIPyBSG9NSA==",
+ "dev": true
+ },
"parallel-transform": {
"version": "1.2.0",
"resolved": "https://registry.npmjs.org/parallel-transform/-/parallel-transform-1.2.0.tgz",
diff --git a/package.json b/package.json
index 2fc667ec76..395390497b 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "codimd",
- "version": "2.1.0",
+ "version": "2.2.0",
"description": "Realtime collaborative markdown notes on all platforms.",
"keywords": [
"Collaborative",
@@ -161,6 +161,7 @@
"markdown-it-sub": "~1.0.0",
"markdown-it-sup": "~1.0.0",
"markdownlint": "^0.17.0",
+ "markmap-lib": "^0.4.2",
"mathjax": "~2.7.5",
"mermaid": "~8.4.8",
"mini-css-extract-plugin": "~0.4.1",
@@ -168,6 +169,7 @@
"mock-require": "~3.0.3",
"nyc": "~14.0.0",
"optimize-css-assets-webpack-plugin": "~5.0.0",
+ "papaparse": "^5.2.0",
"pdfobject": "~2.1.1",
"plantuml-encoder": "^1.2.5",
"power-assert": "~1.6.1",
diff --git a/public/css/cover.css b/public/css/cover.css
index 4693c9c3a1..ca9fa866dd 100644
--- a/public/css/cover.css
+++ b/public/css/cover.css
@@ -397,7 +397,23 @@ select {
color: #fff;
}
-a.btn.btn-social > i.oauth-icon {
+/* add btn-login-method replaced of btn-social, to avoid ad block delete the login button */
+.btn-login-method {
+ padding-left: 61px;
+ position: relative;
+ text-align: left;
+ white-space: nowrap;
+ overflow: hidden;
+ text-overflow: ellipsis;
+}
+.btn-login-method.btn-lg :first-child {
+ line-height:45px;
+ width:45px;
+ font-size:1.8em;
+}
+.btn-login-method>:first-child {position:absolute;left:0;top:0;bottom:0;width:32px;line-height:34px;font-size:1.6em;text-align:center;border-right:1px solid rgba(0,0,0,0.2)}
+
+a.btn.btn-login-method > i.oauth-icon {
display: inline-flex;
height: 45px;
width: 45px;
@@ -405,7 +421,7 @@ a.btn.btn-social > i.oauth-icon {
padding: 6px;
}
-a.btn.btn-social > i.oauth-icon > img {
+a.btn.btn-login-method > i.oauth-icon > img {
width: 100%;
height: 100%;
line-height: inherit;
diff --git a/public/css/extra.css b/public/css/extra.css
index 2b23ad2413..e795bc1b01 100644
--- a/public/css/extra.css
+++ b/public/css/extra.css
@@ -84,6 +84,16 @@
height: 250px;
}
+/* markmap */
+.markmap-container {
+ height: 300px;
+}
+
+.markmap-container > svg {
+ width: 100%;
+ height: 100%;
+}
+
.MJX_Assistive_MathML {
display: none;
}
diff --git a/public/css/font.css b/public/css/font.css
index 4aa2921070..de3ef6f98f 100644
--- a/public/css/font.css
+++ b/public/css/font.css
@@ -3,7 +3,7 @@
font-family: 'Source Code Pro';
font-style: normal;
font-weight: 300;
- src: local('Source Code Pro Light'), local('SourceCodePro-Light'), url('/fonts/SourceCodePro-Light.woff') format('woff');
+ src: local('Source Code Pro Light'), local('SourceCodePro-Light'), url('../fonts/SourceCodePro-Light.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -11,7 +11,7 @@
font-family: 'Source Code Pro';
font-style: normal;
font-weight: 300;
- src: local('Source Code Pro Light'), local('SourceCodePro-Light'), url('/fonts/SourceCodePro-Light.woff') format('woff');
+ src: local('Source Code Pro Light'), local('SourceCodePro-Light'), url('../fonts/SourceCodePro-Light.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* latin-ext */
@@ -19,7 +19,7 @@
font-family: 'Source Code Pro';
font-style: normal;
font-weight: 400;
- src: local('Source Code Pro'), local('SourceCodePro-Regular'), url('/fonts/SourceCodePro-Regular.woff') format('woff');
+ src: local('Source Code Pro'), local('SourceCodePro-Regular'), url('../fonts/SourceCodePro-Regular.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -27,7 +27,7 @@
font-family: 'Source Code Pro';
font-style: normal;
font-weight: 400;
- src: local('Source Code Pro'), local('SourceCodePro-Regular'), url('/fonts/SourceCodePro-Regular.woff') format('woff');
+ src: local('Source Code Pro'), local('SourceCodePro-Regular'), url('../fonts/SourceCodePro-Regular.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* latin-ext */
@@ -35,7 +35,7 @@
font-family: 'Source Code Pro';
font-style: normal;
font-weight: 500;
- src: local('Source Code Pro Medium'), local('SourceCodePro-Medium'), url('/fonts/SourceCodePro-Medium.woff') format('woff');
+ src: local('Source Code Pro Medium'), local('SourceCodePro-Medium'), url('../fonts/SourceCodePro-Medium.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -43,7 +43,7 @@
font-family: 'Source Code Pro';
font-style: normal;
font-weight: 500;
- src: local('Source Code Pro Medium'), local('SourceCodePro-Medium'), url('/fonts/SourceCodePro-Medium.woff') format('woff');
+ src: local('Source Code Pro Medium'), local('SourceCodePro-Medium'), url('../fonts/SourceCodePro-Medium.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* vietnamese */
@@ -51,7 +51,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 300;
- src: local('Source Sans Pro Light'), local('SourceSansPro-Light'), url('/fonts/SourceCodePro-Medium.woff') format('woff');
+ src: local('Source Sans Pro Light'), local('SourceSansPro-Light'), url('../fonts/SourceCodePro-Medium.woff') format('woff');
unicode-range: U+0102-0103, U+1EA0-1EF9, U+20AB;
}
/* latin-ext */
@@ -59,7 +59,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 300;
- src: local('Source Sans Pro Light'), local('SourceSansPro-Light'), url('/fonts/SourceSansPro-Light.woff') format('woff');
+ src: local('Source Sans Pro Light'), local('SourceSansPro-Light'), url('../fonts/SourceSansPro-Light.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -67,7 +67,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 300;
- src: local('Source Sans Pro Light'), local('SourceSansPro-Light'), url('/fonts/SourceSansPro-Light.woff') format('woff');
+ src: local('Source Sans Pro Light'), local('SourceSansPro-Light'), url('../fonts/SourceSansPro-Light.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* vietnamese */
@@ -75,7 +75,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 400;
- src: local('Source Sans Pro'), local('SourceSansPro-Regular'), url('/fonts/SourceSansPro-Regular.woff') format('woff');
+ src: local('Source Sans Pro'), local('SourceSansPro-Regular'), url('../fonts/SourceSansPro-Regular.woff') format('woff');
unicode-range: U+0102-0103, U+1EA0-1EF9, U+20AB;
}
/* latin-ext */
@@ -83,7 +83,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 400;
- src: local('Source Sans Pro'), local('SourceSansPro-Regular'), url('/fonts/SourceSansPro-Regular.woff') format('woff');
+ src: local('Source Sans Pro'), local('SourceSansPro-Regular'), url('../fonts/SourceSansPro-Regular.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -91,7 +91,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 400;
- src: local('Source Sans Pro'), local('SourceSansPro-Regular'), url('/fonts/SourceSansPro-Regular.woff') format('woff');
+ src: local('Source Sans Pro'), local('SourceSansPro-Regular'), url('../fonts/SourceSansPro-Regular.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* vietnamese */
@@ -99,7 +99,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 600;
- src: local('Source Sans Pro Semibold'), local('SourceSansPro-Semibold'), url('/fonts/SourceSansPro-Semibold.woff') format('woff');
+ src: local('Source Sans Pro Semibold'), local('SourceSansPro-Semibold'), url('../fonts/SourceSansPro-Semibold.woff') format('woff');
unicode-range: U+0102-0103, U+1EA0-1EF9, U+20AB;
}
/* latin-ext */
@@ -107,7 +107,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 600;
- src: local('Source Sans Pro Semibold'), local('SourceSansPro-Semibold'), url('/fonts/SourceSansPro-Semibold.woff') format('woff');
+ src: local('Source Sans Pro Semibold'), local('SourceSansPro-Semibold'), url('../fonts/SourceSansPro-Semibold.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -115,7 +115,7 @@
font-family: 'Source Sans Pro';
font-style: normal;
font-weight: 600;
- src: local('Source Sans Pro Semibold'), local('SourceSansPro-Semibold'), url('/fonts/SourceSansPro-Semibold.woff') format('woff');
+ src: local('Source Sans Pro Semibold'), local('SourceSansPro-Semibold'), url('../fonts/SourceSansPro-Semibold.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* vietnamese */
@@ -123,7 +123,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 300;
- src: local('Source Sans Pro Light Italic'), local('SourceSansPro-LightIt'), url('/fonts/SourceSansPro-LightItalic.woff') format('woff');
+ src: local('Source Sans Pro Light Italic'), local('SourceSansPro-LightIt'), url('../fonts/SourceSansPro-LightItalic.woff') format('woff');
unicode-range: U+0102-0103, U+1EA0-1EF9, U+20AB;
}
/* latin-ext */
@@ -131,7 +131,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 300;
- src: local('Source Sans Pro Light Italic'), local('SourceSansPro-LightIt'), url('/fonts/SourceSansPro-LightItalic.woff') format('woff');
+ src: local('Source Sans Pro Light Italic'), local('SourceSansPro-LightIt'), url('../fonts/SourceSansPro-LightItalic.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -139,7 +139,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 300;
- src: local('Source Sans Pro Light Italic'), local('SourceSansPro-LightIt'), url('/fonts/SourceSansPro-LightItalic.woff') format('woff');
+ src: local('Source Sans Pro Light Italic'), local('SourceSansPro-LightIt'), url('../fonts/SourceSansPro-LightItalic.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* vietnamese */
@@ -147,7 +147,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 400;
- src: local('Source Sans Pro Italic'), local('SourceSansPro-It'), url('/fonts/SourceSansPro-Italic.woff') format('woff');
+ src: local('Source Sans Pro Italic'), local('SourceSansPro-It'), url('../fonts/SourceSansPro-Italic.woff') format('woff');
unicode-range: U+0102-0103, U+1EA0-1EF9, U+20AB;
}
/* latin-ext */
@@ -155,7 +155,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 400;
- src: local('Source Sans Pro Italic'), local('SourceSansPro-It'), url('/fonts/SourceSansPro-Italic.woff') format('woff');
+ src: local('Source Sans Pro Italic'), local('SourceSansPro-It'), url('../fonts/SourceSansPro-Italic.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -163,7 +163,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 400;
- src: local('Source Sans Pro Italic'), local('SourceSansPro-It'), url('/fonts/SourceSansPro-Italic.woff') format('woff');
+ src: local('Source Sans Pro Italic'), local('SourceSansPro-It'), url('../fonts/SourceSansPro-Italic.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* vietnamese */
@@ -171,7 +171,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 600;
- src: local('Source Sans Pro Semibold Italic'), local('SourceSansPro-SemiboldIt'), url('/fonts/SourceSansPro-SemiboldItalic.woff') format('woff');
+ src: local('Source Sans Pro Semibold Italic'), local('SourceSansPro-SemiboldIt'), url('../fonts/SourceSansPro-SemiboldItalic.woff') format('woff');
unicode-range: U+0102-0103, U+1EA0-1EF9, U+20AB;
}
/* latin-ext */
@@ -179,7 +179,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 600;
- src: local('Source Sans Pro Semibold Italic'), local('SourceSansPro-SemiboldIt'), url('/fonts/SourceSansPro-SemiboldItalic.woff') format('woff');
+ src: local('Source Sans Pro Semibold Italic'), local('SourceSansPro-SemiboldIt'), url('../fonts/SourceSansPro-SemiboldItalic.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -187,7 +187,7 @@
font-family: 'Source Sans Pro';
font-style: italic;
font-weight: 600;
- src: local('Source Sans Pro Semibold Italic'), local('SourceSansPro-SemiboldIt'), url('/fonts/SourceSansPro-SemiboldItalic.woff') format('woff');
+ src: local('Source Sans Pro Semibold Italic'), local('SourceSansPro-SemiboldIt'), url('../fonts/SourceSansPro-SemiboldItalic.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* latin-ext */
@@ -195,7 +195,7 @@
font-family: 'Source Serif Pro';
font-style: normal;
font-weight: 400;
- src: local('Source Serif Pro'), local('SourceSerifPro-Regular'), url('/fonts/SourceSerifPro-Regular.woff') format('woff');
+ src: local('Source Serif Pro'), local('SourceSerifPro-Regular'), url('../fonts/SourceSerifPro-Regular.woff') format('woff');
unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@@ -203,6 +203,6 @@
font-family: 'Source Serif Pro';
font-style: normal;
font-weight: 400;
- src: local('Source Serif Pro'), local('SourceSerifPro-Regular'), url('/fonts/SourceSerifPro-Regular.woff') format('woff');
+ src: local('Source Serif Pro'), local('SourceSerifPro-Regular'), url('../fonts/SourceSerifPro-Regular.woff') format('woff');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
diff --git a/public/css/slide.css b/public/css/slide.css
index 72275c6a9f..f30726192a 100644
--- a/public/css/slide.css
+++ b/public/css/slide.css
@@ -344,3 +344,7 @@ html, body {
.print-pdf .footer {
display: none;
}
+
+.markmap-container {
+ background: #f7f7f7;
+}
diff --git a/public/docs/features.md b/public/docs/features.md
index c3f5fac931..c4f081b03d 100644
--- a/public/docs/features.md
+++ b/public/docs/features.md
@@ -208,6 +208,30 @@ When you’re a carpenter making a beautiful chest of drawers, you’re not goin
> > Even support the nest blockquotes!
> > [name=ChengHan Wu] [time=Sun, Jun 28, 2015 10:00 PM] [color=red]
+### Render CSV as table
+
+You can use write csv in the codeblock:
+
+~~~md
+```csvpreview {header="true"}
+firstName,lastName,email,phoneNumber
+John,Doe,john@doe.com,0123456789
+Jane,Doe,jane@doe.com,9876543210
+James,Bond,james.bond@mi6.co.uk,0612345678
+```
+~~~
+
+which rendered to:
+
+```csvpreview {header="true"}
+firstName,lastName,email,phoneNumber
+John,Doe,john@doe.com,0123456789
+Jane,Doe,jane@doe.com,9876543210
+James,Bond,james.bond@mi6.co.uk,0612345678
+```
+
+We use [Papa Parse](https://www.papaparse.com/) for parsing csv. The parsing option is given in braces: `{}`, and multiple options are seperated by a space. e.g. `{header="true" delimiter="."}`. Please read [their documentation](https://www.papaparse.com/docs#config) as reference.
+
## Externals
### YouTube
@@ -345,6 +369,40 @@ stop
}
```
+### Fretboad
+
+```fretboard {title="horizontal, 5 frets", type="h6 noNut"}
+-oO-*-
+--o-o-
+-o-oo-
+-o-oO-
+-oo-o-
+-*O-o-
+```
+
+### Mindmap
+
+```markmap
+# markmap-lib
+
+## Links
+
+-
${escapeHTML(f)} | `).join('')} +
---|
${escapeHTML(d[f])} | `).join('')} +
${escapeHTML(f)} | `).join('')} +
- <%- __('Powered by %s', 'CodiMD') %> | <%= __('Releases') %>| <%= __('Source Code') %><% if(privacyStatement) { %> | <%= __('Privacy') %><% } %><% if(termsOfUse) { %> | <%= __('Terms of Use') %><% } %> + <%- __('Powered by %s', 'CodiMD') %> | <%= __('Releases') %> | <%= __('Source Code') %><% if(privacyStatement) { %> | <%= __('Privacy') %><% } %><% if(termsOfUse) { %> | <%= __('Terms of Use') %><% } %>