1# prosemirror Plugin for DokuWiki 2[![Scrutinizer Code Quality](https://scrutinizer-ci.com/g/cosmocode/dokuwiki-plugin-prosemirror/badges/quality-score.png?b=master)](https://scrutinizer-ci.com/g/cosmocode/dokuwiki-plugin-prosemirror/?branch=master) 3 4A WYSIWYG editor for DokuWiki 5 6All documentation for this plugin can be found at 7https://www.dokuwiki.org/plugin:prosemirror 8 9If you install this plugin manually, make sure it is installed in 10``lib/plugins/prosemirror/`` - if the folder is called different it 11will not work! 12 13Please refer to http://www.dokuwiki.org/plugins for additional info 14on how to install plugins in DokuWiki. 15 16## Development Setup 17 18Use yarn to install the dependecies 19 20 yarn 21 22Create a develoment bundle: 23 24 yarn dev 25 26Automatically recreate the bundle during development: 27 28 yarn watch 29 30Build a release 31 32 yarn build 33 34We really recommend yarn, but npm should work, too. 35 36## Architecture 37 38### Dataflow 39 40#### Begin Edit-Session: DokuWiki -> Prosemirror 41- `action/editor.php`: `HTML_EDITFORM_OUTPUT` get Instructions and render them to json 42 - see `renderer.php` 43 - `renderer.php` uses the classes `NodeStack` `Node` and `Mark` in `schema` to do its job 44 - this should possibly renamed 45 - to keep information about a Node in as few places as possible, 46 some rendering instructions have been moved to the respective `parser/` classes 47- Prosemirror parses that json in `script/main.js` according to the schema defined in 48`script/schema.js` and creates its `doc`-Node from it. 49 50#### Rendering: Prosemirror -> DokuWiki -> Prosemirror 51- Some Nodes (e.g. images, links) need to be resolved by DokuWiki in order to be rendered properly. 52- So ProseMirror makes ajax requests 53 - triggered by `LinkForm.resolveSubmittedLinkData` in `script/LinkForm.js` 54- the request is handled by `action/ajax.php` which resolves the link/images and returns 55the resolved html to be rendered into Prosemirror 56 57 58#### Saving/Preview: Prosemirror -> DokuWiki 59- Prosemirror synchronizes all changes with the underlying json in the `<input>` field 60- When the Editform is submitted that data has to be parsed by DokuWiki into DokuWiki-Syntax. 61- This starts in `action/parser.php` during the event `ACTION_ACT_PREPROCESS` 62 - The main challenge is that Prosemirror operates on a flat array, whereas DokuWiki-Syntax is usually a tree 63 - This means that the Syntax `**bold __underlined and bold__**` is represented in Prosemirror's data as 64 `[{text: "bold ", marks: [bold]}, {text: "underlined and bold", marks: [bold, underlined]}]` 65 - The creation of that syntax tree is started in `parser/SyntaxTreeBuilder.php` 66 - Handling marks is complex and subtle: 67 - To know in which order we have to open/close marks we need to know which start 68 earlier or end later 69 - for this purpose, `InlineNodeInterface::getStartingNodeMarkScore($markType)` 70 and `Mark::tailLength` play together 71 - for `getStartingNodeMarkScore()` to work, it needs the inline nodes inside a block node to be 72 chained together, so we can ask the previous node whether it has a given node or not 73 - If the marks on a node have the same start/end than they need a stable order in which they appear. 74 That is defined in `Mark::markOrder` 75 76### Our Prosemirror JS setup 77Currently all our prosemirror scripts are in `script/`. 78This definietly needs some better organisation. 79I can see the following possible groups: 80- NodeViews and Forms 81 - if a Node cannot be simply rendered and edited by ProseMirror, it needs a NodeView 82 - Examples are links, images, footnotes(NodeView not yet implemented) 83 - possibly also `<code>` and `<file>`? 84- Menu-Related classes and menu items 85- keyboard commands 86- possibly `commands` in general wich then can be used by menu-items and keyboard-events? 87- the schema 88 89These files are compiled with webpack and transpiled with Babel into `lib/bundle.js`, 90which is the file actually included by DokuWiki. 91 92## Testing 93The central test-data is the collection of DokuWiki-Syntax and corresponding Prosemirror JSON 94in `_test/json/`. This data is used for three sets of tests: 951. Testing the rendering of DokuWiki-Syntax to Prosemirror JSON in `_test/renderer.test.php` 961. Testing the parsing of Prosemirror JSON back to the original DokuWiki-Syntax in `_test/jsonParser.test.php` 971. Testing the validity of the Prosemirror JSON against the schema (`script/schema.js`) in `_jstest/test.js` 98 99The rendering and parsing tests are run as usual DokuWiki tests. 100The javascript tests are run with `yarn test` 101 102The scripts in `script/` are also checked when building with eslint. 103Eslint can also be run on its own with `yarn eslint`. 104 105## Copyright 106Copyright (C) CosmoCode GmbH <dokuwiki@cosmocode.de> 107 Andreas Gohr 108 Michael Grosse 109 Anna Dabrowska 110 111This program is free software; you can redistribute it and/or modify 112it under the terms of the GNU General Public License as published by 113the Free Software Foundation; version 2 of the License 114 115This program is distributed in the hope that it will be useful, 116but WITHOUT ANY WARRANTY; without even the implied warranty of 117MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 118GNU General Public License for more details. 119 120See the COPYING file in your DokuWiki folder for details 121