Develop and Download Open Source Software

Browse Subversion Repository

Contents of /js/input_assist.js

Parent Directory Parent Directory | Revision Log Revision Log


Revision 17 - (show annotations) (download) (as text)
Tue Dec 29 22:32:33 2009 UTC (14 years, 5 months ago) by berupon
File MIME type: application/x-javascript
File size: 7454 byte(s)
入力補助ライブラリ更新
・候補と完全一致する値が直接入力された場合に、候補選択処理を呼び出すように変更。
・入力コントロールからonBlurイベントが起きた際に、入力内容が候補とどれも一致しない場合、候補選択処理を引数をnullにして呼び出すように変更。
1
2 // Copyright (c) 2009 Katsuhisa Yuasa <berupon [at] gmail.com>
3 // License http://www.opensource.org/licenses/mit-license.html
4 //
5 // Inspired by suggest.js http://www.enjoyxstudy.com/javascript/suggest/
6 //
7
8 InputAssist = function (elem) {
9 this.init.apply(this, arguments);
10 };
11
12 InputAssist.prototype = {
13
14 init : function (elem) {
15 this.elem = elem;
16 this.listElem = null;
17 this.oldValue = elem.value;
18 this.timer = null;
19 this.interval = 300;
20 this.listClassName = "assist_list";
21 this.listItemClassName = "item";
22 this.activeListItemClassName = "active";
23 this.listActiveIndex = -1;
24 this.dataList = new Array();
25 this.matchedDataList = new Array();
26
27 elem.observe("focus", this.onFocus.bind(this));
28 elem.observe("blur", this.onBlur.bind(this));
29
30 elem.observe("keydown", this.onKeyDown.bind(this));
31 var keyevent = (Prototype.Browser.Opera || Prototype.Browser.Gecko) ? 'keypress' : 'keyup';
32 elem.observe(keyevent, this.onKeyUp.bind(this));
33 document.observe('mousemove', this.onMouseMove.bind(this));
34 },
35
36 onFocus : function (e) {
37 var elem = Event.element(e);
38 this.createListElem();
39 },
40
41 onBlur : function (e) {
42 var matched = false;
43 if (this.matchedDataList.length) {
44 for (var i=0; i<this.matchedDataList.length; ++i) {
45 if (this.matchData(this.matchedDataList[i]) == 1) {
46 matched = true;
47 this.selectData(i);
48 break;
49 }
50 }
51 }
52 if (!matched) {
53 this.setData(null);
54 }
55 this.hideList();
56 if (this.timer) {
57 clearTimeout(this.timer);
58 this.timer = null;
59 }
60 },
61
62 onKeyDown : function (e) {
63 switch (e.keyCode) {
64 case 9: // tab
65 if (1
66 && this.matchedDataList.length
67 && this.listActiveIndex >= 0
68 && this.listActiveIndex < this.matchedDataList.length
69 ) {
70 this.selectData(this.listActiveIndex);
71 break;
72 }
73 case 13: // enter
74 if (1
75 && this.matchedDataList.length
76 && this.listActiveIndex >= 0
77 && this.listActiveIndex < this.matchedDataList.length
78 ) {
79 this.selectData(this.listActiveIndex, true);
80 Event.stop(e);
81 break;
82 }
83 break;
84 }
85 },
86
87 selectData : function (idx, bFocus) {
88 setTimeout(
89 function () {
90 this.hideList();
91 this.setData(this.matchedDataList[idx]);
92 this.oldValue = this.elem.value;
93 this.listActiveIndex = -1;
94 if (bFocus) {
95 this.elem.focus();
96 }
97 }.bind(this),
98 10
99 );
100 },
101
102 onKeyUp : function (e) {
103 if (this.timer) {
104 switch (e.keyCode) {
105 case 16: // shift
106 case 17: // ctrl
107 case 18: // alt
108 break;
109 default:
110 clearTimeout(this.timer);
111 }
112 }
113 switch (e.keyCode) {
114 case 37: // left
115 break;
116 case 38: // up
117 this.shiftItemFocus(-1);
118 break;
119 case 39: // right
120 break;
121 case 40: // down
122 if (e.altKey) {
123 this.oldValue = "";
124 this.onTimer();
125 }else {
126 this.shiftItemFocus(1);
127 }
128 break;
129 case 27: // esc
130 this.hideList();
131 break;
132 case 13: // enter
133 case 9: // tab
134 case 16: // shift
135 case 17: // ctrl
136 case 18: // alt
137 break;
138 case 8: // backspace
139 case 46: // delete
140 if (this.elem.value == "") {
141 this.onTimer();
142 break;
143 }
144 default:
145 if (!e.altKey && !e.ctrlKey) {
146 if (this.oldValue == "") {
147 this.timer = setTimeout(this.onTimer.bind(this), this.interval/10);
148 }else {
149 this.timer = setTimeout(this.onTimer.bind(this), this.interval);
150 }
151 }
152 break;
153 }
154 },
155
156 onMouseMove : function (e) {
157 if (!this.listElem) {
158 return;
159 }
160 var nodes = this.listElem.childNodes;
161 if (nodes.length == 0) {
162 return;
163 }
164 var x = Event.pointerX(e);
165 var y = Event.pointerY(e);
166 var listItems = this.listElem.childNodes;
167 for (var i=0; i<listItems.length; ++i) {
168 var elem = listItems[i];
169 if (Position.within(elem, x, y)) {
170 this.moveItemFocus(i);
171 break;
172 }
173 }
174
175 },
176
177 shiftItemFocus : function (shift) {
178 if (!Element.visible(this.listElem)) {
179 return;
180 }
181 var nodes = this.listElem.childNodes;
182 if (nodes.length == 0) {
183 return;
184 }
185 var newActiveIndex = -1;
186 if (this.listActiveIndex == -1) {
187 if (shift < 0) {
188 newActiveIndex = nodes.length - 1;
189 }else {
190 newActiveIndex = 0;
191 }
192 }else {
193 newActiveIndex = this.listActiveIndex + shift;
194 if (newActiveIndex >= nodes.length) {
195 newActiveIndex = -1;
196 }
197 }
198 this.moveItemFocus(newActiveIndex);
199 },
200
201 moveItemFocus : function (newActiveIndex) {
202 if (this.listActiveIndex != newActiveIndex) {
203 var nodes = this.listElem.childNodes;
204 if (this.listActiveIndex != -1 && this.listActiveIndex < nodes.length) {
205 Element.removeClassName(nodes[this.listActiveIndex], this.activeListItemClassName);
206 }
207 if (newActiveIndex != -1) {
208 if (newActiveIndex < 0) {
209 alert(1);
210 }
211 Element.addClassName(nodes[newActiveIndex], this.activeListItemClassName);
212 }
213 this.listActiveIndex = newActiveIndex;
214 }
215 },
216
217 onTimer : function () {
218 if (this.elem.value.length == 0) {
219 this.hideList();
220 return;
221 }
222 if (this.elem != document.activeElement) {
223 return;
224 }
225 if (this.elem.value == this.oldValue) {
226 return;
227 }
228 this.setList();
229 this.oldValue = this.elem.value;
230 this.timer = setTimeout(this.onTimer.bind(this), this.interval);
231 },
232
233 onMouseDown : function(e) {
234 var x = Event.pointerX(e);
235 var y = Event.pointerY(e);
236 var listItems = this.listElem.childNodes;
237 for (var i=0; i<listItems.length; ++i) {
238 var elem = listItems[i];
239 if (Position.within(elem, x, y)) {
240 this.selectData(i, true);
241 break;
242 }
243 }
244 },
245
246 createListElem : function () {
247 if (this.listElem) {
248 return;
249 }
250 var listElem = document.createElement('DIV');
251 listElem.className = this.listClassName;
252 Element.hide(listElem);
253 Event.observe(listElem, "mousedown", this.onMouseDown.bind(this));
254 this.listElem = listElem;
255 this.elem.parentNode.insertBefore(listElem, this.elem.nextSibling);
256 },
257
258 addListElemItem : function (html) {
259 var listItem = document.createElement('DIV');
260 listItem.className = this.listItemClassName;
261 listItem.innerHTML = html;
262 this.listElem.appendChild(listItem);
263 },
264
265 setList : function () {
266 if (!this.listElem) {
267 return;
268 }
269 if (this.listElem.childNodes) {
270 for (var i=this.listElem.childNodes.length-1; i>=0; --i) {
271 this.listElem.removeChild(this.listElem.childNodes[i]);
272 }
273 }
274 this.dataList = this.provideDataList();
275 this.matchedDataList = new Array();
276 var results = new Array();
277 for (var i=0; i<this.dataList.length; ++i) {
278 var data = this.dataList[i];
279 var ret = {html:''};
280 if (this.matchData(data, ret)) {
281 this.matchedDataList.push(data);
282 results.push(ret.html);
283 }
284 }
285 if (results.length != 0) {
286 for (var i=0; i<results.length; ++i) {
287 this.addListElemItem(results[i]);
288 }
289 var style = this.listElem.style;
290 var offset = Element.cumulativeOffset(this.elem);
291 style.left = offset[0] + "px";
292 style.top = (offset[1] + this.elem.offsetHeight) + "px";
293 style.minWidth = this.elem.offsetWidth + "px";
294 Element.show(this.listElem);
295 }else {
296 this.hideList();
297 }
298 },
299
300 hideList : function () {
301 if (!this.listElem) {
302 return;
303 }
304 this.oldValue = this.elem.value;
305 this.listActiveIndex = -1;
306 Element.hide(this.listElem);
307 }
308
309 };
310

Back to OSDN">Back to OSDN
ViewVC Help
Powered by ViewVC 1.1.26