984d4c610f27c92d96aa9ccd3523582d5142334e
[redakcja.git] / project / static / js / edit_area_functions.js
1         //replace tabulation by the good number of white spaces\r
2         EditArea.prototype.replace_tab= function(text){\r
3                 return text.replace(/((\n?)([^\t\n]*)\t)/gi, editArea.smartTab);                // slower than simple replace...        \r
4         };\r
5         \r
6         // call by the replace_tab function\r
7         EditArea.prototype.smartTab= function(){\r
8                 val="                   ";\r
9                 return EditArea.prototype.smartTab.arguments[2] + EditArea.prototype.smartTab.arguments[3] + val.substr(0, editArea.tab_nb_char - (EditArea.prototype.smartTab.arguments[3].length)%editArea.tab_nb_char);\r
10         };\r
11         \r
12         EditArea.prototype.show_waiting_screen= function(){\r
13                 width   = this.editor_area.offsetWidth;\r
14                 height  = this.editor_area.offsetHeight;\r
15                 if( !(this.isIE && this.isIE<6) )\r
16                 {\r
17                         width   -= 2;\r
18                         height  -= 2;\r
19                 }\r
20                 this.processing_screen.style.display= "block";\r
21                 this.processing_screen.style.width      = width+"px";\r
22                 this.processing_screen.style.height     = height+"px";\r
23                 this.waiting_screen_displayed           = true;\r
24         };\r
25         \r
26         EditArea.prototype.hide_waiting_screen= function(){\r
27                 this.processing_screen.style.display="none";\r
28                 this.waiting_screen_displayed= false;\r
29         };\r
30         \r
31         EditArea.prototype.add_style= function(styles){\r
32                 if(styles.length>0){\r
33                         newcss = document.createElement("style");\r
34                         newcss.type="text/css";\r
35                         newcss.media="all";\r
36                         if(newcss.styleSheet){ // IE\r
37                                 newcss.styleSheet.cssText = styles;\r
38                         } else { // W3C\r
39                                 newcss.appendChild(document.createTextNode(styles));\r
40                         }\r
41                         document.getElementsByTagName("head")[0].appendChild(newcss);\r
42                 }\r
43         };\r
44         \r
45         EditArea.prototype.set_font= function(family, size){\r
46                 var t=this, a=this.textarea, s=this.settings, elem_font, i, elem;\r
47                 // list all elements concerned by font changes\r
48                 var elems= ["textarea", "content_highlight", "cursor_pos", "end_bracket", "selection_field", "selection_field_text", "line_number"];\r
49                 \r
50                 if(family && family!="")\r
51                         s["font_family"]= family;\r
52                 if(size && size>0)\r
53                         s["font_size"]  = size;\r
54                 if( t.isOpera && t.isOpera < 9.6 )      // opera<9.6 can't manage non monospace font\r
55                         s['font_family']="monospace";\r
56                         \r
57                 // update the select tag\r
58                 if( elem_font = _$("area_font_size") )\r
59                 {       \r
60                         for( i = 0; i < elem_font.length; i++ )\r
61                         {\r
62                                 if( elem_font.options[i].value && elem_font.options[i].value == s["font_size"] )\r
63                                         elem_font.options[i].selected=true;\r
64                         }\r
65                 }\r
66                 \r
67                 /*\r
68                  * somethimes firefox has rendering mistake with non-monospace font for text width in textarea vs in div for changing font size (eg: verdana change between 11pt to 12pt)\r
69                  * => looks like a browser internal random bug as text width can change while content_highlight is updated\r
70                  * we'll check if the font-size produce the same text width inside textarea and div and if not, we'll increment the font-size\r
71                  * \r
72                  * This is an ugly fix \r
73                  */ \r
74                 if( t.isFirefox )\r
75                 {\r
76                         var nbTry = 3;\r
77                         do {\r
78                                 var div1 = document.createElement( 'div' ), text1 = document.createElement( 'textarea' );\r
79                                 var styles = {\r
80                                         width:          '40px',\r
81                                         overflow:       'scroll',\r
82                                         zIndex:         50,\r
83                                         visibility:     'hidden',\r
84                                         fontFamily:     s["font_family"],\r
85                                         fontSize:       s["font_size"]+"pt",\r
86                                         lineHeight:     t.lineHeight+"px",\r
87                                         padding:        '0',\r
88                                         margin:         '0',\r
89                                         border:         'none',\r
90                                         whiteSpace:     'nowrap'\r
91                                 };\r
92                                 var diff, changed = false;\r
93                                 for( i in styles )\r
94                                 {\r
95                                         div1.style[ i ]         = styles[i];\r
96                                         text1.style[ i ]        = styles[i];\r
97                                 }\r
98                                 // no wrap for this text\r
99                                 text1.wrap = 'off';\r
100                                 text1.setAttribute('wrap', 'off');\r
101                                 t.container.appendChild( div1 );\r
102                                 t.container.appendChild( text1 );\r
103                                 // try to make FF to bug\r
104                                 div1.innerHTML          = text1.value   = 'azertyuiopqsdfghjklm';\r
105                                 div1.innerHTML          = text1.value   = text1.value+'wxcvbn^p*รน$!:;,,';\r
106                                 diff    =  text1.scrollWidth - div1.scrollWidth;
107                                 \r
108                                 // firefox return here a diff of 1 px between equals scrollWidth (can't explain)\r
109                                 if( Math.abs( diff ) >= 2 )\r
110                                 {\r
111                                         s["font_size"]++;\r
112                                         changed = true;\r
113                                 }\r
114                                 t.container.removeChild( div1 );\r
115                                 t.container.removeChild( text1 );\r
116                                 nbTry--;\r
117                         }while( changed && nbTry > 0 );\r
118                 }\r
119                 \r
120                 \r
121                 // calc line height\r
122                 elem                                    = t.test_font_size;\r
123                 elem.style.fontFamily   = ""+s["font_family"];\r
124                 elem.style.fontSize             = s["font_size"]+"pt";                          \r
125                 elem.innerHTML                  = "0";          \r
126                 t.lineHeight                    = elem.offsetHeight;\r
127 \r
128                 // update font for all concerned elements\r
129                 for( i=0; i<elems.length; i++)\r
130                 {\r
131                         elem    = _$(elems[i]); \r
132                         elem.style.fontFamily   = s["font_family"];\r
133                         elem.style.fontSize             = s["font_size"]+"pt";\r
134                         elem.style.lineHeight   = t.lineHeight+"px";\r
135                 }\r
136                 // define a css for <pre> tags\r
137                 t.add_style("pre{font-family:"+s["font_family"]+"}");\r
138                 \r
139                 // old opera and IE>=8 doesn't update font changes to the textarea\r
140                 if( ( t.isOpera && t.isOpera < 9.6 ) || t.isIE >= 8 )\r
141                 {\r
142                         var parNod = a.parentNode, nxtSib = a.nextSibling, start= a.selectionStart, end= a.selectionEnd;\r
143                         parNod.removeChild(a);\r
144                         parNod.insertBefore(a, nxtSib);\r
145                         t.area_select(start, end-start);\r
146                 }\r
147                 \r
148                 // force update of selection field\r
149                 this.focus();\r
150                 this.update_size();\r
151                 this.check_line_selection();\r
152         };\r
153         \r
154         EditArea.prototype.change_font_size= function(){\r
155                 var size=_$("area_font_size").value;\r
156                 if(size>0)\r
157                         this.set_font("", size);                        \r
158         };\r
159         \r
160         \r
161         EditArea.prototype.open_inline_popup= function(popup_id){\r
162                 this.close_all_inline_popup();\r
163                 var popup= _$(popup_id);                \r
164                 var editor= _$("editor");\r
165                 \r
166                 // search matching icon\r
167                 for(var i=0; i<this.inlinePopup.length; i++){\r
168                         if(this.inlinePopup[i]["popup_id"]==popup_id){\r
169                                 var icon= _$(this.inlinePopup[i]["icon_id"]);\r
170                                 if(icon){\r
171                                         this.switchClassSticky(icon, 'editAreaButtonSelected', true);                   \r
172                                         break;\r
173                                 }\r
174                         }\r
175                 }\r
176                 // check size\r
177                 popup.style.height="auto";\r
178                 popup.style.overflow= "visible";\r
179                         \r
180                 if(document.body.offsetHeight< popup.offsetHeight){\r
181                         popup.style.height= (document.body.offsetHeight-10)+"px";\r
182                         popup.style.overflow= "auto";\r
183                 }\r
184                 \r
185                 if(!popup.positionned){\r
186                         var new_left= editor.offsetWidth /2 - popup.offsetWidth /2;\r
187                         var new_top= editor.offsetHeight /2 - popup.offsetHeight /2;\r
188                         //var new_top= area.offsetHeight /2 - popup.offsetHeight /2;\r
189                         //var new_left= area.offsetWidth /2 - popup.offsetWidth /2;\r
190                         //alert("new_top: ("+new_top+") = calculeOffsetTop(area) ("+calculeOffsetTop(area)+") + area.offsetHeight /2("+ area.offsetHeight /2+") - popup.offsetHeight /2("+popup.offsetHeight /2+") - scrollTop: "+document.body.scrollTop);\r
191                         popup.style.left= new_left+"px";\r
192                         popup.style.top= new_top+"px";\r
193                         popup.positionned=true;\r
194                 }\r
195                 popup.style.visibility="visible";\r
196                 \r
197                 //popup.style.display="block";\r
198         };\r
199 \r
200         EditArea.prototype.close_inline_popup= function(popup_id){\r
201                 var popup= _$(popup_id);                \r
202                 // search matching icon\r
203                 for(var i=0; i<this.inlinePopup.length; i++){\r
204                         if(this.inlinePopup[i]["popup_id"]==popup_id){\r
205                                 var icon= _$(this.inlinePopup[i]["icon_id"]);\r
206                                 if(icon){\r
207                                         this.switchClassSticky(icon, 'editAreaButtonNormal', false);                    \r
208                                         break;\r
209                                 }\r
210                         }\r
211                 }\r
212                 \r
213                 popup.style.visibility="hidden";        \r
214         };\r
215         \r
216         EditArea.prototype.close_all_inline_popup= function(e){\r
217                 for(var i=0; i<this.inlinePopup.length; i++){\r
218                         this.close_inline_popup(this.inlinePopup[i]["popup_id"]);               \r
219                 }\r
220                 this.textarea.focus();\r
221         };\r
222         \r
223         EditArea.prototype.show_help= function(){\r
224                 \r
225                 this.open_inline_popup("edit_area_help");\r
226                 \r
227         };\r
228                         \r
229         EditArea.prototype.new_document= function(){\r
230                 this.textarea.value="";\r
231                 this.area_select(0,0);\r
232         };\r
233         \r
234         EditArea.prototype.get_all_toolbar_height= function(){\r
235                 var area= _$("editor");\r
236                 var results= parent.getChildren(area, "div", "class", "area_toolbar", "all", "0");      // search only direct children\r
237                 //results= results.concat(getChildren(area, "table", "class", "area_toolbar", "all", "0"));\r
238                 var height=0;\r
239                 for(var i=0; i<results.length; i++){                    \r
240                         height+= results[i].offsetHeight;\r
241                 }\r
242                 //alert("toolbar height: "+height);\r
243                 return height;\r
244         };\r
245         \r
246         EditArea.prototype.go_to_line= function(line){  \r
247                 if(!line)\r
248                 {       \r
249                         var icon= _$("go_to_line");\r
250                         if(icon != null){\r
251                                 this.restoreClass(icon);\r
252                                 this.switchClassSticky(icon, 'editAreaButtonSelected', true);\r
253                         }\r
254                         \r
255                         line= prompt(this.get_translation("go_to_line_prompt"));\r
256                         if(icon != null)\r
257                                 this.switchClassSticky(icon, 'editAreaButtonNormal', false);\r
258                 }\r
259                 if(line && line!=null && line.search(/^[0-9]+$/)!=-1){\r
260                         var start=0;\r
261                         var lines= this.textarea.value.split("\n");\r
262                         if(line > lines.length)\r
263                                 start= this.textarea.value.length;\r
264                         else{\r
265                                 for(var i=0; i<Math.min(line-1, lines.length); i++)\r
266                                         start+= lines[i].length + 1;\r
267                         }\r
268                         this.area_select(start, 0);\r
269                 }\r
270                 \r
271                 \r
272         };\r
273         \r
274         \r
275         EditArea.prototype.change_smooth_selection_mode= function(setTo){\r
276                 //alert("setTo: "+setTo);\r
277                 if(this.do_highlight)\r
278                         return;\r
279                         \r
280                 if(setTo != null){\r
281                         if(setTo === false)\r
282                                 this.smooth_selection=true;\r
283                         else\r
284                                 this.smooth_selection=false;\r
285                 }\r
286                 var icon= _$("change_smooth_selection");\r
287                 this.textarea.focus();\r
288                 if(this.smooth_selection===true){\r
289                         //setAttribute(icon, "class", getAttribute(icon, "class").replace(/ selected/g, "") );\r
290                         /*setAttribute(icon, "oldClassName", "editAreaButtonNormal" );\r
291                         setAttribute(icon, "className", "editAreaButtonNormal" );*/\r
292                         //this.restoreClass(icon);\r
293                         //this.restoreAndSwitchClass(icon,'editAreaButtonNormal');\r
294                         this.switchClassSticky(icon, 'editAreaButtonNormal', false);\r
295                         \r
296                         this.smooth_selection=false;\r
297                         this.selection_field.style.display= "none";\r
298                         _$("cursor_pos").style.display= "none";\r
299                         _$("end_bracket").style.display= "none";\r
300                 }else{\r
301                         //setAttribute(icon, "class", getAttribute(icon, "class") + " selected");\r
302                         //this.switchClass(icon,'editAreaButtonSelected');\r
303                         this.switchClassSticky(icon, 'editAreaButtonSelected', false);\r
304                         this.smooth_selection=true;\r
305                         this.selection_field.style.display= "block";\r
306                         _$("cursor_pos").style.display= "block";\r
307                         _$("end_bracket").style.display= "block";\r
308                 }       \r
309         };\r
310         \r
311         // the auto scroll of the textarea has some lacks when it have to show cursor in the visible area when the textarea size change\r
312         // show specifiy whereas it is the "top" or "bottom" of the selection that is showned\r
313         EditArea.prototype.scroll_to_view= function(show){\r
314                 var zone, lineElem;\r
315                 if(!this.smooth_selection)\r
316                         return;\r
317                 zone= _$("result");\r
318                 \r
319                 // manage height scroll\r
320                 var cursor_pos_top= _$("cursor_pos").cursor_top;\r
321                 if(show=="bottom")\r
322                 {\r
323                         //cursor_pos_top+=  (this.last_selection["line_nb"]-1)* this.lineHeight;\r
324                         cursor_pos_top+= this.getLinePosTop( this.last_selection['line_start'] + this.last_selection['line_nb'] - 1 );\r
325                 }\r
326                         \r
327                 var max_height_visible= zone.clientHeight + zone.scrollTop;\r
328                 var miss_top    = cursor_pos_top + this.lineHeight - max_height_visible;\r
329                 if(miss_top>0){\r
330                         //alert(miss_top);\r
331                         zone.scrollTop=  zone.scrollTop + miss_top;\r
332                 }else if( zone.scrollTop > cursor_pos_top){\r
333                         // when erase all the content -> does'nt scroll back to the top\r
334                         //alert("else: "+cursor_pos_top);\r
335                         zone.scrollTop= cursor_pos_top;  \r
336                 }\r
337                 \r
338                 // manage left scroll\r
339                 //var cursor_pos_left= parseInt(_$("cursor_pos").style.left.replace("px",""));\r
340                 var cursor_pos_left= _$("cursor_pos").cursor_left;\r
341                 var max_width_visible= zone.clientWidth + zone.scrollLeft;\r
342                 var miss_left= cursor_pos_left + 10 - max_width_visible;\r
343                 if(miss_left>0){                        \r
344                         zone.scrollLeft= zone.scrollLeft + miss_left + 50;\r
345                 }else if( zone.scrollLeft > cursor_pos_left){\r
346                         zone.scrollLeft= cursor_pos_left ;\r
347                 }else if( zone.scrollLeft == 45){\r
348                         // show the line numbers if textarea align to it's left\r
349                         zone.scrollLeft=0;\r
350                 }\r
351         };\r
352         \r
353         EditArea.prototype.check_undo= function(only_once){\r
354                 if(!editAreas[this.id])\r
355                         return false;\r
356                 if(this.textareaFocused && editAreas[this.id]["displayed"]==true){\r
357                         var text=this.textarea.value;\r
358                         if(this.previous.length<=1)\r
359                                 this.switchClassSticky(_$("undo"), 'editAreaButtonDisabled', true);\r
360                 \r
361                         if(!this.previous[this.previous.length-1] || this.previous[this.previous.length-1]["text"] != text){\r
362                                 this.previous.push({"text": text, "selStart": this.textarea.selectionStart, "selEnd": this.textarea.selectionEnd});\r
363                                 if(this.previous.length > this.settings["max_undo"]+1)\r
364                                         this.previous.shift();\r
365                                 \r
366                         }\r
367                         if(this.previous.length >= 2)\r
368                                 this.switchClassSticky(_$("undo"), 'editAreaButtonNormal', false);              \r
369                 }\r
370 \r
371                 if(!only_once)\r
372                         setTimeout("editArea.check_undo()", 3000);\r
373         };\r
374         \r
375         EditArea.prototype.undo= function(){\r
376                 //alert("undo"+this.previous.length);\r
377                 if(this.previous.length > 0)\r
378                 {\r
379                         this.getIESelection();\r
380                 //      var pos_cursor=this.textarea.selectionStart;\r
381                         this.next.push( { "text": this.textarea.value, "selStart": this.textarea.selectionStart, "selEnd": this.textarea.selectionEnd } );\r
382                         var prev= this.previous.pop();\r
383                         if( prev["text"] == this.textarea.value && this.previous.length > 0 )\r
384                                 prev    =this.previous.pop();                                           \r
385                         this.textarea.value     = prev["text"];\r
386                         this.last_undo          = prev["text"];\r
387                         this.area_select(prev["selStart"], prev["selEnd"]-prev["selStart"]);\r
388                         this.switchClassSticky(_$("redo"), 'editAreaButtonNormal', false);\r
389                         this.resync_highlight(true);\r
390                         //alert("undo"+this.previous.length);\r
391                         this.check_file_changes();\r
392                 }\r
393         };\r
394         \r
395         EditArea.prototype.redo= function(){\r
396                 if(this.next.length > 0)\r
397                 {\r
398                         /*this.getIESelection();*/\r
399                         //var pos_cursor=this.textarea.selectionStart;\r
400                         var next= this.next.pop();\r
401                         this.previous.push(next);\r
402                         this.textarea.value= next["text"];\r
403                         this.last_undo= next["text"];\r
404                         this.area_select(next["selStart"], next["selEnd"]-next["selStart"]);\r
405                         this.switchClassSticky(_$("undo"), 'editAreaButtonNormal', false);\r
406                         this.resync_highlight(true);\r
407                         this.check_file_changes();\r
408                 }\r
409                 if(     this.next.length == 0)\r
410                         this.switchClassSticky(_$("redo"), 'editAreaButtonDisabled', true);\r
411         };\r
412         \r
413         EditArea.prototype.check_redo= function(){\r
414                 if(editArea.next.length == 0 || editArea.textarea.value!=editArea.last_undo){\r
415                         editArea.next= [];      // undo the ability to use "redo" button\r
416                         editArea.switchClassSticky(_$("redo"), 'editAreaButtonDisabled', true);\r
417                 }\r
418                 else\r
419                 {\r
420                         this.switchClassSticky(_$("redo"), 'editAreaButtonNormal', false);\r
421                 }\r
422         };\r
423         \r
424         \r
425         // functions that manage icons roll over, disabled, etc...\r
426         EditArea.prototype.switchClass = function(element, class_name, lock_state) {\r
427                 var lockChanged = false;\r
428         \r
429                 if (typeof(lock_state) != "undefined" && element != null) {\r
430                         element.classLock = lock_state;\r
431                         lockChanged = true;\r
432                 }\r
433         \r
434                 if (element != null && (lockChanged || !element.classLock)) {\r
435                         element.oldClassName = element.className;\r
436                         element.className = class_name;\r
437                 }\r
438         };\r
439         \r
440         EditArea.prototype.restoreAndSwitchClass = function(element, class_name) {\r
441                 if (element != null && !element.classLock) {\r
442                         this.restoreClass(element);\r
443                         this.switchClass(element, class_name);\r
444                 }\r
445         };\r
446         \r
447         EditArea.prototype.restoreClass = function(element) {\r
448                 if (element != null && element.oldClassName && !element.classLock) {\r
449                         element.className = element.oldClassName;\r
450                         element.oldClassName = null;\r
451                 }\r
452         };\r
453         \r
454         EditArea.prototype.setClassLock = function(element, lock_state) {\r
455                 if (element != null)\r
456                         element.classLock = lock_state;\r
457         };\r
458         \r
459         EditArea.prototype.switchClassSticky = function(element, class_name, lock_state) {\r
460                 var lockChanged = false;\r
461                 if (typeof(lock_state) != "undefined" && element != null) {\r
462                         element.classLock = lock_state;\r
463                         lockChanged = true;\r
464                 }\r
465         \r
466                 if (element != null && (lockChanged || !element.classLock)) {\r
467                         element.className = class_name;\r
468                         element.oldClassName = class_name;\r
469                 }\r
470         };\r
471         \r
472         //make the "page up" and "page down" buttons works correctly\r
473         EditArea.prototype.scroll_page= function(params){\r
474                 var dir= params["dir"], shift_pressed= params["shift"];\r
475                 var lines= this.textarea.value.split("\n");             \r
476                 var new_pos=0, length=0, char_left=0, line_nb=0, curLine=0;\r
477                 var toScrollAmount      = _$("result").clientHeight -30;\r
478                 var nbLineToScroll      = 0, diff= 0;\r
479                 \r
480                 if(dir=="up"){\r
481                         nbLineToScroll  = Math.ceil( toScrollAmount / this.lineHeight );\r
482                         \r
483                         // fix number of line to scroll\r
484                         for( i = this.last_selection["line_start"]; i - diff > this.last_selection["line_start"] - nbLineToScroll ; i-- )\r
485                         {\r
486                                 if( elem = _$('line_'+ i) )\r
487                                 {\r
488                                         diff +=  Math.floor( ( elem.offsetHeight - 1 ) / this.lineHeight );\r
489                                 }\r
490                         }\r
491                         nbLineToScroll  -= diff;\r
492                         \r
493                         if(this.last_selection["selec_direction"]=="up"){\r
494                                 for(line_nb=0; line_nb< Math.min(this.last_selection["line_start"]-nbLineToScroll, lines.length); line_nb++){\r
495                                         new_pos+= lines[line_nb].length + 1;\r
496                                 }\r
497                                 char_left=Math.min(lines[Math.min(lines.length-1, line_nb)].length, this.last_selection["curr_pos"]-1);\r
498                                 if(shift_pressed)\r
499                                         length=this.last_selection["selectionEnd"]-new_pos-char_left;   \r
500                                 this.area_select(new_pos+char_left, length);\r
501                                 view="top";\r
502                         }else{                  \r
503                                 view="bottom";\r
504                                 for(line_nb=0; line_nb< Math.min(this.last_selection["line_start"]+this.last_selection["line_nb"]-1-nbLineToScroll, lines.length); line_nb++){\r
505                                         new_pos+= lines[line_nb].length + 1;\r
506                                 }\r
507                                 char_left=Math.min(lines[Math.min(lines.length-1, line_nb)].length, this.last_selection["curr_pos"]-1);\r
508                                 if(shift_pressed){\r
509                                         //length=this.last_selection["selectionEnd"]-new_pos-char_left; \r
510                                         start= Math.min(this.last_selection["selectionStart"], new_pos+char_left);\r
511                                         length= Math.max(new_pos+char_left, this.last_selection["selectionStart"] )- start ;\r
512                                         if(new_pos+char_left < this.last_selection["selectionStart"])\r
513                                                 view="top";\r
514                                 }else\r
515                                         start=new_pos+char_left;\r
516                                 this.area_select(start, length);\r
517                                 \r
518                         }\r
519                 }\r
520                 else\r
521                 {\r
522                         var nbLineToScroll= Math.floor( toScrollAmount / this.lineHeight );\r
523                         // fix number of line to scroll\r
524                         for( i = this.last_selection["line_start"]; i + diff < this.last_selection["line_start"] + nbLineToScroll ; i++ )\r
525                         {\r
526                                 if( elem = _$('line_'+ i) )\r
527                                 {\r
528                                         diff +=  Math.floor( ( elem.offsetHeight - 1 ) / this.lineHeight );\r
529                                 }\r
530                         }\r
531                         nbLineToScroll  -= diff;\r
532                                 \r
533                         if(this.last_selection["selec_direction"]=="down"){\r
534                                 view="bottom";\r
535                                 for(line_nb=0; line_nb< Math.min(this.last_selection["line_start"]+this.last_selection["line_nb"]-2+nbLineToScroll, lines.length); line_nb++){\r
536                                         if(line_nb==this.last_selection["line_start"]-1)\r
537                                                 char_left= this.last_selection["selectionStart"] -new_pos;\r
538                                         new_pos+= lines[line_nb].length + 1;\r
539                                                                         \r
540                                 }\r
541                                 if(shift_pressed){\r
542                                         length=Math.abs(this.last_selection["selectionStart"]-new_pos); \r
543                                         length+=Math.min(lines[Math.min(lines.length-1, line_nb)].length, this.last_selection["curr_pos"]);\r
544                                         //length+=Math.min(lines[Math.min(lines.length-1, line_nb)].length, char_left);\r
545                                         this.area_select(Math.min(this.last_selection["selectionStart"], new_pos), length);\r
546                                 }else{\r
547                                         this.area_select(new_pos+char_left, 0);\r
548                                 }\r
549                                 \r
550                         }else{\r
551                                 view="top";\r
552                                 for(line_nb=0; line_nb< Math.min(this.last_selection["line_start"]+nbLineToScroll-1, lines.length, lines.length); line_nb++){\r
553                                         if(line_nb==this.last_selection["line_start"]-1)\r
554                                                 char_left= this.last_selection["selectionStart"] -new_pos;\r
555                                         new_pos+= lines[line_nb].length + 1;                                                                    \r
556                                 }\r
557                                 if(shift_pressed){\r
558                                         length=Math.abs(this.last_selection["selectionEnd"]-new_pos-char_left); \r
559                                         length+=Math.min(lines[Math.min(lines.length-1, line_nb)].length, this.last_selection["curr_pos"])- char_left-1;\r
560                                         //length+=Math.min(lines[Math.min(lines.length-1, line_nb)].length, char_left);\r
561                                         this.area_select(Math.min(this.last_selection["selectionEnd"], new_pos+char_left), length);\r
562                                         if(new_pos+char_left > this.last_selection["selectionEnd"])\r
563                                                 view="bottom";\r
564                                 }else{\r
565                                         this.area_select(new_pos+char_left, 0);\r
566                                 }\r
567                                 \r
568                         }\r
569                 }\r
570                 //console.log( new_pos, char_left, length, nbLineToScroll, toScrollAmount, _$("result").clientHeigh );\r
571                 this.check_line_selection();\r
572                 this.scroll_to_view(view);\r
573         };\r
574         \r
575         EditArea.prototype.start_resize= function(e){\r
576                 parent.editAreaLoader.resize["id"]              = editArea.id;          \r
577                 parent.editAreaLoader.resize["start_x"] = (e)? e.pageX : event.x + document.body.scrollLeft;            \r
578                 parent.editAreaLoader.resize["start_y"] = (e)? e.pageY : event.y + document.body.scrollTop;\r
579                 if(editArea.isIE)\r
580                 {\r
581                         editArea.textarea.focus();\r
582                         editArea.getIESelection();\r
583                 }\r
584                 parent.editAreaLoader.resize["selectionStart"]  = editArea.textarea.selectionStart;\r
585                 parent.editAreaLoader.resize["selectionEnd"]    = editArea.textarea.selectionEnd;\r
586                 parent.editAreaLoader.start_resize_area();\r
587         };\r
588         \r
589         EditArea.prototype.toggle_full_screen= function(to){\r
590                 var t=this, p=parent, a=t.textarea, html, frame, selStart, selEnd, old, icon;\r
591                 if(typeof(to)=="undefined")\r
592                         to= !t.fullscreen['isFull'];\r
593                 old                     = t.fullscreen['isFull'];\r
594                 t.fullscreen['isFull']= to;\r
595                 icon            = _$("fullscreen");\r
596                 selStart        = t.textarea.selectionStart;\r
597                 selEnd          = t.textarea.selectionEnd;\r
598                 html            = p.document.getElementsByTagName("html")[0];\r
599                 frame           = p.document.getElementById("frame_"+t.id);\r
600                 \r
601                 if(to && to!=old)\r
602                 {       // toogle on fullscreen         \r
603                         \r
604                         t.fullscreen['old_overflow']    = p.get_css_property(html, "overflow");\r
605                         t.fullscreen['old_height']              = p.get_css_property(html, "height");\r
606                         t.fullscreen['old_width']               = p.get_css_property(html, "width");\r
607                         t.fullscreen['old_scrollTop']   = html.scrollTop;\r
608                         t.fullscreen['old_scrollLeft']  = html.scrollLeft;\r
609                         t.fullscreen['old_zIndex']              = p.get_css_property(frame, "z-index");\r
610                         if(t.isOpera){\r
611                                 html.style.height       = "100%";\r
612                                 html.style.width        = "100%";       \r
613                         }\r
614                         html.style.overflow     = "hidden";\r
615                         html.scrollTop          = 0;\r
616                         html.scrollLeft         = 0;\r
617                         \r
618                         frame.style.position    = "absolute";\r
619                         frame.style.width               = html.clientWidth+"px";\r
620                         frame.style.height              = html.clientHeight+"px";\r
621                         frame.style.display             = "block";\r
622                         frame.style.zIndex              = "999999";\r
623                         frame.style.top                 = "0px";\r
624                         frame.style.left                = "0px";\r
625                         \r
626                         // if the iframe was in a div with position absolute, the top and left are the one of the div, \r
627                         // so I fix it by seeing at witch position the iframe start and correcting it\r
628                         frame.style.top                 = "-"+p.calculeOffsetTop(frame)+"px";\r
629                         frame.style.left                = "-"+p.calculeOffsetLeft(frame)+"px";\r
630                         \r
631                 //      parent.editAreaLoader.execCommand(t.id, "update_size();");\r
632                 //      var body=parent.document.getElementsByTagName("body")[0];\r
633                 //      body.appendChild(frame);\r
634                         \r
635                         t.switchClassSticky(icon, 'editAreaButtonSelected', false);\r
636                         t.fullscreen['allow_resize']= t.resize_allowed;\r
637                         t.allow_resize(false);\r
638         \r
639                         //t.area_select(selStart, selEnd-selStart);\r
640                         \r
641                 \r
642                         // opera can't manage to do a direct size update\r
643                         if(t.isFirefox){\r
644                                 p.editAreaLoader.execCommand(t.id, "update_size();");\r
645                                 t.area_select(selStart, selEnd-selStart);\r
646                                 t.scroll_to_view();\r
647                                 t.focus();\r
648                         }else{\r
649                                 setTimeout("p.editAreaLoader.execCommand('"+ t.id +"', 'update_size();');editArea.focus();", 10);\r
650                         }       \r
651                         \r
652         \r
653                 }\r
654                 else if(to!=old)\r
655                 {       // toogle off fullscreen\r
656                         frame.style.position="static";\r
657                         frame.style.zIndex= t.fullscreen['old_zIndex'];\r
658                 \r
659                         if(t.isOpera)\r
660                         {\r
661                                 html.style.height       = "auto"; \r
662                                 html.style.width        = "auto";\r
663                                 html.style.overflow     = "auto";\r
664                         }\r
665                         else if(t.isIE && p!=top)\r
666                         {       // IE doesn't manage html overflow in frames like in normal page... \r
667                                 html.style.overflow     = "auto";\r
668                         }\r
669                         else\r
670                         {\r
671                                 html.style.overflow     = t.fullscreen['old_overflow'];\r
672                         }\r
673                         html.scrollTop  = t.fullscreen['old_scrollTop'];\r
674                         html.scrollLeft = t.fullscreen['old_scrollLeft'];\r
675                 \r
676                         p.editAreaLoader.hide(t.id);\r
677                         p.editAreaLoader.show(t.id);\r
678                         \r
679                         t.switchClassSticky(icon, 'editAreaButtonNormal', false);\r
680                         if(t.fullscreen['allow_resize'])\r
681                                 t.allow_resize(t.fullscreen['allow_resize']);\r
682                         if(t.isFirefox){\r
683                                 t.area_select(selStart, selEnd-selStart);\r
684                                 setTimeout("editArea.scroll_to_view();", 10);\r
685                         }                       \r
686                         \r
687                         //p.editAreaLoader.remove_event(p.window, "resize", editArea.update_size);\r
688                 }\r
689                 \r
690         };\r
691         \r
692         EditArea.prototype.allow_resize= function(allow){\r
693                 var resize= _$("resize_area");\r
694                 if(allow){\r
695                         \r
696                         resize.style.visibility="visible";\r
697                         parent.editAreaLoader.add_event(resize, "mouseup", editArea.start_resize);\r
698                 }else{\r
699                         resize.style.visibility="hidden";\r
700                         parent.editAreaLoader.remove_event(resize, "mouseup", editArea.start_resize);\r
701                 }\r
702                 this.resize_allowed= allow;\r
703         };\r
704         \r
705         \r
706         EditArea.prototype.change_syntax= function(new_syntax, is_waiting){\r
707         //      alert("cahnge to "+new_syntax);\r
708                 // the syntax is the same\r
709                 if(new_syntax==this.settings['syntax'])\r
710                         return true;\r
711                 \r
712                 // check that the syntax is one allowed\r
713                 var founded= false;\r
714                 for(var i=0; i<this.syntax_list.length; i++)\r
715                 {\r
716                         if(this.syntax_list[i]==new_syntax)\r
717                                 founded= true;\r
718                 }\r
719                 \r
720                 if(founded==true)\r
721                 {\r
722                         // the reg syntax file is not loaded\r
723                         if(!parent.editAreaLoader.load_syntax[new_syntax])\r
724                         {\r
725                                 // load the syntax file and wait for file loading\r
726                                 if(!is_waiting)\r
727                                         parent.editAreaLoader.load_script(parent.editAreaLoader.baseURL + "reg_syntax/" + new_syntax + ".js");\r
728                                 setTimeout("editArea.change_syntax('"+ new_syntax +"', true);", 100);\r
729                                 this.show_waiting_screen();\r
730                         }\r
731                         else\r
732                         {\r
733                                 if(!this.allready_used_syntax[new_syntax])\r
734                                 {       // the syntax has still not been used\r
735                                         // rebuild syntax definition for new languages\r
736                                         parent.editAreaLoader.init_syntax_regexp();\r
737                                         // add style to the new list\r
738                                         this.add_style(parent.editAreaLoader.syntax[new_syntax]["styles"]);\r
739                                         this.allready_used_syntax[new_syntax]=true;\r
740                                 }\r
741                                 // be sure that the select option is correctly updated\r
742                                 var sel= _$("syntax_selection");\r
743                                 if(sel && sel.value!=new_syntax)\r
744                                 {\r
745                                         for(var i=0; i<sel.length; i++){\r
746                                                 if(sel.options[i].value && sel.options[i].value == new_syntax)\r
747                                                         sel.options[i].selected=true;\r
748                                         }\r
749                                 }\r
750                                 \r
751                         /*      if(this.settings['syntax'].length==0)\r
752                                 {\r
753                                         this.switchClassSticky(_$("highlight"), 'editAreaButtonNormal', false);\r
754                                         this.switchClassSticky(_$("reset_highlight"), 'editAreaButtonNormal', false);\r
755                                         this.change_highlight(true);\r
756                                 }\r
757                                 */\r
758                                 this.settings['syntax']= new_syntax;\r
759                                 this.resync_highlight(true);\r
760                                 this.hide_waiting_screen();\r
761                                 return true;\r
762                         }\r
763                 }\r
764                 return false;\r
765         };\r
766         \r
767         \r
768         // check if the file has changed\r
769         EditArea.prototype.set_editable= function(is_editable){\r
770                 if(is_editable)\r
771                 {\r
772                         document.body.className= "";\r
773                         this.textarea.readOnly= false;\r
774                         this.is_editable= true;\r
775                 }\r
776                 else\r
777                 {\r
778                         document.body.className= "non_editable";\r
779                         this.textarea.readOnly= true;\r
780                         this.is_editable= false;\r
781                 }\r
782                 \r
783                 if(editAreas[this.id]["displayed"]==true)\r
784                         this.update_size();\r
785         };\r
786         \r
787         /***** Wrap mode *****/\r
788         \r
789         // toggling function for set_wrap_mode\r
790         EditArea.prototype.toggle_word_wrap= function(){\r
791                 this.set_word_wrap( !this.settings['word_wrap'] );\r
792         };\r
793         \r
794         \r
795         // open a new tab for the given file\r
796         EditArea.prototype.set_word_wrap= function(to){\r
797                 var t=this, a= t.textarea;\r
798                 \r
799                 if( t.isOpera )\r
800                 {\r
801                         this.settings['word_wrap']= false;\r
802                         t.switchClassSticky( _$("word_wrap"), 'editAreaButtonDisabled', true );\r
803                         return false;\r
804                 }\r
805                 \r
806                 if( to )\r
807                 {\r
808                         wrap_mode = 'soft';\r
809                         this.container.className+= ' word_wrap';\r
810                         this.container.style.width="";\r
811                         this.content_highlight.style.width="";\r
812                         a.style.width="100%";\r
813                         if( t.isIE && t.isIE < 7 )      // IE 6 count 50 px too much\r
814                         {\r
815                                 a.style.width   = ( a.offsetWidth-5 )+"px";\r
816                         }\r
817                         \r
818                         t.switchClassSticky( _$("word_wrap"), 'editAreaButtonSelected', false );\r
819                 }\r
820                 else\r
821                 {\r
822                         wrap_mode = 'off';\r
823                         this.container.className        = this.container.className.replace(/word_wrap/g, '');\r
824                         t.switchClassSticky( _$("word_wrap"), 'editAreaButtonNormal', true );\r
825                 }\r
826                 this.textarea.previous_scrollWidth = '';\r
827                 this.textarea.previous_scrollHeight = '';\r
828                 \r
829                 a.wrap= wrap_mode;\r
830                 a.setAttribute('wrap', wrap_mode);\r
831                 // only IE can change wrap mode on the fly without element reloading\r
832                 if(!this.isIE)\r
833                 {\r
834                         var start=a.selectionStart, end= a.selectionEnd;\r
835                         var parNod = a.parentNode, nxtSib = a.nextSibling;\r
836                         parNod.removeChild(a);\r
837                         parNod.insertBefore(a, nxtSib);\r
838                         this.area_select(start, end-start);\r
839                 }\r
840                 // reset some optimisation\r
841                 this.settings['word_wrap']      = to;\r
842                 this.focus();\r
843                 this.update_size();\r
844                 this.check_line_selection();\r
845         };      \r
846         /***** tabbed files managing functions *****/\r
847         \r
848         // open a new tab for the given file\r
849         EditArea.prototype.open_file= function(settings){\r
850                 \r
851                 if(settings['id']!="undefined")\r
852                 {\r
853                         var id= settings['id'];\r
854                         // create a new file object with defautl values\r
855                         var new_file= {};\r
856                         new_file['id']                  = id;\r
857                         new_file['title']               = id;\r
858                         new_file['text']                = "";\r
859                         new_file['last_selection']      = "";           \r
860                         new_file['last_text_to_highlight']      = "";\r
861                         new_file['last_hightlighted_text']      = "";\r
862                         new_file['previous']    = [];\r
863                         new_file['next']                = [];\r
864                         new_file['last_undo']   = "";\r
865                         new_file['smooth_selection']    = this.settings['smooth_selection'];\r
866                         new_file['do_highlight']= this.settings['start_highlight'];\r
867                         new_file['syntax']              = this.settings['syntax'];\r
868                         new_file['scroll_top']  = 0;\r
869                         new_file['scroll_left'] = 0;\r
870                         new_file['selection_start']= 0;\r
871                         new_file['selection_end']= 0;\r
872                         new_file['edited']              = false;\r
873                         new_file['font_size']   = this.settings["font_size"];\r
874                         new_file['font_family'] = this.settings["font_family"];\r
875                         new_file['word_wrap']   = this.settings["word_wrap"];\r
876                         new_file['toolbar']             = {'links':{}, 'selects': {}};\r
877                         new_file['compare_edited_text']= new_file['text'];\r
878                         \r
879                         \r
880                         this.files[id]= new_file;\r
881                         this.update_file(id, settings);\r
882                         this.files[id]['compare_edited_text']= this.files[id]['text'];\r
883                         \r
884                         \r
885                         var html_id= 'tab_file_'+encodeURIComponent(id);\r
886                         this.filesIdAssoc[html_id]= id;\r
887                         this.files[id]['html_id']= html_id;\r
888                 \r
889                         if(!_$(this.files[id]['html_id']) && id!="")\r
890                         {\r
891                                 // be sure the tab browsing area is displayed\r
892                                 this.tab_browsing_area.style.display= "block";\r
893                                 var elem= document.createElement('li');\r
894                                 elem.id= this.files[id]['html_id'];\r
895                                 var close= "<img src=\""+ parent.editAreaLoader.baseURL +"images/close.gif\" title=\""+ this.get_translation('close_tab', 'word') +"\" onclick=\"editArea.execCommand('close_file', editArea.filesIdAssoc['"+ html_id +"']);return false;\" class=\"hidden\" onmouseover=\"this.className=''\" onmouseout=\"this.className='hidden'\" />";\r
896                                 elem.innerHTML= "<a onclick=\"javascript:editArea.execCommand('switch_to_file', editArea.filesIdAssoc['"+ html_id +"']);\" selec=\"none\"><b><span><strong class=\"edited\">*</strong>"+ this.files[id]['title'] + close +"</span></b></a>";\r
897                                 _$('tab_browsing_list').appendChild(elem);\r
898                                 var elem= document.createElement('text');\r
899                                 this.update_size();\r
900                         }\r
901                         \r
902                         // open file callback (for plugin)\r
903                         if(id!="")\r
904                                 this.execCommand('file_open', this.files[id]);\r
905                         \r
906                         this.switch_to_file(id, true);\r
907                         return true;\r
908                 }\r
909                 else\r
910                         return false;\r
911         };\r
912         \r
913         // close the given file\r
914         EditArea.prototype.close_file= function(id){\r
915                 if(this.files[id])\r
916                 {\r
917                         this.save_file(id);\r
918                         \r
919                         // close file callback\r
920                         if(this.execCommand('file_close', this.files[id])!==false)\r
921                         {\r
922                                 // remove the tab in the toolbar\r
923                                 var li= _$(this.files[id]['html_id']);\r
924                                 li.parentNode.removeChild(li);\r
925                                 // select a new file\r
926                                 if(id== this.curr_file)\r
927                                 {\r
928                                         var next_file= "";\r
929                                         var is_next= false;\r
930                                         for(var i in this.files)\r
931                                         {\r
932                                                 if( is_next )\r
933                                                 {\r
934                                                         next_file       = i;\r
935                                                         break;\r
936                                                 }\r
937                                                 else if( i == id )\r
938                                                         is_next         = true;\r
939                                                 else\r
940                                                         next_file       = i;\r
941                                         }\r
942                                         // display the next file\r
943                                         this.switch_to_file(next_file);\r
944                                 }\r
945                                 // clear datas\r
946                                 delete (this.files[id]);\r
947                                 this.update_size();\r
948                         }       \r
949                 }\r
950         };\r
951         \r
952         // backup current file datas\r
953         EditArea.prototype.save_file= function(id){\r
954                 var t= this, save, a_links, a_selects, save_butt, img, i;\r
955                 if(t.files[id])\r
956                 {\r
957                         var save= t.files[id];\r
958                         save['last_selection']                  = t.last_selection;             \r
959                         save['last_text_to_highlight']  = t.last_text_to_highlight;\r
960                         save['last_hightlighted_text']  = t.last_hightlighted_text;\r
961                         save['previous']                                = t.previous;\r
962                         save['next']                                    = t.next;\r
963                         save['last_undo']                               = t.last_undo;\r
964                         save['smooth_selection']                = t.smooth_selection;\r
965                         save['do_highlight']                    = t.do_highlight;\r
966                         save['syntax']                                  = t.settings['syntax'];\r
967                         save['text']                                    = t.textarea.value;\r
968                         save['scroll_top']                              = t.result.scrollTop;\r
969                         save['scroll_left']                             = t.result.scrollLeft;\r
970                         save['selection_start']                 = t.last_selection["selectionStart"];\r
971                         save['selection_end']                   = t.last_selection["selectionEnd"];\r
972                         save['font_size']                               = t.settings["font_size"];\r
973                         save['font_family']                             = t.settings["font_family"];\r
974                         save['word_wrap']                               = t.settings["word_wrap"];\r
975                         save['toolbar']                                 = {'links':{}, 'selects': {}};\r
976                         \r
977                         // save toolbar buttons state for fileSpecific buttons\r
978                         a_links= _$("toolbar_1").getElementsByTagName("a");\r
979                         for( i=0; i<a_links.length; i++ )\r
980                         {\r
981                                 if( a_links[i].getAttribute('fileSpecific') == 'yes' )\r
982                                 {\r
983                                         save_butt       = {};\r
984                                         img                     = a_links[i].getElementsByTagName('img')[0];\r
985                                         save_butt['classLock']          = img.classLock;\r
986                                         save_butt['className']          = img.className;\r
987                                         save_butt['oldClassName']       = img.oldClassName;\r
988                                         \r
989                                         save['toolbar']['links'][a_links[i].id]= save_butt;\r
990                                 }\r
991                         }\r
992                         \r
993                         // save toolbar select state for fileSpecific buttons\r
994                         a_selects= _$("toolbar_1").getElementsByTagName("select");\r
995                         for( i=0; i<a_selects.length; i++)\r
996                         {\r
997                                 if(a_selects[i].getAttribute('fileSpecific')=='yes')\r
998                                 {\r
999                                         save['toolbar']['selects'][a_selects[i].id]= a_selects[i].value;\r
1000                                 }\r
1001                         }\r
1002                                 \r
1003                         t.files[id]= save;\r
1004                         \r
1005                         return save;\r
1006                 }\r
1007                 \r
1008                 return false;\r
1009         };\r
1010         \r
1011         // update file_datas\r
1012         EditArea.prototype.update_file= function(id, new_values){\r
1013                 for(var i in new_values)\r
1014                 {\r
1015                         this.files[id][i]= new_values[i];\r
1016                 }\r
1017         };\r
1018         \r
1019         // display file datas\r
1020         EditArea.prototype.display_file= function(id){\r
1021                 var t = this, a= t.textarea, new_file, a_lis, a_selects, a_links, a_options, i, j;\r
1022                 \r
1023                 // we're showing the empty file\r
1024                 if(id=='')\r
1025                 {\r
1026                         a.readOnly= true;\r
1027                         t.tab_browsing_area.style.display= "none";\r
1028                         _$("no_file_selected").style.display= "block";\r
1029                         t.result.className= "empty";\r
1030                         // clear current datas\r
1031                         if(!t.files[''])\r
1032                         {\r
1033                                 t.open_file({id: ''});\r
1034                         }\r
1035                 }\r
1036                 // we try to show a non existent file, so we left\r
1037                 else if( typeof( t.files[id] ) == 'undefined' )\r
1038                 {\r
1039                         return false;\r
1040                 }\r
1041                 // display a normal file\r
1042                 else\r
1043                 {\r
1044                         t.result.className= "";\r
1045                         a.readOnly= !t.is_editable;\r
1046                         _$("no_file_selected").style.display= "none";\r
1047                         t.tab_browsing_area.style.display= "block";\r
1048                 }\r
1049                 \r
1050                 // ensure to have last state for undo/redo actions\r
1051                 t.check_redo(true);\r
1052                 t.check_undo(true);\r
1053                 t.curr_file= id;\r
1054                 \r
1055                 // replace selected tab file\r
1056                 a_lis= t.tab_browsing_area.getElementsByTagName('li');\r
1057                 for( i=0; i<a_lis.length; i++)\r
1058                 {\r
1059                         if(a_lis[i].id == t.files[id]['html_id'])\r
1060                                 a_lis[i].className='selected';\r
1061                         else\r
1062                                 a_lis[i].className='';\r
1063                 }\r
1064                 \r
1065                 // replace next files datas\r
1066                 new_file= t.files[id];\r
1067         \r
1068                 // restore text content\r
1069                 a.value= new_file['text'];\r
1070                 \r
1071                 // restore font-size\r
1072                 t.set_font(new_file['font_family'], new_file['font_size']);\r
1073                 \r
1074                 // restore selection and scroll\r
1075                 t.area_select(new_file['last_selection']['selection_start'], new_file['last_selection']['selection_end'] - new_file['last_selection']['selection_start']);\r
1076                 t.manage_size(true);\r
1077                 t.result.scrollTop= new_file['scroll_top'];\r
1078                 t.result.scrollLeft= new_file['scroll_left'];\r
1079                 \r
1080                 // restore undo, redo\r
1081                 t.previous=     new_file['previous'];\r
1082                 t.next= new_file['next'];\r
1083                 t.last_undo=    new_file['last_undo'];\r
1084                 t.check_redo(true);\r
1085                 t.check_undo(true);\r
1086                 \r
1087                 // restore highlight\r
1088                 t.execCommand("change_highlight", new_file['do_highlight']);\r
1089                 t.execCommand("change_syntax", new_file['syntax']);\r
1090                 \r
1091                 // smooth mode\r
1092                 t.execCommand("change_smooth_selection_mode", new_file['smooth_selection']);\r
1093                 \r
1094                 // word_wrap\r
1095                 t.execCommand("set_word_wrap", new_file['word_wrap']);\r
1096                         \r
1097                 // restore links state in toolbar\r
1098                 a_links= new_file['toolbar']['links'];\r
1099                 for( i in a_links)\r
1100                 {\r
1101                         if( img =  _$(i).getElementsByTagName('img')[0] )\r
1102                         {\r
1103                                 img.classLock   = a_links[i]['classLock'];\r
1104                                 img.className   = a_links[i]['className'];\r
1105                                 img.oldClassName= a_links[i]['oldClassName'];\r
1106                         }\r
1107                 }\r
1108                 \r
1109                 // restore select state in toolbar\r
1110                 a_selects = new_file['toolbar']['selects'];\r
1111                 for( i in a_selects)\r
1112                 {\r
1113                         a_options       = _$(i).options;\r
1114                         for( j=0; j<a_options.length; j++)\r
1115                         {\r
1116                                 if( a_options[j].value == a_selects[i] )\r
1117                                         _$(i).options[j].selected=true;\r
1118                         }\r
1119                 }\r
1120         \r
1121         };\r
1122 \r
1123         // change tab for displaying a new one\r
1124         EditArea.prototype.switch_to_file= function(file_to_show, force_refresh){\r
1125                 if(file_to_show!=this.curr_file || force_refresh)\r
1126                 {\r
1127                         this.save_file(this.curr_file);\r
1128                         if(this.curr_file!='')\r
1129                                 this.execCommand('file_switch_off', this.files[this.curr_file]);\r
1130                         this.display_file(file_to_show);\r
1131                         if(file_to_show!='')\r
1132                                 this.execCommand('file_switch_on', this.files[file_to_show]);\r
1133                 }\r
1134         };\r
1135 \r
1136         // get all infos for the given file\r
1137         EditArea.prototype.get_file= function(id){\r
1138                 if(id==this.curr_file)\r
1139                         this.save_file(id);\r
1140                 return this.files[id];\r
1141         };\r
1142         \r
1143         // get all available files infos\r
1144         EditArea.prototype.get_all_files= function(){\r
1145                 tmp_files= this.files;\r
1146                 this.save_file(this.curr_file);\r
1147                 if(tmp_files[''])\r
1148                         delete(this.files['']);\r
1149                 return tmp_files;\r
1150         };\r
1151         \r
1152         \r
1153         // check if the file has changed\r
1154         EditArea.prototype.check_file_changes= function(){\r
1155         \r
1156                 var id= this.curr_file;\r
1157                 if(this.files[id] && this.files[id]['compare_edited_text']!=undefined)\r
1158                 {\r
1159                         if(this.files[id]['compare_edited_text'].length==this.textarea.value.length && this.files[id]['compare_edited_text']==this.textarea.value)\r
1160                         {\r
1161                                 if(this.files[id]['edited']!= false)\r
1162                                         this.set_file_edited_mode(id, false);\r
1163                         }\r
1164                         else\r
1165                         {\r
1166                                 if(this.files[id]['edited']!= true)\r
1167                                         this.set_file_edited_mode(id, true);\r
1168                         }\r
1169                 }\r
1170         };\r
1171         \r
1172         // set if the file is edited or not\r
1173         EditArea.prototype.set_file_edited_mode= function(id, to){\r
1174                 // change CSS for edited tab\r
1175                 if(this.files[id] && _$(this.files[id]['html_id']))\r
1176                 {\r
1177                         var link= _$(this.files[id]['html_id']).getElementsByTagName('a')[0];\r
1178                         if(to==true)\r
1179                         {\r
1180                                 link.className= 'edited';\r
1181                         }\r
1182                         else\r
1183                         {\r
1184                                 link.className= '';\r
1185                                 if(id==this.curr_file)\r
1186                                         text= this.textarea.value;\r
1187                                 else\r
1188                                         text= this.files[id]['text'];\r
1189                                 this.files[id]['compare_edited_text']= text;\r
1190                         }\r
1191                                 \r
1192                         this.files[id]['edited']= to;\r
1193                 }\r
1194         };\r
1195 \r
1196         EditArea.prototype.set_show_line_colors = function(new_value){\r
1197                 this.show_line_colors = new_value;\r
1198                 \r
1199                 if( new_value )\r
1200                         this.selection_field.className  += ' show_colors';\r
1201                 else\r
1202                         this.selection_field.className  = this.selection_field.className.replace( / show_colors/g, '' );\r
1203         };