editarea-rails 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE.txt +22 -0
- data/README.md +31 -0
- data/lib/editarea-rails.rb +8 -0
- data/lib/editarea-rails/version.rb +5 -0
- data/vendor/assets/images/autocompletion.gif +0 -0
- data/vendor/assets/images/close.gif +0 -0
- data/vendor/assets/images/fullscreen.gif +0 -0
- data/vendor/assets/images/go_to_line.gif +0 -0
- data/vendor/assets/images/help.gif +0 -0
- data/vendor/assets/images/highlight.gif +0 -0
- data/vendor/assets/images/load.gif +0 -0
- data/vendor/assets/images/move.gif +0 -0
- data/vendor/assets/images/newdocument.gif +0 -0
- data/vendor/assets/images/opacity.png +0 -0
- data/vendor/assets/images/plugins/charmap/charmap.gif +0 -0
- data/vendor/assets/images/plugins/test/css/test.css +3 -0
- data/vendor/assets/images/plugins/test/images/Thumbs.db +0 -0
- data/vendor/assets/images/plugins/test/images/test.gif +0 -0
- data/vendor/assets/images/plugins/test/langs/bg.js +10 -0
- data/vendor/assets/images/plugins/test/langs/cs.js +4 -0
- data/vendor/assets/images/plugins/test/langs/de.js +4 -0
- data/vendor/assets/images/plugins/test/langs/dk.js +4 -0
- data/vendor/assets/images/plugins/test/langs/en.js +4 -0
- data/vendor/assets/images/plugins/test/langs/eo.js +4 -0
- data/vendor/assets/images/plugins/test/langs/es.js +4 -0
- data/vendor/assets/images/plugins/test/langs/fr.js +4 -0
- data/vendor/assets/images/plugins/test/langs/hr.js +4 -0
- data/vendor/assets/images/plugins/test/langs/it.js +4 -0
- data/vendor/assets/images/plugins/test/langs/ja.js +4 -0
- data/vendor/assets/images/plugins/test/langs/mk.js +4 -0
- data/vendor/assets/images/plugins/test/langs/nl.js +4 -0
- data/vendor/assets/images/plugins/test/langs/pl.js +4 -0
- data/vendor/assets/images/plugins/test/langs/pt.js +4 -0
- data/vendor/assets/images/plugins/test/langs/ru.js +4 -0
- data/vendor/assets/images/plugins/test/langs/sk.js +4 -0
- data/vendor/assets/images/plugins/test/langs/zh.js +4 -0
- data/vendor/assets/images/plugins/test/test.js +110 -0
- data/vendor/assets/images/plugins/test/test2.js +1 -0
- data/vendor/assets/images/processing.gif +0 -0
- data/vendor/assets/images/redo.gif +0 -0
- data/vendor/assets/images/reset_highlight.gif +0 -0
- data/vendor/assets/images/save.gif +0 -0
- data/vendor/assets/images/search.gif +0 -0
- data/vendor/assets/images/smooth_selection.gif +0 -0
- data/vendor/assets/images/spacer.gif +0 -0
- data/vendor/assets/images/statusbar_resize.gif +0 -0
- data/vendor/assets/images/undo.gif +0 -0
- data/vendor/assets/images/word_wrap.gif +0 -0
- data/vendor/assets/javascripts/autocompletion.js +491 -0
- data/vendor/assets/javascripts/edit_area.js +527 -0
- data/vendor/assets/javascripts/edit_area_full.js +38 -0
- data/vendor/assets/javascripts/edit_area_functions.js +1202 -0
- data/vendor/assets/javascripts/edit_area_loader.js +1081 -0
- data/vendor/assets/javascripts/elements_functions.js +336 -0
- data/vendor/assets/javascripts/highlight.js +407 -0
- data/vendor/assets/javascripts/keyboard.js +145 -0
- data/vendor/assets/javascripts/langs/bg.js +54 -0
- data/vendor/assets/javascripts/langs/cs.js +48 -0
- data/vendor/assets/javascripts/langs/de.js +48 -0
- data/vendor/assets/javascripts/langs/dk.js +48 -0
- data/vendor/assets/javascripts/langs/en.js +48 -0
- data/vendor/assets/javascripts/langs/eo.js +48 -0
- data/vendor/assets/javascripts/langs/es.js +48 -0
- data/vendor/assets/javascripts/langs/fi.js +48 -0
- data/vendor/assets/javascripts/langs/fr.js +48 -0
- data/vendor/assets/javascripts/langs/hr.js +48 -0
- data/vendor/assets/javascripts/langs/it.js +48 -0
- data/vendor/assets/javascripts/langs/ja.js +48 -0
- data/vendor/assets/javascripts/langs/mk.js +48 -0
- data/vendor/assets/javascripts/langs/nl.js +48 -0
- data/vendor/assets/javascripts/langs/pl.js +48 -0
- data/vendor/assets/javascripts/langs/pt.js +48 -0
- data/vendor/assets/javascripts/langs/ru.js +48 -0
- data/vendor/assets/javascripts/langs/sk.js +48 -0
- data/vendor/assets/javascripts/langs/zh.js +48 -0
- data/vendor/assets/javascripts/manage_area.js +623 -0
- data/vendor/assets/javascripts/plugins/charmap/charmap.js +90 -0
- data/vendor/assets/javascripts/plugins/charmap/jscripts/map.js +373 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/bg.js +12 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/cs.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/de.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/dk.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/en.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/eo.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/es.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/fr.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/hr.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/it.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/ja.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/mk.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/nl.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/pl.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/pt.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/ru.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/sk.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/langs/zh.js +6 -0
- data/vendor/assets/javascripts/plugins/charmap/popup.html +24 -0
- data/vendor/assets/javascripts/plugins/test/langs/bg.js +10 -0
- data/vendor/assets/javascripts/plugins/test/langs/cs.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/de.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/dk.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/en.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/eo.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/es.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/fr.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/hr.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/it.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/ja.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/mk.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/nl.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/pl.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/pt.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/ru.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/sk.js +4 -0
- data/vendor/assets/javascripts/plugins/test/langs/zh.js +4 -0
- data/vendor/assets/javascripts/plugins/test/test.js +110 -0
- data/vendor/assets/javascripts/plugins/test/test2.js +1 -0
- data/vendor/assets/javascripts/reg_syntax.js +166 -0
- data/vendor/assets/javascripts/reg_syntax/basic.js +70 -0
- data/vendor/assets/javascripts/reg_syntax/brainfuck.js +45 -0
- data/vendor/assets/javascripts/reg_syntax/c.js +63 -0
- data/vendor/assets/javascripts/reg_syntax/coldfusion.js +120 -0
- data/vendor/assets/javascripts/reg_syntax/cpp.js +66 -0
- data/vendor/assets/javascripts/reg_syntax/css.js +85 -0
- data/vendor/assets/javascripts/reg_syntax/html.js +51 -0
- data/vendor/assets/javascripts/reg_syntax/java.js +57 -0
- data/vendor/assets/javascripts/reg_syntax/js.js +94 -0
- data/vendor/assets/javascripts/reg_syntax/pas.js +83 -0
- data/vendor/assets/javascripts/reg_syntax/perl.js +88 -0
- data/vendor/assets/javascripts/reg_syntax/php.js +157 -0
- data/vendor/assets/javascripts/reg_syntax/python.js +145 -0
- data/vendor/assets/javascripts/reg_syntax/robotstxt.js +25 -0
- data/vendor/assets/javascripts/reg_syntax/ruby.js +68 -0
- data/vendor/assets/javascripts/reg_syntax/sql.js +56 -0
- data/vendor/assets/javascripts/reg_syntax/tsql.js +88 -0
- data/vendor/assets/javascripts/reg_syntax/vb.js +53 -0
- data/vendor/assets/javascripts/reg_syntax/xml.js +57 -0
- data/vendor/assets/javascripts/regexp.js +139 -0
- data/vendor/assets/javascripts/resize_area.js +73 -0
- data/vendor/assets/javascripts/search_replace.js +174 -0
- data/vendor/assets/stylesheets/edit_area.css +530 -0
- data/vendor/assets/stylesheets/plugins/charmap/css/charmap.css +64 -0
- data/vendor/assets/stylesheets/plugins/test/css/test.css +3 -0
- metadata +210 -0
data/LICENSE.txt
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
Copyright (c) 2013 Jun
|
2
|
+
|
3
|
+
MIT License
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
a copy of this software and associated documentation files (the
|
7
|
+
"Software"), to deal in the Software without restriction, including
|
8
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
the following conditions:
|
12
|
+
|
13
|
+
The above copyright notice and this permission notice shall be
|
14
|
+
included in all copies or substantial portions of the Software.
|
15
|
+
|
16
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
18
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
# Editarea::Rails
|
2
|
+
|
3
|
+
Gem for editarea
|
4
|
+
|
5
|
+
|
6
|
+
## Installation
|
7
|
+
|
8
|
+
Add this line to your application's Gemfile:
|
9
|
+
|
10
|
+
gem 'editarea-rails'
|
11
|
+
|
12
|
+
And then execute:
|
13
|
+
|
14
|
+
$ bundle
|
15
|
+
|
16
|
+
Or install it yourself as:
|
17
|
+
|
18
|
+
$ gem install editarea-rails
|
19
|
+
|
20
|
+
## Usage
|
21
|
+
|
22
|
+
//= require edit_area_full
|
23
|
+
|
24
|
+
|
25
|
+
## Contributing
|
26
|
+
|
27
|
+
1. Fork it
|
28
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
29
|
+
3. Commit your changes (`git commit -am 'Add some feature'`)
|
30
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
31
|
+
5. Create new Pull Request
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
@@ -0,0 +1,110 @@
|
|
1
|
+
/**
|
2
|
+
* Plugin designed for test prupose. It add a button (that manage an alert) and a select (that allow to insert tags) in the toolbar.
|
3
|
+
* This plugin also disable the "f" key in the editarea, and load a CSS and a JS file
|
4
|
+
*/
|
5
|
+
var EditArea_test= {
|
6
|
+
/**
|
7
|
+
* Get called once this file is loaded (editArea still not initialized)
|
8
|
+
*
|
9
|
+
* @return nothing
|
10
|
+
*/
|
11
|
+
init: function(){
|
12
|
+
// alert("test init: "+ this._someInternalFunction(2, 3));
|
13
|
+
editArea.load_css(this.baseURL+"css/test.css");
|
14
|
+
editArea.load_script(this.baseURL+"test2.js");
|
15
|
+
}
|
16
|
+
/**
|
17
|
+
* Returns the HTML code for a specific control string or false if this plugin doesn't have that control.
|
18
|
+
* A control can be a button, select list or any other HTML item to present in the EditArea user interface.
|
19
|
+
* Language variables such as {$lang_somekey} will also be replaced with contents from
|
20
|
+
* the language packs.
|
21
|
+
*
|
22
|
+
* @param {string} ctrl_name: the name of the control to add
|
23
|
+
* @return HTML code for a specific control or false.
|
24
|
+
* @type string or boolean
|
25
|
+
*/
|
26
|
+
,get_control_html: function(ctrl_name){
|
27
|
+
switch(ctrl_name){
|
28
|
+
case "test_but":
|
29
|
+
// Control id, button img, command
|
30
|
+
return parent.editAreaLoader.get_button_html('test_but', 'test.gif', 'test_cmd', false, this.baseURL);
|
31
|
+
case "test_select":
|
32
|
+
html= "<select id='test_select' onchange='javascript:editArea.execCommand(\"test_select_change\")' fileSpecific='no'>"
|
33
|
+
+" <option value='-1'>{$test_select}</option>"
|
34
|
+
+" <option value='h1'>h1</option>"
|
35
|
+
+" <option value='h2'>h2</option>"
|
36
|
+
+" <option value='h3'>h3</option>"
|
37
|
+
+" <option value='h4'>h4</option>"
|
38
|
+
+" <option value='h5'>h5</option>"
|
39
|
+
+" <option value='h6'>h6</option>"
|
40
|
+
+" </select>";
|
41
|
+
return html;
|
42
|
+
}
|
43
|
+
return false;
|
44
|
+
}
|
45
|
+
/**
|
46
|
+
* Get called once EditArea is fully loaded and initialised
|
47
|
+
*
|
48
|
+
* @return nothing
|
49
|
+
*/
|
50
|
+
,onload: function(){
|
51
|
+
alert("test load");
|
52
|
+
}
|
53
|
+
|
54
|
+
/**
|
55
|
+
* Is called each time the user touch a keyboard key.
|
56
|
+
*
|
57
|
+
* @param (event) e: the keydown event
|
58
|
+
* @return true - pass to next handler in chain, false - stop chain execution
|
59
|
+
* @type boolean
|
60
|
+
*/
|
61
|
+
,onkeydown: function(e){
|
62
|
+
var str= String.fromCharCode(e.keyCode);
|
63
|
+
// desactivate the "f" character
|
64
|
+
if(str.toLowerCase()=="f"){
|
65
|
+
return true;
|
66
|
+
}
|
67
|
+
return false;
|
68
|
+
}
|
69
|
+
|
70
|
+
/**
|
71
|
+
* Executes a specific command, this function handles plugin commands.
|
72
|
+
*
|
73
|
+
* @param {string} cmd: the name of the command being executed
|
74
|
+
* @param {unknown} param: the parameter of the command
|
75
|
+
* @return true - pass to next handler in chain, false - stop chain execution
|
76
|
+
* @type boolean
|
77
|
+
*/
|
78
|
+
,execCommand: function(cmd, param){
|
79
|
+
// Handle commands
|
80
|
+
switch(cmd){
|
81
|
+
case "test_select_change":
|
82
|
+
var val= document.getElementById("test_select").value;
|
83
|
+
if(val!=-1)
|
84
|
+
parent.editAreaLoader.insertTags(editArea.id, "<"+val+">", "</"+val+">");
|
85
|
+
document.getElementById("test_select").options[0].selected=true;
|
86
|
+
return false;
|
87
|
+
case "test_cmd":
|
88
|
+
alert("user clicked on test_cmd");
|
89
|
+
return false;
|
90
|
+
}
|
91
|
+
// Pass to next handler in chain
|
92
|
+
return true;
|
93
|
+
}
|
94
|
+
|
95
|
+
/**
|
96
|
+
* This is just an internal plugin method, prefix all internal methods with a _ character.
|
97
|
+
* The prefix is needed so they doesn't collide with future EditArea callback functions.
|
98
|
+
*
|
99
|
+
* @param {string} a Some arg1.
|
100
|
+
* @param {string} b Some arg2.
|
101
|
+
* @return Some return.
|
102
|
+
* @type unknown
|
103
|
+
*/
|
104
|
+
,_someInternalFunction : function(a, b) {
|
105
|
+
return a+b;
|
106
|
+
}
|
107
|
+
};
|
108
|
+
|
109
|
+
// Adds the plugin class to the list of available EditArea plugins
|
110
|
+
editArea.add_plugin("test", EditArea_test);
|
@@ -0,0 +1 @@
|
|
1
|
+
alert("test2.js is loaded from test plugin");
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
@@ -0,0 +1,491 @@
|
|
1
|
+
/**
|
2
|
+
* Autocompletion class
|
3
|
+
*
|
4
|
+
* An auto completion box appear while you're writing. It's possible to force it to appear with Ctrl+Space short cut
|
5
|
+
*
|
6
|
+
* Loaded as a plugin inside editArea (everything made here could have been made in the plugin directory)
|
7
|
+
* But is definitly linked to syntax selection (no need to do 2 different files for color and auto complete for each syntax language)
|
8
|
+
* and add a too important feature that many people would miss if included as a plugin
|
9
|
+
*
|
10
|
+
* - init param: autocompletion_start
|
11
|
+
* - Button name: "autocompletion"
|
12
|
+
*/
|
13
|
+
|
14
|
+
var EditArea_autocompletion= {
|
15
|
+
|
16
|
+
/**
|
17
|
+
* Get called once this file is loaded (editArea still not initialized)
|
18
|
+
*
|
19
|
+
* @return nothing
|
20
|
+
*/
|
21
|
+
init: function(){
|
22
|
+
// alert("test init: "+ this._someInternalFunction(2, 3));
|
23
|
+
|
24
|
+
if(editArea.settings["autocompletion"])
|
25
|
+
this.enabled= true;
|
26
|
+
else
|
27
|
+
this.enabled= false;
|
28
|
+
this.current_word = false;
|
29
|
+
this.shown = false;
|
30
|
+
this.selectIndex = -1;
|
31
|
+
this.forceDisplay = false;
|
32
|
+
this.isInMiddleWord = false;
|
33
|
+
this.autoSelectIfOneResult = false;
|
34
|
+
this.delayBeforeDisplay = 100;
|
35
|
+
this.checkDelayTimer = false;
|
36
|
+
this.curr_syntax_str = '';
|
37
|
+
|
38
|
+
this.file_syntax_datas = {};
|
39
|
+
}
|
40
|
+
/**
|
41
|
+
* Returns the HTML code for a specific control string or false if this plugin doesn't have that control.
|
42
|
+
* A control can be a button, select list or any other HTML item to present in the EditArea user interface.
|
43
|
+
* Language variables such as {$lang_somekey} will also be replaced with contents from
|
44
|
+
* the language packs.
|
45
|
+
*
|
46
|
+
* @param {string} ctrl_name: the name of the control to add
|
47
|
+
* @return HTML code for a specific control or false.
|
48
|
+
* @type string or boolean
|
49
|
+
*/
|
50
|
+
/*,get_control_html: function(ctrl_name){
|
51
|
+
switch( ctrl_name ){
|
52
|
+
case 'autocompletion':
|
53
|
+
// Control id, button img, command
|
54
|
+
return parent.editAreaLoader.get_button_html('autocompletion_but', 'autocompletion.gif', 'toggle_autocompletion', false, this.baseURL);
|
55
|
+
break;
|
56
|
+
}
|
57
|
+
return false;
|
58
|
+
}*/
|
59
|
+
/**
|
60
|
+
* Get called once EditArea is fully loaded and initialised
|
61
|
+
*
|
62
|
+
* @return nothing
|
63
|
+
*/
|
64
|
+
,onload: function(){
|
65
|
+
if(this.enabled)
|
66
|
+
{
|
67
|
+
var icon= document.getElementById("autocompletion");
|
68
|
+
if(icon)
|
69
|
+
editArea.switchClassSticky(icon, 'editAreaButtonSelected', true);
|
70
|
+
}
|
71
|
+
|
72
|
+
this.container = document.createElement('div');
|
73
|
+
this.container.id = "auto_completion_area";
|
74
|
+
editArea.container.insertBefore( this.container, editArea.container.firstChild );
|
75
|
+
|
76
|
+
// add event detection for hiding suggestion box
|
77
|
+
parent.editAreaLoader.add_event( document, "click", function(){ editArea.plugins['autocompletion']._hide();} );
|
78
|
+
parent.editAreaLoader.add_event( editArea.textarea, "blur", function(){ editArea.plugins['autocompletion']._hide();} );
|
79
|
+
|
80
|
+
}
|
81
|
+
|
82
|
+
/**
|
83
|
+
* Is called each time the user touch a keyboard key.
|
84
|
+
*
|
85
|
+
* @param (event) e: the keydown event
|
86
|
+
* @return true - pass to next handler in chain, false - stop chain execution
|
87
|
+
* @type boolean
|
88
|
+
*/
|
89
|
+
,onkeydown: function(e){
|
90
|
+
if(!this.enabled)
|
91
|
+
return true;
|
92
|
+
|
93
|
+
if (EA_keys[e.keyCode])
|
94
|
+
letter=EA_keys[e.keyCode];
|
95
|
+
else
|
96
|
+
letter=String.fromCharCode(e.keyCode);
|
97
|
+
// shown
|
98
|
+
if( this._isShown() )
|
99
|
+
{
|
100
|
+
// if escape, hide the box
|
101
|
+
if(letter=="Esc")
|
102
|
+
{
|
103
|
+
this._hide();
|
104
|
+
return false;
|
105
|
+
}
|
106
|
+
// Enter
|
107
|
+
else if( letter=="Entrer")
|
108
|
+
{
|
109
|
+
var as = this.container.getElementsByTagName('A');
|
110
|
+
// select a suggested entry
|
111
|
+
if( this.selectIndex >= 0 && this.selectIndex < as.length )
|
112
|
+
{
|
113
|
+
as[ this.selectIndex ].onmousedown();
|
114
|
+
return false
|
115
|
+
}
|
116
|
+
// simply add an enter in the code
|
117
|
+
else
|
118
|
+
{
|
119
|
+
this._hide();
|
120
|
+
return true;
|
121
|
+
}
|
122
|
+
}
|
123
|
+
else if( letter=="Tab" || letter=="Down")
|
124
|
+
{
|
125
|
+
this._selectNext();
|
126
|
+
return false;
|
127
|
+
}
|
128
|
+
else if( letter=="Up")
|
129
|
+
{
|
130
|
+
this._selectBefore();
|
131
|
+
return false;
|
132
|
+
}
|
133
|
+
}
|
134
|
+
// hidden
|
135
|
+
else
|
136
|
+
{
|
137
|
+
|
138
|
+
}
|
139
|
+
|
140
|
+
// show current suggestion list and do autoSelect if possible (no matter it's shown or hidden)
|
141
|
+
if( letter=="Space" && CtrlPressed(e) )
|
142
|
+
{
|
143
|
+
//parent.console.log('SHOW SUGGEST');
|
144
|
+
this.forceDisplay = true;
|
145
|
+
this.autoSelectIfOneResult = true;
|
146
|
+
this._checkLetter();
|
147
|
+
return false;
|
148
|
+
}
|
149
|
+
|
150
|
+
// wait a short period for check that the cursor isn't moving
|
151
|
+
setTimeout("editArea.plugins['autocompletion']._checkDelayAndCursorBeforeDisplay();", editArea.check_line_selection_timer +5 );
|
152
|
+
this.checkDelayTimer = false;
|
153
|
+
return true;
|
154
|
+
}
|
155
|
+
/**
|
156
|
+
* Executes a specific command, this function handles plugin commands.
|
157
|
+
*
|
158
|
+
* @param {string} cmd: the name of the command being executed
|
159
|
+
* @param {unknown} param: the parameter of the command
|
160
|
+
* @return true - pass to next handler in chain, false - stop chain execution
|
161
|
+
* @type boolean
|
162
|
+
*/
|
163
|
+
,execCommand: function(cmd, param){
|
164
|
+
switch( cmd ){
|
165
|
+
case 'toggle_autocompletion':
|
166
|
+
var icon= document.getElementById("autocompletion");
|
167
|
+
if(!this.enabled)
|
168
|
+
{
|
169
|
+
if(icon != null){
|
170
|
+
editArea.restoreClass(icon);
|
171
|
+
editArea.switchClassSticky(icon, 'editAreaButtonSelected', true);
|
172
|
+
}
|
173
|
+
this.enabled= true;
|
174
|
+
}
|
175
|
+
else
|
176
|
+
{
|
177
|
+
this.enabled= false;
|
178
|
+
if(icon != null)
|
179
|
+
editArea.switchClassSticky(icon, 'editAreaButtonNormal', false);
|
180
|
+
}
|
181
|
+
return true;
|
182
|
+
}
|
183
|
+
return true;
|
184
|
+
}
|
185
|
+
,_checkDelayAndCursorBeforeDisplay: function()
|
186
|
+
{
|
187
|
+
this.checkDelayTimer = setTimeout("if(editArea.textarea.selectionStart == "+ editArea.textarea.selectionStart +") EditArea_autocompletion._checkLetter();", this.delayBeforeDisplay - editArea.check_line_selection_timer - 5 );
|
188
|
+
}
|
189
|
+
// hide the suggested box
|
190
|
+
,_hide: function(){
|
191
|
+
this.container.style.display="none";
|
192
|
+
this.selectIndex = -1;
|
193
|
+
this.shown = false;
|
194
|
+
this.forceDisplay = false;
|
195
|
+
this.autoSelectIfOneResult = false;
|
196
|
+
}
|
197
|
+
// display the suggested box
|
198
|
+
,_show: function(){
|
199
|
+
if( !this._isShown() )
|
200
|
+
{
|
201
|
+
this.container.style.display="block";
|
202
|
+
this.selectIndex = -1;
|
203
|
+
this.shown = true;
|
204
|
+
}
|
205
|
+
}
|
206
|
+
// is the suggested box displayed?
|
207
|
+
,_isShown: function(){
|
208
|
+
return this.shown;
|
209
|
+
}
|
210
|
+
// setter and getter
|
211
|
+
,_isInMiddleWord: function( new_value ){
|
212
|
+
if( typeof( new_value ) == "undefined" )
|
213
|
+
return this.isInMiddleWord;
|
214
|
+
else
|
215
|
+
this.isInMiddleWord = new_value;
|
216
|
+
}
|
217
|
+
// select the next element in the suggested box
|
218
|
+
,_selectNext: function()
|
219
|
+
{
|
220
|
+
var as = this.container.getElementsByTagName('A');
|
221
|
+
|
222
|
+
// clean existing elements
|
223
|
+
for( var i=0; i<as.length; i++ )
|
224
|
+
{
|
225
|
+
if( as[i].className )
|
226
|
+
as[i].className = as[i].className.replace(/ focus/g, '');
|
227
|
+
}
|
228
|
+
|
229
|
+
this.selectIndex++;
|
230
|
+
this.selectIndex = ( this.selectIndex >= as.length || this.selectIndex < 0 ) ? 0 : this.selectIndex;
|
231
|
+
as[ this.selectIndex ].className += " focus";
|
232
|
+
}
|
233
|
+
// select the previous element in the suggested box
|
234
|
+
,_selectBefore: function()
|
235
|
+
{
|
236
|
+
var as = this.container.getElementsByTagName('A');
|
237
|
+
|
238
|
+
// clean existing elements
|
239
|
+
for( var i=0; i<as.length; i++ )
|
240
|
+
{
|
241
|
+
if( as[i].className )
|
242
|
+
as[i].className = as[ i ].className.replace(/ focus/g, '');
|
243
|
+
}
|
244
|
+
|
245
|
+
this.selectIndex--;
|
246
|
+
|
247
|
+
this.selectIndex = ( this.selectIndex >= as.length || this.selectIndex < 0 ) ? as.length-1 : this.selectIndex;
|
248
|
+
as[ this.selectIndex ].className += " focus";
|
249
|
+
}
|
250
|
+
,_select: function( content )
|
251
|
+
{
|
252
|
+
cursor_forced_position = content.indexOf( '{@}' );
|
253
|
+
content = content.replace(/{@}/g, '' );
|
254
|
+
editArea.getIESelection();
|
255
|
+
|
256
|
+
// retrive the number of matching characters
|
257
|
+
var start_index = Math.max( 0, editArea.textarea.selectionEnd - content.length );
|
258
|
+
|
259
|
+
line_string = editArea.textarea.value.substring( start_index, editArea.textarea.selectionEnd + 1);
|
260
|
+
limit = line_string.length -1;
|
261
|
+
nbMatch = 0;
|
262
|
+
for( i =0; i<limit ; i++ )
|
263
|
+
{
|
264
|
+
if( line_string.substring( limit - i - 1, limit ) == content.substring( 0, i + 1 ) )
|
265
|
+
nbMatch = i + 1;
|
266
|
+
}
|
267
|
+
// if characters match, we should include them in the selection that will be replaced
|
268
|
+
if( nbMatch > 0 )
|
269
|
+
parent.editAreaLoader.setSelectionRange(editArea.id, editArea.textarea.selectionStart - nbMatch , editArea.textarea.selectionEnd);
|
270
|
+
|
271
|
+
parent.editAreaLoader.setSelectedText(editArea.id, content );
|
272
|
+
range= parent.editAreaLoader.getSelectionRange(editArea.id);
|
273
|
+
|
274
|
+
if( cursor_forced_position != -1 )
|
275
|
+
new_pos = range["end"] - ( content.length-cursor_forced_position );
|
276
|
+
else
|
277
|
+
new_pos = range["end"];
|
278
|
+
parent.editAreaLoader.setSelectionRange(editArea.id, new_pos, new_pos);
|
279
|
+
this._hide();
|
280
|
+
}
|
281
|
+
|
282
|
+
|
283
|
+
/**
|
284
|
+
* Parse the AUTO_COMPLETION part of syntax definition files
|
285
|
+
*/
|
286
|
+
,_parseSyntaxAutoCompletionDatas: function(){
|
287
|
+
//foreach syntax loaded
|
288
|
+
for(var lang in parent.editAreaLoader.load_syntax)
|
289
|
+
{
|
290
|
+
if(!parent.editAreaLoader.syntax[lang]['autocompletion']) // init the regexp if not already initialized
|
291
|
+
{
|
292
|
+
parent.editAreaLoader.syntax[lang]['autocompletion']= {};
|
293
|
+
// the file has auto completion datas
|
294
|
+
if(parent.editAreaLoader.load_syntax[lang]['AUTO_COMPLETION'])
|
295
|
+
{
|
296
|
+
// parse them
|
297
|
+
for(var i in parent.editAreaLoader.load_syntax[lang]['AUTO_COMPLETION'])
|
298
|
+
{
|
299
|
+
datas = parent.editAreaLoader.load_syntax[lang]['AUTO_COMPLETION'][i];
|
300
|
+
tmp = {};
|
301
|
+
if(datas["CASE_SENSITIVE"]!="undefined" && datas["CASE_SENSITIVE"]==false)
|
302
|
+
tmp["modifiers"]="i";
|
303
|
+
else
|
304
|
+
tmp["modifiers"]="";
|
305
|
+
tmp["prefix_separator"]= datas["REGEXP"]["prefix_separator"];
|
306
|
+
tmp["match_prefix_separator"]= new RegExp( datas["REGEXP"]["prefix_separator"] +"$", tmp["modifiers"]);
|
307
|
+
tmp["match_word"]= new RegExp("(?:"+ datas["REGEXP"]["before_word"] +")("+ datas["REGEXP"]["possible_words_letters"] +")$", tmp["modifiers"]);
|
308
|
+
tmp["match_next_letter"]= new RegExp("^("+ datas["REGEXP"]["letter_after_word_must_match"] +")$", tmp["modifiers"]);
|
309
|
+
tmp["keywords"]= {};
|
310
|
+
//console.log( datas["KEYWORDS"] );
|
311
|
+
for( var prefix in datas["KEYWORDS"] )
|
312
|
+
{
|
313
|
+
tmp["keywords"][prefix]= {
|
314
|
+
prefix: prefix,
|
315
|
+
prefix_name: prefix,
|
316
|
+
prefix_reg: new RegExp("(?:"+ parent.editAreaLoader.get_escaped_regexp( prefix ) +")(?:"+ tmp["prefix_separator"] +")$", tmp["modifiers"] ),
|
317
|
+
datas: []
|
318
|
+
};
|
319
|
+
for( var j=0; j<datas["KEYWORDS"][prefix].length; j++ )
|
320
|
+
{
|
321
|
+
tmp["keywords"][prefix]['datas'][j]= {
|
322
|
+
is_typing: datas["KEYWORDS"][prefix][j][0],
|
323
|
+
// if replace with is empty, replace with the is_typing value
|
324
|
+
replace_with: datas["KEYWORDS"][prefix][j][1] ? datas["KEYWORDS"][prefix][j][1].replace('�', datas["KEYWORDS"][prefix][j][0] ) : '',
|
325
|
+
comment: datas["KEYWORDS"][prefix][j][2] ? datas["KEYWORDS"][prefix][j][2] : ''
|
326
|
+
};
|
327
|
+
|
328
|
+
// the replace with shouldn't be empty
|
329
|
+
if( tmp["keywords"][prefix]['datas'][j]['replace_with'].length == 0 )
|
330
|
+
tmp["keywords"][prefix]['datas'][j]['replace_with'] = tmp["keywords"][prefix]['datas'][j]['is_typing'];
|
331
|
+
|
332
|
+
// if the comment is empty, display the replace_with value
|
333
|
+
if( tmp["keywords"][prefix]['datas'][j]['comment'].length == 0 )
|
334
|
+
tmp["keywords"][prefix]['datas'][j]['comment'] = tmp["keywords"][prefix]['datas'][j]['replace_with'].replace(/{@}/g, '' );
|
335
|
+
}
|
336
|
+
|
337
|
+
}
|
338
|
+
tmp["max_text_length"]= datas["MAX_TEXT_LENGTH"];
|
339
|
+
parent.editAreaLoader.syntax[lang]['autocompletion'][i] = tmp;
|
340
|
+
}
|
341
|
+
}
|
342
|
+
}
|
343
|
+
}
|
344
|
+
}
|
345
|
+
|
346
|
+
,_checkLetter: function(){
|
347
|
+
// check that syntax hasn't changed
|
348
|
+
if( this.curr_syntax_str != editArea.settings['syntax'] )
|
349
|
+
{
|
350
|
+
if( !parent.editAreaLoader.syntax[editArea.settings['syntax']]['autocompletion'] )
|
351
|
+
this._parseSyntaxAutoCompletionDatas();
|
352
|
+
this.curr_syntax= parent.editAreaLoader.syntax[editArea.settings['syntax']]['autocompletion'];
|
353
|
+
this.curr_syntax_str = editArea.settings['syntax'];
|
354
|
+
//console.log( this.curr_syntax );
|
355
|
+
}
|
356
|
+
|
357
|
+
if( editArea.is_editable )
|
358
|
+
{
|
359
|
+
time=new Date;
|
360
|
+
t1= time.getTime();
|
361
|
+
editArea.getIESelection();
|
362
|
+
this.selectIndex = -1;
|
363
|
+
start=editArea.textarea.selectionStart;
|
364
|
+
var str = editArea.textarea.value;
|
365
|
+
var results= [];
|
366
|
+
|
367
|
+
|
368
|
+
for(var i in this.curr_syntax)
|
369
|
+
{
|
370
|
+
var last_chars = str.substring(Math.max(0, start-this.curr_syntax[i]["max_text_length"]), start);
|
371
|
+
var matchNextletter = str.substring(start, start+1).match( this.curr_syntax[i]["match_next_letter"]);
|
372
|
+
// if not writting in the middle of a word or if forcing display
|
373
|
+
if( matchNextletter || this.forceDisplay )
|
374
|
+
{
|
375
|
+
// check if the last chars match a separator
|
376
|
+
var match_prefix_separator = last_chars.match(this.curr_syntax[i]["match_prefix_separator"]);
|
377
|
+
|
378
|
+
// check if it match a possible word
|
379
|
+
var match_word= last_chars.match(this.curr_syntax[i]["match_word"]);
|
380
|
+
|
381
|
+
//console.log( match_word );
|
382
|
+
if( match_word )
|
383
|
+
{
|
384
|
+
var begin_word= match_word[1];
|
385
|
+
var match_curr_word= new RegExp("^"+ parent.editAreaLoader.get_escaped_regexp( begin_word ), this.curr_syntax[i]["modifiers"]);
|
386
|
+
//console.log( match_curr_word );
|
387
|
+
for(var prefix in this.curr_syntax[i]["keywords"])
|
388
|
+
{
|
389
|
+
// parent.console.log( this.curr_syntax[i]["keywords"][prefix] );
|
390
|
+
for(var j=0; j<this.curr_syntax[i]["keywords"][prefix]['datas'].length; j++)
|
391
|
+
{
|
392
|
+
// parent.console.log( this.curr_syntax[i]["keywords"][prefix]['datas'][j]['is_typing'] );
|
393
|
+
// the key word match or force display
|
394
|
+
if( this.curr_syntax[i]["keywords"][prefix]['datas'][j]['is_typing'].match(match_curr_word) )
|
395
|
+
{
|
396
|
+
// parent.console.log('match');
|
397
|
+
hasMatch = false;
|
398
|
+
var before = last_chars.substr( 0, last_chars.length - begin_word.length );
|
399
|
+
|
400
|
+
// no prefix to match => it's valid
|
401
|
+
if( !match_prefix_separator && this.curr_syntax[i]["keywords"][prefix]['prefix'].length == 0 )
|
402
|
+
{
|
403
|
+
if( ! before.match( this.curr_syntax[i]["keywords"][prefix]['prefix_reg'] ) )
|
404
|
+
hasMatch = true;
|
405
|
+
}
|
406
|
+
// we still need to check the prefix if there is one
|
407
|
+
else if( this.curr_syntax[i]["keywords"][prefix]['prefix'].length > 0 )
|
408
|
+
{
|
409
|
+
if( before.match( this.curr_syntax[i]["keywords"][prefix]['prefix_reg'] ) )
|
410
|
+
hasMatch = true;
|
411
|
+
}
|
412
|
+
|
413
|
+
if( hasMatch )
|
414
|
+
results[results.length]= [ this.curr_syntax[i]["keywords"][prefix], this.curr_syntax[i]["keywords"][prefix]['datas'][j] ];
|
415
|
+
}
|
416
|
+
}
|
417
|
+
}
|
418
|
+
}
|
419
|
+
// it doesn't match any possible word but we want to display something
|
420
|
+
// we'll display to list of all available words
|
421
|
+
else if( this.forceDisplay || match_prefix_separator )
|
422
|
+
{
|
423
|
+
for(var prefix in this.curr_syntax[i]["keywords"])
|
424
|
+
{
|
425
|
+
for(var j=0; j<this.curr_syntax[i]["keywords"][prefix]['datas'].length; j++)
|
426
|
+
{
|
427
|
+
hasMatch = false;
|
428
|
+
// no prefix to match => it's valid
|
429
|
+
if( !match_prefix_separator && this.curr_syntax[i]["keywords"][prefix]['prefix'].length == 0 )
|
430
|
+
{
|
431
|
+
hasMatch = true;
|
432
|
+
}
|
433
|
+
// we still need to check the prefix if there is one
|
434
|
+
else if( match_prefix_separator && this.curr_syntax[i]["keywords"][prefix]['prefix'].length > 0 )
|
435
|
+
{
|
436
|
+
var before = last_chars; //.substr( 0, last_chars.length );
|
437
|
+
if( before.match( this.curr_syntax[i]["keywords"][prefix]['prefix_reg'] ) )
|
438
|
+
hasMatch = true;
|
439
|
+
}
|
440
|
+
|
441
|
+
if( hasMatch )
|
442
|
+
results[results.length]= [ this.curr_syntax[i]["keywords"][prefix], this.curr_syntax[i]["keywords"][prefix]['datas'][j] ];
|
443
|
+
}
|
444
|
+
}
|
445
|
+
}
|
446
|
+
}
|
447
|
+
}
|
448
|
+
|
449
|
+
// there is only one result, and we can select it automatically
|
450
|
+
if( results.length == 1 && this.autoSelectIfOneResult )
|
451
|
+
{
|
452
|
+
// console.log( results );
|
453
|
+
this._select( results[0][1]['replace_with'] );
|
454
|
+
}
|
455
|
+
else if( results.length == 0 )
|
456
|
+
{
|
457
|
+
this._hide();
|
458
|
+
}
|
459
|
+
else
|
460
|
+
{
|
461
|
+
// build the suggestion box content
|
462
|
+
var lines=[];
|
463
|
+
for(var i=0; i<results.length; i++)
|
464
|
+
{
|
465
|
+
var line= "<li><a href=\"#\" class=\"entry\" onmousedown=\"EditArea_autocompletion._select('"+ results[i][1]['replace_with'].replace(new RegExp('"', "g"), """) +"');return false;\">"+ results[i][1]['comment'];
|
466
|
+
if(results[i][0]['prefix_name'].length>0)
|
467
|
+
line+='<span class="prefix">'+ results[i][0]['prefix_name'] +'</span>';
|
468
|
+
line+='</a></li>';
|
469
|
+
lines[lines.length]=line;
|
470
|
+
}
|
471
|
+
// sort results
|
472
|
+
this.container.innerHTML = '<ul>'+ lines.sort().join('') +'</ul>';
|
473
|
+
|
474
|
+
var cursor = _$("cursor_pos");
|
475
|
+
this.container.style.top = ( cursor.cursor_top + editArea.lineHeight ) +"px";
|
476
|
+
this.container.style.left = ( cursor.cursor_left + 8 ) +"px";
|
477
|
+
this._show();
|
478
|
+
}
|
479
|
+
|
480
|
+
this.autoSelectIfOneResult = false;
|
481
|
+
time=new Date;
|
482
|
+
t2= time.getTime();
|
483
|
+
|
484
|
+
//parent.console.log( begin_word +"\n"+ (t2-t1) +"\n"+ html );
|
485
|
+
}
|
486
|
+
}
|
487
|
+
};
|
488
|
+
|
489
|
+
// Load as a plugin
|
490
|
+
editArea.settings['plugins'][ editArea.settings['plugins'].length ] = 'autocompletion';
|
491
|
+
editArea.add_plugin('autocompletion', EditArea_autocompletion);
|