Passed
Push — master ( b9c47f...a5c980 )
by Andreas
10:28
created

buildOldToggleButton()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 10
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
eloc 6
c 0
b 0
f 0
nc 2
nop 0
dl 0
loc 10
rs 10
1
<?php
2
/**
3
 * DokuWiki Plugin prosemirror (Action Component)
4
 *
5
 * @license GPL 2 http://www.gnu.org/licenses/gpl-2.0.html
6
 * @author  Andreas Gohr <[email protected]>
7
 */
8
9
// must be run within Dokuwiki
10
use dokuwiki\Form\ButtonElement;
11
12
if (!defined('DOKU_INC')) {
13
    die();
14
}
15
16
class action_plugin_prosemirror_editor extends DokuWiki_Action_Plugin
17
{
18
    /**
19
     * Registers a callback function for a given event
20
     *
21
     * @param Doku_Event_Handler $controller DokuWiki's event controller object
22
     *
23
     * @return void
24
     */
25
    public function register(Doku_Event_Handler $controller)
26
    {
27
        $controller->register_hook('ACTION_HEADERS_SEND', 'BEFORE', $this, 'forceWYSIWYG');
28
        $controller->register_hook('ACTION_HEADERS_SEND', 'AFTER', $this, 'addJSINFO');
29
        $controller->register_hook('HTML_EDITFORM_OUTPUT', 'BEFORE', $this, 'addDataAndToggleButton');
30
        $controller->register_hook('FORM_EDIT_OUTPUT', 'BEFORE', $this, 'addDataAndToggleButton');
31
        $controller->register_hook('TPL_ACT_RENDER', 'AFTER', $this, 'addAddtionalForms');
32
    }
33
34
    /**
35
     * If the current user is forced to use the WYSIWYG editor, set the cookie accordingly
36
     *
37
     * Triggered by event: ACTION_HEADERS_SEND
38
     *
39
     * @param Doku_Event $event
40
     * @param            $param
41
     */
42
    public function forceWYSIWYG(Doku_Event $event, $param)
43
    {
44
        if ($this->isForceWYSIWYG()) {
45
            set_doku_pref('plugin_prosemirror_useWYSIWYG', true);
46
        }
47
    }
48
49
    /**
50
     * Add the editor toggle button and, if using the WYSIWYG editor, the instructions rendered to json
51
     *
52
     * Triggered by event: HTML_EDITFORM_OUTPUT
53
     *
54
     * @param Doku_Event $event  event object
55
     * @param mixed      $param  [the parameters passed as fifth argument to register_hook() when this
56
     *                           handler was registered]
57
     *
58
     * @return void
59
     */
60
    public function addDataAndToggleButton(Doku_Event $event, $param)
61
    {
62
        if (!$this->allowWYSIWYG()) {
63
            return;
64
        }
65
66
        $useWYSIWYG = get_doku_pref('plugin_prosemirror_useWYSIWYG', false);
67
68
        $prosemirrorJSON = '';
69
        if ($useWYSIWYG) {
70
            global $TEXT;
71
            $instructions = p_get_instructions($TEXT);
72
            try {
73
                $prosemirrorJSON = p_render('prosemirror', $instructions, $info);
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $info seems to be never defined.
Loading history...
74
            } catch (Throwable $e) {
75
                $errorMsg = 'Rendering the page\'s syntax for the WYSIWYG editor failed: ' . $e->getMessage();
76
77
                /** @var \helper_plugin_prosemirror $helper */
78
                $helper = plugin_load('helper', 'prosemirror');
79
                if ($helper->tryToLogErrorToSentry($e, ['text' => $TEXT])) {
80
                    $errorMsg .= ' -- The error has been logged to Sentry.';
81
                }
82
83
                msg($errorMsg, -1);
84
                return;
85
            }
86
        }
87
88
        /** @var Doku_Form|\dokuwiki\Form\Form $form */
89
        $form = $event->data;
90
91
        if(is_a($form, \dokuwiki\Form\Form::class)) {
92
            $form->addElement($this->buildToggleButton());
93
            $form->setHiddenField('prosemirror_json',$prosemirrorJSON);
94
            $form->addHTML('<div class="prosemirror_wrapper" id="prosemirror__editor"></div>', 1);
95
        } else {
96
            // todo remove when old stable is no longer supported
97
            $form->addElement($this->buildOldToggleButton());
0 ignored issues
show
Deprecated Code introduced by
The function action_plugin_prosemirro...:buildOldToggleButton() has been deprecated: use buildToggleButton instead ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

97
            $form->addElement(/** @scrutinizer ignore-deprecated */ $this->buildOldToggleButton());

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
98
            $form->addHidden('prosemirror_json',$prosemirrorJSON);
99
            $form->insertElement(1, '<div class="prosemirror_wrapper" id="prosemirror__editor"></div>');
100
        }
101
    }
102
103
    /**
104
     * Create the button to toggle the WYSIWYG editor
105
     *
106
     * Creates it as hidden if forcing WYSIWYG
107
     *
108
     * @deprecated use buildToggleButton instead
109
     * @return array the pseudo-tag expected by \Doku_Form::addElement
110
     */
111
    protected function buildOldToggleButton()
112
    {
113
        dbg_deprecated('buildToggleButton');
114
        $attr = [
115
            'class' => 'button plugin_prosemirror_useWYSIWYG'
116
        ];
117
        if ($this->isForceWYSIWYG()) {
118
            $attr['style'] = 'display: none;';
119
        }
120
        return form_makeButton('button', '', $this->getLang('switch_editors'), $attr);
121
    }
122
123
    /**
124
     * Create the button to toggle the WYSIWYG editor
125
     *
126
     * Creates it as hidden if forcing WYSIWYG
127
     *
128
     * @return ButtonElement
129
     */
130
    protected function buildToggleButton()
131
    {
132
        $button = new ButtonElement('prosemirror', $this->getLang('switch_editors'));
133
        $button->addClass('button plugin_prosemirror_useWYSIWYG');
134
        if ($this->isForceWYSIWYG()) {
135
            $button->attr('style', 'display: none;');
136
        }
137
        return $button;
138
    }
139
140
    /**
141
     * Determine if the current user is forced to use the WYSIWYG editor
142
     *
143
     * @return bool
144
     */
145
    protected function isForceWYSIWYG()
146
    {
147
        return $this->getConf('forceWYSIWYG') && !auth_ismanager();
148
    }
149
150
    /**
151
     * Forbid using WYSIWYG editor when editing anything else then sections or the entire page
152
     *
153
     * This would be the case for the edittable editor or the editor of the data plugin
154
     *
155
     * @return bool
156
     */
157
    protected function allowWYSIWYG()
158
    {
159
        global $INPUT;
160
        return !$INPUT->has('target') || $INPUT->str('target') === 'section';
161
    }
162
163
    public function addAddtionalForms(Doku_Event $event)
164
    {
165
        if (!$this->allowWYSIWYG()) {
166
            return;
167
        }
168
169
        if (!in_array($event->data, ['edit', 'preview'])) {
170
            return;
171
        }
172
173
        $linkForm = new dokuwiki\Form\Form([
174
            'class' => 'plugin_prosemirror_linkform',
175
            'id' => 'prosemirror-linkform',
176
            'style' => 'display: none;',
177
        ]);
178
        $linkForm->addFieldsetOpen('Links')->addClass('js-link-fieldset');;
179
        $iwOptions = array_keys(getInterwiki());
180
        $linkForm->addDropdown('iwshortcut', $iwOptions, 'InterWiki')->attr('required', 'required');
181
182
        $linkForm->addButtonHTML('linkwiz', inlineSVG(DOKU_PLUGIN . 'prosemirror/images/link.svg'))->attrs([
0 ignored issues
show
Bug introduced by
The constant DOKU_PLUGIN was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
183
            'type' => 'button',
184
            'class' => 'js-open-linkwiz linkform_linkwiz'
185
        ]);
186
        $linkForm->addTextInput('linktarget', $this->getLang('link target'))->attrs(
187
            [
188
            'required'=> 'required',
189
            'autofocus' => 'autofocus',
190
            ]
191
        );
192
193
        $linkForm->addTagOpen('div')->addClass('radio-wrapper');
194
        $linkForm->addTagOpen('fieldset');
195
        $linkForm->addTagOpen('legend');
196
        $linkForm->addHTML('Link Type');
197
        $linkForm->addTagClose('legend');
198
        $linkForm->addRadioButton('linktype', $this->getLang('type:wiki page'))->val('internallink');
199
        $linkForm->addRadioButton('linktype', $this->getLang('type:interwiki'))->val('interwikilink');
200
        $linkForm->addRadioButton('linktype', $this->getLang('type:email'))->val('emaillink');
201
        $linkForm->addRadioButton('linktype', $this->getLang('type:external'))->val('externallink')->attr('checked', 'checked');
202
        $linkForm->addRadioButton('linktype', $this->getLang('type:other'))->val('other');
203
        $linkForm->addTagClose('fieldset');
204
        $linkForm->addTagClose('div');
205
206
        $linkForm->addTagOpen('div')->addClass('radio-wrapper');
207
        $linkForm->addTagOpen('fieldset');
208
        $linkForm->addTagOpen('legend');
209
        $linkForm->addHTML('Link Name Type');
210
        $linkForm->addTagClose('legend');
211
        $linkForm->addRadioButton('nametype', $this->getLang('type:automatic title'))->val('automatic')->attr('checked', 'checked');
212
        $linkForm->addRadioButton('nametype', $this->getLang('type:custom title'))->val('custom');
213
        $linkForm->addRadioButton('nametype', $this->getLang('type:image'))->val('image');
214
        $linkForm->addTextInput('linkname', 'Link name')->attr('placeholder', $this->getLang('placeholder:link name'));
215
        $linkForm->addTagOpen('div')->addClass('js-media-wrapper');
216
        $linkForm->addTagClose('div');
217
        $linkForm->addTagClose('fieldset');
218
        $linkForm->addTagClose('div');
219
220
221
        $linkForm->addFieldsetClose();
222
        $linkForm->addButton('ok-button', 'OK')->attr('type', 'submit');
223
        $linkForm->addButton('cancel-button', $this->getLang('cancel'))->attr('type', 'button');
224
225
        echo $linkForm->toHTML();
226
227
        $mediaForm = new dokuwiki\Form\Form([
228
            'class' => 'plugin_prosemirror_mediaform',
229
            'id' => 'prosemirror-mediaform',
230
            'style' => 'display: none;',
231
        ]);
232
        $mediaForm->addFieldsetOpen($this->getLang('legend:media'))->addClass('js-media-fieldset');
233
        $mediaForm->addButtonHTML('mediamanager', inlineSVG(DOKU_PLUGIN . 'prosemirror/images/file-image-outline.svg'))->attrs([
234
            'type' => 'button',
235
            'class' => 'js-open-mediamanager mediaform_mediamanager'
236
        ]);
237
        $mediaForm->addTextInput('mediatarget', $this->getLang('media target'))->attrs(
238
            [
239
                'required'=> 'required',
240
                'autofocus' => 'autofocus',
241
            ]
242
        );
243
        $mediaForm->addTextInput('mediacaption', $this->getLang('label:caption'));
244
245
        $mediaForm->addTagOpen('div')->addClass('image-properties');
246
        $mediaForm->addTagOpen('p');
247
        $mediaForm->addHTML($this->getLang('label:image_properties'));
248
        $mediaForm->addTagClose('p');
249
250
        $mediaForm->addTagOpen('div')->addClass('input-wrapper');
251
        $mediaForm->addTagOpen('fieldset');
252
        $mediaForm->addTagOpen('legend');
253
        $mediaForm->addHTML($this->getLang('legend:size'));
254
        $mediaForm->addTagClose('legend');
255
        $mediaForm->addTextInput('width', $this->getLang('label:width'))->attr('type', 'number');
256
        $mediaForm->addTextInput('height', $this->getLang('label:height'))->attr('type', 'number');
257
        $mediaForm->addTagClose('fieldset');
258
        $mediaForm->addTagClose('div');
259
260
        $mediaForm->addTagOpen('div')->addClass('input-wrapper');
261
        $mediaForm->addTagOpen('fieldset');
262
        $mediaForm->addTagOpen('legend');
263
        $mediaForm->addHTML($this->getLang('legend:alignment'));
264
        $mediaForm->addTagClose('legend');
265
        $mediaForm->addRadioButton('alignment', $this->getLang('label:default alignment'))->val('')->attr('checked', 'checked');
266
        $mediaForm->addRadioButton('alignment', $this->getLang('label:float left'))->val('left');
267
        $mediaForm->addRadioButton('alignment', $this->getLang('label:center alignment'))->val('center');
268
        $mediaForm->addRadioButton('alignment', $this->getLang('label:float right'))->val('right');
269
        $mediaForm->addTagClose('fieldset');
270
        $mediaForm->addTagClose('div');
271
272
        $mediaForm->addTagOpen('div')->addClass('input-wrapper');
273
        $mediaForm->addTagOpen('fieldset');
274
        $mediaForm->addTagOpen('legend');
275
        $mediaForm->addHTML($this->getLang('legend:linking'));
276
        $mediaForm->addTagClose('legend');
277
        $mediaForm->addRadioButton('linking', $this->getLang('label:default linking'))->val('details')->attr('checked', 'checked');
278
        $mediaForm->addRadioButton('linking', $this->getLang('label:direct linking'))->val('direct');
279
        $mediaForm->addRadioButton('linking', $this->getLang('label:nolink'))->val('nolink');
280
        $mediaForm->addRadioButton('linking', $this->getLang('label:linkonly'))->val('linkonly');
281
        $mediaForm->addTagClose('fieldset');
282
        $mediaForm->addTagClose('div');
283
284
        $mediaForm->addTagOpen('div')->addClass('input-wrapper');
285
        $mediaForm->addTagOpen('fieldset');
286
        $mediaForm->addTagOpen('legend');
287
        $mediaForm->addHTML($this->getLang('legend:caching'));
288
        $mediaForm->addTagClose('legend');
289
        $mediaForm->addRadioButton('caching', $this->getLang('label:default caching'))->val('')->attr('checked', 'checked');
290
        $mediaForm->addRadioButton('caching', $this->getLang('label:recache'))->val('recache');
291
        $mediaForm->addRadioButton('caching', $this->getLang('label:nocache'))->val('nocache');
292
        $mediaForm->addTagClose('fieldset');
293
        $mediaForm->addTagClose('div');
294
295
        $mediaForm->addTagClose('div'); // end of image-properties
296
297
        $mediaForm->addFieldsetClose();
298
        $mediaForm->addButton('ok-button', 'OK')->attr('type', 'submit');
299
        $mediaForm->addButton('cancel-button', $this->getLang('cancel'))->attr('type', 'button');
300
301
        // dynamic image hack? https://www.dokuwiki.org/images#dynamic_images
302
303
        echo $mediaForm->toHTML();
304
305
        // phpcs:disable
306
        $languages = explode(' ', '4cs 6502acme 6502kickass 6502tasm 68000devpac abap actionscript3 actionscript ada aimms algol68 apache applescript apt_sources arm asm asp asymptote autoconf autohotkey autoit avisynth awk bascomavr bash basic4gl batch bf biblatex bibtex blitzbasic bnf boo caddcl cadlisp ceylon cfdg cfm chaiscript chapel cil c_loadrunner clojure c_mac cmake cobol coffeescript c cpp cpp-qt cpp-winapi csharp css cuesheet c_winapi dart dcl dcpu16 dcs delphi diff div dos dot d ecmascript eiffel email epc e erlang euphoria ezt f1 falcon fo fortran freebasic freeswitch fsharp gambas gdb genero genie gettext glsl gml gnuplot go groovy gwbasic haskell haxe hicest hq9plus html html4strict html5 icon idl ini inno intercal io ispfpanel java5 java javascript jcl j jquery julia kixtart klonec klonecpp kotlin latex lb ldif lisp llvm locobasic logtalk lolcode lotusformulas lotusscript lscript lsl2 lua m68k magiksf make mapbasic mathematica matlab mercury metapost mirc mk-61 mmix modula2 modula3 mpasm mxml mysql nagios netrexx newlisp nginx nimrod nsis oberon2 objc objeck ocaml-brief ocaml octave oobas oorexx oracle11 oracle8 oxygene oz parasail parigp pascal pcre perl6 perl per pf phix php-brief php pic16 pike pixelbender pli plsql postgresql postscript povray powerbuilder powershell proftpd progress prolog properties providex purebasic pycon pys60 python qbasic qml q racket rails rbs rebol reg rexx robots rpmspec rsplus ruby rust sas sass scala scheme scilab scl sdlbasic smalltalk smarty spark sparql sql standardml stonescript swift systemverilog tclegg tcl teraterm texgraph text thinbasic tsql twig typoscript unicon upc urbi uscript vala vbnet vb vbscript vedit verilog vhdl vim visualfoxpro visualprolog whitespace whois winbatch xbasic xml xojo xorg_conf xpp yaml z80 zxbasic');
307
        // phpcs:enable
308
        $datalistHTML = '<datalist id="codelanguages">';
309
        foreach ($languages as $language) {
310
            $datalistHTML .= "<option value=\"$language\">";
311
        }
312
        $datalistHTML .= '</datalist>';
313
        echo $datalistHTML;
314
    }
315
316
    /**
317
     * Provide the current smiley configuration to Javascript
318
     */
319
    public function addJSINFO()
320
    {
321
        global $JSINFO;
322
        $JSINFO['SMILEY_CONF'] = getSmileys();
323
    }
324
}
325
326
// vim:ts=4:sw=4:et:
327