]> CyberLeo.Net >> Repos - SourceForge/phpwiki.git/blob - lib/WysiwygEdit/Wikiwyg.php
include [all] Include and file path should be devided with single space. File path...
[SourceForge/phpwiki.git] / lib / WysiwygEdit / Wikiwyg.php
1 <?php
2
3 /**
4  * Wikiwyg is compatible with most internet browsers which
5  * include: IE 5.5+ (Windows), Firefox 1.0+, Mozilla 1.3+
6  * and Netscape 7+.
7  *
8  * Download: http://openjsan.org/doc/i/in/ingy/Wikiwyg/
9  * Suggested installation into themes/default/Wikiwyg/
10  *
11  * @package WysiwygEdit
12  * @author  Reini Urban, based on a patch by Jean-Nicolas GEREONE, STMicroelectronics, 2006
13  * Current maintainer: Sabri LABBENE, STMicroelectronics, 2006
14  */
15
16 require_once 'lib/WysiwygEdit.php';
17
18 class WysiwygEdit_Wikiwyg extends WysiwygEdit {
19
20     function WysiwygEdit_Wikiwyg() {
21         global $request, $LANG;
22         $this->_transformer_tags = false;
23     $this->BasePath = DATA_PATH.'/themes/default/Wikiwyg';
24     $this->_htmltextid = "edit-content";
25         $this->_wikitextid = "editareawiki";
26     $script_url = deduce_script_name();
27     if ((DEBUG & _DEBUG_REMOTE) and isset($_GET['start_debug']))
28         $script_url .= ("?start_debug=".$_GET['start_debug']);
29         $this->_jsdefault = "";
30     }
31
32     function Head($name='edit[content]') {
33         global $WikiTheme;
34         foreach (array("Wikiwyg.js","Wikiwyg/Toolbar.js","Wikiwyg/Preview.js","Wikiwyg/Wikitext.js",
35                        "Wikiwyg/Wysiwyg.js","Wikiwyg/Phpwiki.js","Wikiwyg/HTML.js",
36                        "Wikiwyg/Toolbar.js") as $js) {
37             $WikiTheme->addMoreHeaders
38                 (Javascript('', array('src' => $this->BasePath . '/' . $js,
39                                       'language' => 'JavaScript')));
40         }
41         $doubleClickToEdit = ($GLOBALS['request']->getPref('doubleClickEdit') or ENABLE_DOUBLECLICKEDIT)
42             ? 'true' : 'false';
43     if ($GLOBALS['request']->getArg('mode') && $GLOBALS['request']->getArg('mode') == 'wysiwyg'){
44             return JavaScript($this->_jsdefault . "
45             window.onload = function() {
46             var wikiwyg = new Wikiwyg.Phpwiki();
47             var config = {
48             doubleClickToEdit:  $doubleClickToEdit,
49             javascriptLocation: data_path+'/themes/default/Wikiwyg/',
50             toolbar: {
51             imagesLocation: data_path+'/themes/default/Wikiwyg/images/',
52         controlLayout: [
53                'save','preview','save_button','|',
54                'p','|',
55                'h2', 'h3', 'h4','|',
56                'bold', 'italic', '|',
57                        'sup', 'sub', '|',
58                        'toc',
59                        'wikitext','|',
60                'pre','|',
61                'ordered', 'unordered','hr','|',
62                'link','|',
63                        'table'
64                ],
65         styleSelector: [
66                'label', 'p', 'h2', 'h3', 'h4', 'pre'
67                 ],
68         controlLabels: {
69                    save:     '"._("Apply changes")."',
70                cancel:   '"._("Exit toolbar")."',
71                h2:       '"._("Title 1")."',
72                h3:       '"._("Title 2")."',
73                h4:       '"._("Title 3")."',
74                verbatim: '"._("Verbatim")."',
75                        toc:   '"._("Table of Contents")."',
76                        wikitext:   '"._("Insert Wikitext section")."',
77                        sup:      '"._("Sup")."',
78                        sub:      '"._("Sub")."',
79                        preview:  '"._("Preview")."',
80                        save_button:'"._("Save")."'
81                   }
82             },
83             wysiwyg: {
84                 iframeId: 'iframe0'
85             },
86         wikitext: {
87           supportCamelCaseLinks: true
88         }
89             };
90             var div = document.getElementById(\"" . $this->_htmltextid . "\");
91             wikiwyg.createWikiwygArea(div, config);
92             wikiwyg_divs.push(wikiwyg);
93             wikiwyg.editMode();}"
94         );
95         }
96     }
97
98     function Textarea ($textarea, $wikitext, $name='edit[content]') {
99         global $request;
100
101         $htmltextid = $this->_htmltextid;
102         $textarea->SetAttr('id', $htmltextid);
103         $iframe0 = new RawXml('<iframe id="iframe0" src="blank.htm" height="0" width="0" frameborder="0"></iframe>');
104         if ($request->getArg('mode') and $request->getArg('mode') == 'wysiwyg'){
105         $out = HTML(HTML::div(array('class' => 'hint'),
106                                   _("Warning: This Wikiwyg editor has only Beta quality!")),
107                         $textarea,
108                         $iframe0,
109                 "\n");
110     } else {
111         $out = HTML($textarea, $iframe0, "\n");
112     }
113     return $out;
114     }
115
116     /**
117      * Handler to convert the Wiki Markup to HTML before editing.
118      * This will be converted back by WysiwygEdit_ConvertAfter if required.
119      *  *text* => '<b>text<b>'
120      */
121     function ConvertBefore($text) {
122         return $text;
123     }
124
125     /*
126      * No special PHP HTML->Wikitext conversion needed. This is done in js thanksfully.
127      * Avoided in editpage.php: PageEditor->getContent
128      */
129     function ConvertAfter($text) {
130         return TransformInline($text);
131     }
132 }
133
134 class WikiToHtml {
135   function WikiToHtml ($wikitext, &$request) {
136         $this->_wikitext = $wikitext;
137     $this->_request =& $request;
138     $this->_html = "";
139     $this->html_content = "";
140     }
141
142     function send() {
143         $this->convert();
144     echo $this->html_content;
145     }
146
147     function convert() {
148         require_once 'lib/BlockParser.php';
149     $xmlcontent = TransformText($this->_wikitext, 2.0, $this->_request->getArg('pagename'));
150     $this->_html = $xmlcontent->AsXML();
151
152     $this->replace_inside_html();
153     }
154
155     function replace_inside_html() {
156     global $charset;
157
158     $this->clean_links();
159         $this->clean_plugin_name();
160         $this->replace_known_plugins();
161         $this->replace_unknown_plugins();
162     // $this->replace_tags();
163     $this->clean_plugin();
164
165     if ($charset != 'utf-8') {
166          if ($charset == 'iso-8959-1') {
167              $this->_html = utf8_decode($this->_html);
168         } else {
169                 // check for iconv support
170                 loadPhpExtension("iconv");
171             $this->_html = iconv("UTF-8", $charset, $this->_html);
172          }
173         }
174     $this->html_content = $this->_html;
175     }
176
177     // Draft function to replace RichTable
178     // by a html table
179     // Works only on one plugin for the moment
180     function replace_known_plugins() {
181       // If match a plugin
182       $pattern = '/\&lt\;\?plugin\s+RichTable(.*)\?\&gt\;/Umsi';
183       $replace_string = "replace_rich_table";
184       $this->_html = preg_replace_callback($pattern,
185                        $replace_string,
186                        $this->_html);
187     }
188
189     // Replace unknown plugins by keyword Wikitext { tag }
190     function replace_unknown_plugins() {
191         $pattern = '/(\&lt\;\?plugin[^?]*\?\&gt\;)/Usi';
192     $replace_string =
193       '<p><div style="background-color:#D3D3D3;font-size:smaller;">Wikitext {
194  <br> \1 <br>}</div><br></p>';
195
196     $this->_html = preg_replace($pattern,
197                     $replace_string,
198                     $this->_html);
199     }
200
201     // Clean links to keep only <a href="link">name</a>
202     function clean_links() {
203         // Existing links
204         // FIXME: use VIRTUAL_PATH
205         $pattern = '/\<a href\=\"index.php\?pagename\=(\w+)\"([^>])*\>/Umsi';
206         $replace_string = '<a href="\1">';
207         $this->_html = preg_replace($pattern,
208                                     $replace_string,
209                                     $this->_html) ;
210         // Non existing links
211         $pattern = '/\<a href\=\"index.php\?pagename\=([^"]*)(&amp;action){1}([^>])*\>/Umsi';
212         $replace_string = '<a href="\1">';
213
214         $this->_html = preg_replace($pattern,
215                                     $replace_string,
216                                     $this->_html) ;
217
218         // Clean underline
219         $pattern = '/\<u\>(.*)\<\/u\>(\<a href="(.*))[?"]{1}.*\>.*\<\/a\>/Umsi';
220         $replace_string =
221             '<span>\2" style="color:blue;">\1</a></span>';
222
223         $this->_html = preg_replace($pattern,
224                                     $replace_string,
225                                     $this->_html) ;
226     }
227
228     // Put unknown tags in Wikitext {}
229     function replace_tags() {
230         // Replace old table format ( non plugin )
231         $pattern = '/(\ {0,4}(?:\S.*)?\|\S+\s*$.*?\<\/p\>)/ms';
232         $replace_string =
233             '<p><div style="background-color:#D3D3D3;font-size:smaller;">Wikitext {
234  <br> \1 <br>}</div><br></p>';
235
236         $this->_html = preg_replace($pattern,
237                                     $replace_string,
238                                     $this->_html);
239 }
240
241     // Replace \n by <br> only in
242     // <?plugin ? > tag to keep formatting
243     function clean_plugin() {
244         $pattern = '/(\&lt\;\?plugin.*\?\&gt\;)/Umsei';
245     $replace_string = 'preg_replace("/\n/Ums","<br>","\1")';
246
247     $this->_html = preg_replace($pattern,
248                     $replace_string,
249                     $this->_html) ;
250
251     }
252
253     function clean_plugin_name() {
254     // Remove plugin name converted in a link
255     $pattern = '/(\&lt\;\?plugin\s)\<span.*\>\<span\>\<a href=.*\>(\w+)\<\/a\><\/span\><\/span>([^?]*\?\&gt\;)/Umsi';
256      $replace_string = '\1 \2 \3';
257      $this->_html = preg_replace($pattern,
258                      $replace_string,
259                      $this->_html) ;
260     }
261 }
262
263 // This is called to replace the RichTable plugin by an html table
264 // $matched contains html <p> tags so
265 // they are deleted before the conversion.
266 function replace_rich_table($matched) {
267     $plugin = $matched[1];
268
269     $unknown_options = "/colspan|rowspan|width|height/";
270
271     // if the plugin contains one of the options bellow
272     // it won't be converted
273     if (preg_match($unknown_options,$plugin))
274         return $matched[0]."\n";
275     else {
276         //Replace unused <p...>
277         $pattern = '/\<p.*\>/Umsi';
278         $replace_string = "";
279
280         $plugin = preg_replace($pattern,
281                                $replace_string,
282                                $plugin) ;
283
284         //replace unused </p> by \n
285         $pattern = '/\<\/p\>/Umsi';
286         $replace_string = "\n";
287
288         $plugin = preg_replace($pattern,
289                                $replace_string,
290                                $plugin) ;
291
292         $plugin = "<?plugin RichTable ".$plugin." ?>";
293
294         require_once 'lib/BlockParser.php';
295         $xmlcontent = TransformText($plugin, 2.0, $GLOBALS['request']->getArg('pagename'));
296         return $xmlcontent->AsXML();
297   }
298 }
299
300 // Local Variables:
301 // mode: php
302 // tab-width: 8
303 // c-basic-offset: 4
304 // c-hanging-comment-ender-p: nil
305 // indent-tabs-mode: nil
306 // End: