diff --git a/TODO b/TODO index 2301f0577..b200b75b3 100644 --- a/TODO +++ b/TODO @@ -5,9 +5,15 @@ - Have updated column resizing to set cell widths - Now need to handle table overall size on change, then heights. +- Details/Summary + - Need view to control summary editability, make readonly but editable via popover. + - Need some default styles to visualise details boundary. + - Markdown parser needs to be updated to handle separate open/close tags for blocks. + ### In-Progress - Tables +- Details/Summary ### Features @@ -17,7 +23,6 @@ - Fullscreen - Paste Image Uploading - Drag + Drop Image Uploading -- Details/Summary - Checkbox/TODO list items - Code blocks - Indents diff --git a/resources/js/editor/markdown-serializer.js b/resources/js/editor/markdown-serializer.js index c0e3fcb0f..57d8484dc 100644 --- a/resources/js/editor/markdown-serializer.js +++ b/resources/js/editor/markdown-serializer.js @@ -17,6 +17,14 @@ nodes.iframe = function (state, node) { writeNodeAsHtml(state, node); }; +nodes.details = function (state, node) { + wrapNodeWithHtml(state, node, '
', '
'); +}; + +nodes.details_summary = function(state, node) { + writeNodeAsHtml(state, node); +}; + function isPlainURL(link, parent, index, side) { if (link.attrs.title || !/^\w+:/.test(link.attrs.href)) { return false @@ -85,7 +93,7 @@ marks.background_color = { /** * @param {MarkdownSerializerState} state - * @param node + * @param {PmNode} node */ function writeNodeAsHtml(state, node) { const html = docToHtml({content: [node]}); @@ -95,6 +103,22 @@ function writeNodeAsHtml(state, node) { state.closeBlock(); } +/** + * @param {MarkdownSerializerState} state + * @param {PmNode} node + * @param {String} openTag + * @param {String} closeTag + */ +function wrapNodeWithHtml(state, node, openTag, closeTag) { + state.write(openTag); + state.ensureNewLine(); + state.renderContent(node); + state.write(closeTag); + state.closeBlock(); + state.ensureNewLine(); + state.write('\n'); +} + // Update serializers to just write out as HTML if we have an attribute // or element that cannot be represented in commonmark without losing // formatting or content. diff --git a/resources/js/editor/menu/icons.js b/resources/js/editor/menu/icons.js index 3445ac10d..72a53a5f3 100644 --- a/resources/js/editor/menu/icons.js +++ b/resources/js/editor/menu/icons.js @@ -107,6 +107,10 @@ export const icons = { iframe: { width: 24, height: 24, path: "m 22.71,18.43 c 0.03,-0.29 0.04,-0.58 0.01,-0.86 l 1.07,-0.85 c 0.1,-0.08 0.12,-0.21 0.06,-0.32 L 22.82,14.61 C 22.76,14.5 22.63,14.46 22.51,14.5 L 21.23,15 C 21,14.83 20.75,14.69 20.48,14.58 l -0.2,-1.36 C 20.26,13.09 20.16,13 20.03,13 h -2.07 c -0.12,0 -0.23,0.09 -0.25,0.21 l -0.2,1.36 c -0.26,0.11 -0.51,0.26 -0.74,0.42 l -1.28,-0.5 c -0.12,-0.05 -0.25,0 -0.31,0.11 l -1.03,1.79 c -0.06,0.11 -0.04,0.24 0.06,0.32 l 1.07,0.86 c -0.03,0.29 -0.04,0.58 -0.01,0.86 l -1.07,0.85 c -0.1,0.08 -0.12,0.21 -0.06,0.32 l 1.03,1.79 c 0.06,0.11 0.19,0.15 0.31,0.11 L 16.75,21 c 0.23,0.17 0.48,0.31 0.75,0.42 l 0.2,1.36 c 0.02,0.12 0.12,0.21 0.25,0.21 h 2.07 c 0.12,0 0.23,-0.09 0.25,-0.21 l 0.2,-1.36 c 0.26,-0.11 0.51,-0.26 0.74,-0.42 l 1.28,0.5 c 0.12,0.05 0.25,0 0.31,-0.11 l 1.03,-1.79 c 0.06,-0.11 0.04,-0.24 -0.06,-0.32 z M 19,19.5 c -0.83,0 -1.5,-0.67 -1.5,-1.5 0,-0.83 0.67,-1.5 1.5,-1.5 0.83,0 1.5,0.67 1.5,1.5 0,0.83 -0.67,1.5 -1.5,1.5 z M 15,12 9,8 v 8 z M 3,6 h 18 v 5 h 2 V 6 C 23,4.9 22.1,4 21,4 H 3 C 1.9,4 1,4.9 1,6 v 12 c 0,1.1 0.9,2 2,2 h 9 V 18 H 3 Z", + }, + details: { + width: 24, height: 24, + path: "m 7,10 5,5 5,-5 z M 19,2.5 H 5 c -1.11,0 -2,0.9 -2,2 v 14 c 0,1.1 0.89,2 2,2 h 14 c 1.1,0 2,-0.9 2,-2 v -14 c 0,-1.1 -0.89,-2 -2,-2 z m 0,16 H 5 v -12 h 14 z", } }; diff --git a/resources/js/editor/menu/index.js b/resources/js/editor/menu/index.js index ecf574642..d88330ab5 100644 --- a/resources/js/editor/menu/index.js +++ b/resources/js/editor/menu/index.js @@ -160,7 +160,10 @@ const inserts = [ new TableCreatorGrid() ], {icon: icons.table}), itemIframeButton(), - itemHtmlSourceButton(), + wrapItem(schema.nodes.details, { + title: "Dropdown Block", + icon: icons.details, + }) ]; const utilities = [ @@ -170,6 +173,7 @@ const utilities = [ run: removeMarks(), enable: state => true, }), + itemHtmlSourceButton(), ]; const menu = menuBar({ diff --git a/resources/js/editor/schema-nodes.js b/resources/js/editor/schema-nodes.js index 5ebf76a7f..f930d1100 100644 --- a/resources/js/editor/schema-nodes.js +++ b/resources/js/editor/schema-nodes.js @@ -1,5 +1,5 @@ import {orderedList, bulletList, listItem} from "prosemirror-schema-list"; -import {tableNodes} from "prosemirror-tables"; +import {Fragment} from "prosemirror-model"; /** * @param {HTMLElement} node @@ -328,6 +328,35 @@ const table_header = { toDOM(node) { return ["th", setCellAttrs(node), 0] } }; + +const details = { + content: "details_summary block*", + isolating: true, + group: "block", + parseDOM: [{ + tag: "details", + getAttrs(domNode) { + return {} + }, + }], + toDOM(node) { + return ["details", 0]; + } +}; + +const details_summary = { + content: "inline*", + group: "block", + parseDOM: [{ + tag: "details summary", + }], + toDOM(node) { + return ["summary", 0]; + } +}; + + + const nodes = { doc, paragraph, @@ -347,6 +376,8 @@ const nodes = { table_row, table_cell, table_header, + details, + details_summary, }; export default nodes; \ No newline at end of file diff --git a/resources/views/editor-test.blade.php b/resources/views/editor-test.blade.php index ee9537d25..94819121b 100644 --- a/resources/views/editor-test.blade.php +++ b/resources/views/editor-test.blade.php @@ -19,6 +19,12 @@ Some Linked Content Lorem ipsum dolor sit amet.

+
+ Dropdown here +

Inner header

+

Paragraph

+
+