]>
Commit | Line | Data |
---|---|---|
1354d172 AD |
1 | require({cache:{ |
2 | 'url:dijit/templates/InlineEditBox.html':"<span data-dojo-attach-point=\"editNode\" role=\"presentation\" style=\"position: absolute; visibility:hidden\" class=\"dijitReset dijitInline\"\n\tdata-dojo-attach-event=\"onkeypress: _onKeyPress\"\n\t><span data-dojo-attach-point=\"editorPlaceholder\"></span\n\t><span data-dojo-attach-point=\"buttonContainer\"\n\t\t><button data-dojo-type=\"dijit.form.Button\" data-dojo-props=\"label: '${buttonSave}', 'class': 'saveButton'\"\n\t\t\tdata-dojo-attach-point=\"saveButton\" data-dojo-attach-event=\"onClick:save\"></button\n\t\t><button data-dojo-type=\"dijit.form.Button\" data-dojo-props=\"label: '${buttonCancel}', 'class': 'cancelButton'\"\n\t\t\tdata-dojo-attach-point=\"cancelButton\" data-dojo-attach-event=\"onClick:cancel\"></button\n\t></span\n></span>\n"}}); | |
3 | define("dijit/InlineEditBox", [ | |
4 | "dojo/_base/array", // array.forEach | |
5 | "dojo/_base/declare", // declare | |
6 | "dojo/dom-attr", // domAttr.set domAttr.get | |
7 | "dojo/dom-class", // domClass.add domClass.remove domClass.toggle | |
8 | "dojo/dom-construct", // domConstruct.create domConstruct.destroy | |
9 | "dojo/dom-style", // domStyle.getComputedStyle domStyle.set domStyle.get | |
10 | "dojo/_base/event", // event.stop | |
11 | "dojo/i18n", // i18n.getLocalization | |
12 | "dojo/_base/kernel", // kernel.deprecated | |
13 | "dojo/keys", // keys.ENTER keys.ESCAPE | |
14 | "dojo/_base/lang", // lang.getObject | |
15 | "dojo/_base/sniff", // has("ie") | |
16 | "./focus", | |
17 | "./_Widget", | |
18 | "./_TemplatedMixin", | |
19 | "./_WidgetsInTemplateMixin", | |
20 | "./_Container", | |
21 | "./form/Button", | |
22 | "./form/_TextBoxMixin", | |
23 | "./form/TextBox", | |
24 | "dojo/text!./templates/InlineEditBox.html", | |
25 | "dojo/i18n!./nls/common" | |
26 | ], function(array, declare, domAttr, domClass, domConstruct, domStyle, event, i18n, kernel, keys, lang, has, | |
27 | fm, _Widget, _TemplatedMixin, _WidgetsInTemplateMixin, _Container, Button, _TextBoxMixin, TextBox, template){ | |
28 | ||
29 | /*===== | |
30 | var _Widget = dijit._Widget; | |
31 | var _TemplatedMixin = dijit._TemplatedMixin; | |
32 | var _WidgetsInTemplateMixin = dijit._WidgetsInTemplateMixin; | |
33 | var _Container = dijit._Container; | |
34 | var Button = dijit.form.Button; | |
35 | var TextBox = dijit.form.TextBox; | |
36 | =====*/ | |
37 | ||
38 | // module: | |
39 | // dijit/InlineEditBox | |
40 | // summary: | |
41 | // An element with in-line edit capabilities | |
42 | ||
43 | var InlineEditor = declare("dijit._InlineEditor", [_Widget, _TemplatedMixin, _WidgetsInTemplateMixin], { | |
44 | // summary: | |
45 | // Internal widget used by InlineEditBox, displayed when in editing mode | |
46 | // to display the editor and maybe save/cancel buttons. Calling code should | |
47 | // connect to save/cancel methods to detect when editing is finished | |
48 | // | |
49 | // Has mainly the same parameters as InlineEditBox, plus these values: | |
50 | // | |
51 | // style: Object | |
52 | // Set of CSS attributes of display node, to replicate in editor | |
53 | // | |
54 | // value: String | |
55 | // Value as an HTML string or plain text string, depending on renderAsHTML flag | |
56 | ||
57 | templateString: template, | |
58 | ||
59 | postMixInProperties: function(){ | |
60 | this.inherited(arguments); | |
61 | this.messages = i18n.getLocalization("dijit", "common", this.lang); | |
62 | array.forEach(["buttonSave", "buttonCancel"], function(prop){ | |
63 | if(!this[prop]){ this[prop] = this.messages[prop]; } | |
64 | }, this); | |
65 | }, | |
66 | ||
67 | buildRendering: function(){ | |
68 | this.inherited(arguments); | |
69 | ||
70 | // Create edit widget in place in the template | |
71 | var cls = typeof this.editor == "string" ? lang.getObject(this.editor) : this.editor; | |
72 | ||
73 | // Copy the style from the source | |
74 | // Don't copy ALL properties though, just the necessary/applicable ones. | |
75 | // wrapperStyle/destStyle code is to workaround IE bug where getComputedStyle().fontSize | |
76 | // is a relative value like 200%, rather than an absolute value like 24px, and | |
77 | // the 200% can refer *either* to a setting on the node or it's ancestor (see #11175) | |
78 | var srcStyle = this.sourceStyle, | |
79 | editStyle = "line-height:" + srcStyle.lineHeight + ";", | |
80 | destStyle = domStyle.getComputedStyle(this.domNode); | |
81 | array.forEach(["Weight","Family","Size","Style"], function(prop){ | |
82 | var textStyle = srcStyle["font"+prop], | |
83 | wrapperStyle = destStyle["font"+prop]; | |
84 | if(wrapperStyle != textStyle){ | |
85 | editStyle += "font-"+prop+":"+srcStyle["font"+prop]+";"; | |
86 | } | |
87 | }, this); | |
88 | array.forEach(["marginTop","marginBottom","marginLeft", "marginRight"], function(prop){ | |
89 | this.domNode.style[prop] = srcStyle[prop]; | |
90 | }, this); | |
91 | var width = this.inlineEditBox.width; | |
92 | if(width == "100%"){ | |
93 | // block mode | |
94 | editStyle += "width:100%;"; | |
95 | this.domNode.style.display = "block"; | |
96 | }else{ | |
97 | // inline-block mode | |
98 | editStyle += "width:" + (width + (Number(width) == width ? "px" : "")) + ";"; | |
99 | } | |
100 | var editorParams = lang.delegate(this.inlineEditBox.editorParams, { | |
101 | style: editStyle, | |
102 | dir: this.dir, | |
103 | lang: this.lang, | |
104 | textDir: this.textDir | |
105 | }); | |
106 | editorParams[ "displayedValue" in cls.prototype ? "displayedValue" : "value"] = this.value; | |
107 | this.editWidget = new cls(editorParams, this.editorPlaceholder); | |
108 | ||
109 | if(this.inlineEditBox.autoSave){ | |
110 | // Remove the save/cancel buttons since saving is done by simply tabbing away or | |
111 | // selecting a value from the drop down list | |
112 | domConstruct.destroy(this.buttonContainer); | |
113 | } | |
114 | }, | |
115 | ||
116 | postCreate: function(){ | |
117 | this.inherited(arguments); | |
118 | ||
119 | var ew = this.editWidget; | |
120 | ||
121 | if(this.inlineEditBox.autoSave){ | |
122 | // Selecting a value from a drop down list causes an onChange event and then we save | |
123 | this.connect(ew, "onChange", "_onChange"); | |
124 | ||
125 | // ESC and TAB should cancel and save. Note that edit widgets do a stopEvent() on ESC key (to | |
126 | // prevent Dialog from closing when the user just wants to revert the value in the edit widget), | |
127 | // so this is the only way we can see the key press event. | |
128 | this.connect(ew, "onKeyPress", "_onKeyPress"); | |
129 | }else{ | |
130 | // If possible, enable/disable save button based on whether the user has changed the value | |
131 | if("intermediateChanges" in ew){ | |
132 | ew.set("intermediateChanges", true); | |
133 | this.connect(ew, "onChange", "_onIntermediateChange"); | |
134 | this.saveButton.set("disabled", true); | |
135 | } | |
136 | } | |
137 | }, | |
138 | ||
139 | _onIntermediateChange: function(/*===== val =====*/){ | |
140 | // summary: | |
141 | // Called for editor widgets that support the intermediateChanges=true flag as a way | |
142 | // to detect when to enable/disabled the save button | |
143 | this.saveButton.set("disabled", (this.getValue() == this._resetValue) || !this.enableSave()); | |
144 | }, | |
145 | ||
146 | destroy: function(){ | |
147 | this.editWidget.destroy(true); // let the parent wrapper widget clean up the DOM | |
148 | this.inherited(arguments); | |
149 | }, | |
150 | ||
151 | getValue: function(){ | |
152 | // summary: | |
153 | // Return the [display] value of the edit widget | |
154 | var ew = this.editWidget; | |
155 | return String(ew.get("displayedValue" in ew ? "displayedValue" : "value")); | |
156 | }, | |
157 | ||
158 | _onKeyPress: function(e){ | |
159 | // summary: | |
160 | // Handler for keypress in the edit box in autoSave mode. | |
161 | // description: | |
162 | // For autoSave widgets, if Esc/Enter, call cancel/save. | |
163 | // tags: | |
164 | // private | |
165 | ||
166 | if(this.inlineEditBox.autoSave && this.inlineEditBox.editing){ | |
167 | if(e.altKey || e.ctrlKey){ return; } | |
168 | // If Enter/Esc pressed, treat as save/cancel. | |
169 | if(e.charOrCode == keys.ESCAPE){ | |
170 | event.stop(e); | |
171 | this.cancel(true); // sets editing=false which short-circuits _onBlur processing | |
172 | }else if(e.charOrCode == keys.ENTER && e.target.tagName == "INPUT"){ | |
173 | event.stop(e); | |
174 | this._onChange(); // fire _onBlur and then save | |
175 | } | |
176 | ||
177 | // _onBlur will handle TAB automatically by allowing | |
178 | // the TAB to change focus before we mess with the DOM: #6227 | |
179 | // Expounding by request: | |
180 | // The current focus is on the edit widget input field. | |
181 | // save() will hide and destroy this widget. | |
182 | // We want the focus to jump from the currently hidden | |
183 | // displayNode, but since it's hidden, it's impossible to | |
184 | // unhide it, focus it, and then have the browser focus | |
185 | // away from it to the next focusable element since each | |
186 | // of these events is asynchronous and the focus-to-next-element | |
187 | // is already queued. | |
188 | // So we allow the browser time to unqueue the move-focus event | |
189 | // before we do all the hide/show stuff. | |
190 | } | |
191 | }, | |
192 | ||
193 | _onBlur: function(){ | |
194 | // summary: | |
195 | // Called when focus moves outside the editor | |
196 | // tags: | |
197 | // private | |
198 | ||
199 | this.inherited(arguments); | |
200 | if(this.inlineEditBox.autoSave && this.inlineEditBox.editing){ | |
201 | if(this.getValue() == this._resetValue){ | |
202 | this.cancel(false); | |
203 | }else if(this.enableSave()){ | |
204 | this.save(false); | |
205 | } | |
206 | } | |
207 | }, | |
208 | ||
209 | _onChange: function(){ | |
210 | // summary: | |
211 | // Called when the underlying widget fires an onChange event, | |
212 | // such as when the user selects a value from the drop down list of a ComboBox, | |
213 | // which means that the user has finished entering the value and we should save. | |
214 | // tags: | |
215 | // private | |
216 | ||
217 | if(this.inlineEditBox.autoSave && this.inlineEditBox.editing && this.enableSave()){ | |
218 | fm.focus(this.inlineEditBox.displayNode); // fires _onBlur which will save the formatted value | |
219 | } | |
220 | }, | |
221 | ||
222 | enableSave: function(){ | |
223 | // summary: | |
224 | // User overridable function returning a Boolean to indicate | |
225 | // if the Save button should be enabled or not - usually due to invalid conditions | |
226 | // tags: | |
227 | // extension | |
228 | return ( | |
229 | this.editWidget.isValid | |
230 | ? this.editWidget.isValid() | |
231 | : true | |
232 | ); | |
233 | }, | |
234 | ||
235 | focus: function(){ | |
236 | // summary: | |
237 | // Focus the edit widget. | |
238 | // tags: | |
239 | // protected | |
240 | ||
241 | this.editWidget.focus(); | |
242 | setTimeout(lang.hitch(this, function(){ | |
243 | if(this.editWidget.focusNode && this.editWidget.focusNode.tagName == "INPUT"){ | |
244 | _TextBoxMixin.selectInputText(this.editWidget.focusNode); | |
245 | } | |
246 | }), 0); | |
247 | } | |
248 | }); | |
249 | ||
250 | ||
251 | var InlineEditBox = declare("dijit.InlineEditBox", _Widget, { | |
252 | // summary: | |
253 | // An element with in-line edit capabilities | |
254 | // | |
255 | // description: | |
256 | // Behavior for an existing node (`<p>`, `<div>`, `<span>`, etc.) so that | |
257 | // when you click it, an editor shows up in place of the original | |
258 | // text. Optionally, Save and Cancel button are displayed below the edit widget. | |
259 | // When Save is clicked, the text is pulled from the edit | |
260 | // widget and redisplayed and the edit widget is again hidden. | |
261 | // By default a plain Textarea widget is used as the editor (or for | |
262 | // inline values a TextBox), but you can specify an editor such as | |
263 | // dijit.Editor (for editing HTML) or a Slider (for adjusting a number). | |
264 | // An edit widget must support the following API to be used: | |
265 | // - displayedValue or value as initialization parameter, | |
266 | // and available through set('displayedValue') / set('value') | |
267 | // - void focus() | |
268 | // - DOM-node focusNode = node containing editable text | |
269 | ||
270 | // editing: [readonly] Boolean | |
271 | // Is the node currently in edit mode? | |
272 | editing: false, | |
273 | ||
274 | // autoSave: Boolean | |
275 | // Changing the value automatically saves it; don't have to push save button | |
276 | // (and save button isn't even displayed) | |
277 | autoSave: true, | |
278 | ||
279 | // buttonSave: String | |
280 | // Save button label | |
281 | buttonSave: "", | |
282 | ||
283 | // buttonCancel: String | |
284 | // Cancel button label | |
285 | buttonCancel: "", | |
286 | ||
287 | // renderAsHtml: Boolean | |
288 | // Set this to true if the specified Editor's value should be interpreted as HTML | |
289 | // rather than plain text (ex: `dijit.Editor`) | |
290 | renderAsHtml: false, | |
291 | ||
292 | // editor: String|Function | |
293 | // Class name (or reference to the Class) for Editor widget | |
294 | editor: TextBox, | |
295 | ||
296 | // editorWrapper: String|Function | |
297 | // Class name (or reference to the Class) for widget that wraps the editor widget, displaying save/cancel | |
298 | // buttons. | |
299 | editorWrapper: InlineEditor, | |
300 | ||
301 | // editorParams: Object | |
302 | // Set of parameters for editor, like {required: true} | |
303 | editorParams: {}, | |
304 | ||
305 | // disabled: Boolean | |
306 | // If true, clicking the InlineEditBox to edit it will have no effect. | |
307 | disabled: false, | |
308 | ||
309 | onChange: function(/*===== value =====*/){ | |
310 | // summary: | |
311 | // Set this handler to be notified of changes to value. | |
312 | // tags: | |
313 | // callback | |
314 | }, | |
315 | ||
316 | onCancel: function(){ | |
317 | // summary: | |
318 | // Set this handler to be notified when editing is cancelled. | |
319 | // tags: | |
320 | // callback | |
321 | }, | |
322 | ||
323 | // width: String | |
324 | // Width of editor. By default it's width=100% (ie, block mode). | |
325 | width: "100%", | |
326 | ||
327 | // value: String | |
328 | // The display value of the widget in read-only mode | |
329 | value: "", | |
330 | ||
331 | // noValueIndicator: [const] String | |
332 | // The text that gets displayed when there is no value (so that the user has a place to click to edit) | |
333 | noValueIndicator: has("ie") <= 6 ? // font-family needed on IE6 but it messes up IE8 | |
334 | "<span style='font-family: wingdings; text-decoration: underline;'>    ✍    </span>" : | |
335 | "<span style='text-decoration: underline;'>    ✍    </span>", // //   == | |
336 | ||
337 | constructor: function(){ | |
338 | // summary: | |
339 | // Sets up private arrays etc. | |
340 | // tags: | |
341 | // private | |
342 | this.editorParams = {}; | |
343 | }, | |
344 | ||
345 | postMixInProperties: function(){ | |
346 | this.inherited(arguments); | |
347 | ||
348 | // save pointer to original source node, since Widget nulls-out srcNodeRef | |
349 | this.displayNode = this.srcNodeRef; | |
350 | ||
351 | // connect handlers to the display node | |
352 | var events = { | |
353 | ondijitclick: "_onClick", | |
354 | onmouseover: "_onMouseOver", | |
355 | onmouseout: "_onMouseOut", | |
356 | onfocus: "_onMouseOver", | |
357 | onblur: "_onMouseOut" | |
358 | }; | |
359 | for(var name in events){ | |
360 | this.connect(this.displayNode, name, events[name]); | |
361 | } | |
362 | this.displayNode.setAttribute("role", "button"); | |
363 | if(!this.displayNode.getAttribute("tabIndex")){ | |
364 | this.displayNode.setAttribute("tabIndex", 0); | |
365 | } | |
366 | ||
367 | if(!this.value && !("value" in this.params)){ // "" is a good value if specified directly so check params){ | |
368 | this.value = lang.trim(this.renderAsHtml ? this.displayNode.innerHTML : | |
369 | (this.displayNode.innerText||this.displayNode.textContent||"")); | |
370 | } | |
371 | if(!this.value){ | |
372 | this.displayNode.innerHTML = this.noValueIndicator; | |
373 | } | |
374 | ||
375 | domClass.add(this.displayNode, 'dijitInlineEditBoxDisplayMode'); | |
376 | }, | |
377 | ||
378 | setDisabled: function(/*Boolean*/ disabled){ | |
379 | // summary: | |
380 | // Deprecated. Use set('disabled', ...) instead. | |
381 | // tags: | |
382 | // deprecated | |
383 | kernel.deprecated("dijit.InlineEditBox.setDisabled() is deprecated. Use set('disabled', bool) instead.", "", "2.0"); | |
384 | this.set('disabled', disabled); | |
385 | }, | |
386 | ||
387 | _setDisabledAttr: function(/*Boolean*/ disabled){ | |
388 | // summary: | |
389 | // Hook to make set("disabled", ...) work. | |
390 | // Set disabled state of widget. | |
391 | this.domNode.setAttribute("aria-disabled", disabled); | |
392 | if(disabled){ | |
393 | this.displayNode.removeAttribute("tabIndex"); | |
394 | }else{ | |
395 | this.displayNode.setAttribute("tabIndex", 0); | |
396 | } | |
397 | domClass.toggle(this.displayNode, "dijitInlineEditBoxDisplayModeDisabled", disabled); | |
398 | this._set("disabled", disabled); | |
399 | }, | |
400 | ||
401 | _onMouseOver: function(){ | |
402 | // summary: | |
403 | // Handler for onmouseover and onfocus event. | |
404 | // tags: | |
405 | // private | |
406 | if(!this.disabled){ | |
407 | domClass.add(this.displayNode, "dijitInlineEditBoxDisplayModeHover"); | |
408 | } | |
409 | }, | |
410 | ||
411 | _onMouseOut: function(){ | |
412 | // summary: | |
413 | // Handler for onmouseout and onblur event. | |
414 | // tags: | |
415 | // private | |
416 | domClass.remove(this.displayNode, "dijitInlineEditBoxDisplayModeHover"); | |
417 | }, | |
418 | ||
419 | _onClick: function(/*Event*/ e){ | |
420 | // summary: | |
421 | // Handler for onclick event. | |
422 | // tags: | |
423 | // private | |
424 | if(this.disabled){ return; } | |
425 | if(e){ event.stop(e); } | |
426 | this._onMouseOut(); | |
427 | ||
428 | // Since FF gets upset if you move a node while in an event handler for that node... | |
429 | setTimeout(lang.hitch(this, "edit"), 0); | |
430 | }, | |
431 | ||
432 | edit: function(){ | |
433 | // summary: | |
434 | // Display the editor widget in place of the original (read only) markup. | |
435 | // tags: | |
436 | // private | |
437 | ||
438 | if(this.disabled || this.editing){ return; } | |
439 | this._set('editing', true); | |
440 | ||
441 | // save some display node values that can be restored later | |
442 | this._savedPosition = domStyle.get(this.displayNode, "position") || "static"; | |
443 | this._savedOpacity = domStyle.get(this.displayNode, "opacity") || "1"; | |
444 | this._savedTabIndex = domAttr.get(this.displayNode, "tabIndex") || "0"; | |
445 | ||
446 | if(this.wrapperWidget){ | |
447 | var ew = this.wrapperWidget.editWidget; | |
448 | ew.set("displayedValue" in ew ? "displayedValue" : "value", this.value); | |
449 | }else{ | |
450 | // Placeholder for edit widget | |
451 | // Put place holder (and eventually editWidget) before the display node so that it's positioned correctly | |
452 | // when Calendar dropdown appears, which happens automatically on focus. | |
453 | var placeholder = domConstruct.create("span", null, this.domNode, "before"); | |
454 | ||
455 | // Create the editor wrapper (the thing that holds the editor widget and the save/cancel buttons) | |
456 | var ewc = typeof this.editorWrapper == "string" ? lang.getObject(this.editorWrapper) : this.editorWrapper; | |
457 | this.wrapperWidget = new ewc({ | |
458 | value: this.value, | |
459 | buttonSave: this.buttonSave, | |
460 | buttonCancel: this.buttonCancel, | |
461 | dir: this.dir, | |
462 | lang: this.lang, | |
463 | tabIndex: this._savedTabIndex, | |
464 | editor: this.editor, | |
465 | inlineEditBox: this, | |
466 | sourceStyle: domStyle.getComputedStyle(this.displayNode), | |
467 | save: lang.hitch(this, "save"), | |
468 | cancel: lang.hitch(this, "cancel"), | |
469 | textDir: this.textDir | |
470 | }, placeholder); | |
471 | if(!this._started){ | |
472 | this.startup(); | |
473 | } | |
474 | } | |
475 | var ww = this.wrapperWidget; | |
476 | ||
477 | // to avoid screen jitter, we first create the editor with position:absolute, visibility:hidden, | |
478 | // and then when it's finished rendering, we switch from display mode to editor | |
479 | // position:absolute releases screen space allocated to the display node | |
480 | // opacity:0 is the same as visibility:hidden but is still focusable | |
481 | // visiblity:hidden removes focus outline | |
482 | ||
483 | domStyle.set(this.displayNode, { position: "absolute", opacity: "0" }); // makes display node invisible, display style used for focus-ability | |
484 | domStyle.set(ww.domNode, { position: this._savedPosition, visibility: "visible", opacity: "1" }); | |
485 | domAttr.set(this.displayNode, "tabIndex", "-1"); // needed by WebKit for TAB from editor to skip displayNode | |
486 | ||
487 | // Replace the display widget with edit widget, leaving them both displayed for a brief time so that | |
488 | // focus can be shifted without incident. (browser may needs some time to render the editor.) | |
489 | setTimeout(lang.hitch(ww, function(){ | |
490 | this.focus(); // both nodes are showing, so we can switch focus safely | |
491 | this._resetValue = this.getValue(); | |
492 | }), 0); | |
493 | }, | |
494 | ||
495 | _onBlur: function(){ | |
496 | // summary: | |
497 | // Called when focus moves outside the InlineEditBox. | |
498 | // Performs garbage collection. | |
499 | // tags: | |
500 | // private | |
501 | ||
502 | this.inherited(arguments); | |
503 | if(!this.editing){ | |
504 | /* causes IE focus problems, see TooltipDialog_a11y.html... | |
505 | setTimeout(lang.hitch(this, function(){ | |
506 | if(this.wrapperWidget){ | |
507 | this.wrapperWidget.destroy(); | |
508 | delete this.wrapperWidget; | |
509 | } | |
510 | }), 0); | |
511 | */ | |
512 | } | |
513 | }, | |
514 | ||
515 | destroy: function(){ | |
516 | if(this.wrapperWidget && !this.wrapperWidget._destroyed){ | |
517 | this.wrapperWidget.destroy(); | |
518 | delete this.wrapperWidget; | |
519 | } | |
520 | this.inherited(arguments); | |
521 | }, | |
522 | ||
523 | _showText: function(/*Boolean*/ focus){ | |
524 | // summary: | |
525 | // Revert to display mode, and optionally focus on display node | |
526 | // tags: | |
527 | // private | |
528 | ||
529 | var ww = this.wrapperWidget; | |
530 | domStyle.set(ww.domNode, { position: "absolute", visibility: "hidden", opacity: "0" }); // hide the editor from mouse/keyboard events | |
531 | domStyle.set(this.displayNode, { position: this._savedPosition, opacity: this._savedOpacity }); // make the original text visible | |
532 | domAttr.set(this.displayNode, "tabIndex", this._savedTabIndex); | |
533 | if(focus){ | |
534 | fm.focus(this.displayNode); | |
535 | } | |
536 | }, | |
537 | ||
538 | save: function(/*Boolean*/ focus){ | |
539 | // summary: | |
540 | // Save the contents of the editor and revert to display mode. | |
541 | // focus: Boolean | |
542 | // Focus on the display mode text | |
543 | // tags: | |
544 | // private | |
545 | ||
546 | if(this.disabled || !this.editing){ return; } | |
547 | this._set('editing', false); | |
548 | ||
549 | var ww = this.wrapperWidget; | |
550 | var value = ww.getValue(); | |
551 | this.set('value', value); // display changed, formatted value | |
552 | ||
553 | this._showText(focus); // set focus as needed | |
554 | }, | |
555 | ||
556 | setValue: function(/*String*/ val){ | |
557 | // summary: | |
558 | // Deprecated. Use set('value', ...) instead. | |
559 | // tags: | |
560 | // deprecated | |
561 | kernel.deprecated("dijit.InlineEditBox.setValue() is deprecated. Use set('value', ...) instead.", "", "2.0"); | |
562 | return this.set("value", val); | |
563 | }, | |
564 | ||
565 | _setValueAttr: function(/*String*/ val){ | |
566 | // summary: | |
567 | // Hook to make set("value", ...) work. | |
568 | // Inserts specified HTML value into this node, or an "input needed" character if node is blank. | |
569 | ||
570 | val = lang.trim(val); | |
571 | var renderVal = this.renderAsHtml ? val : val.replace(/&/gm, "&").replace(/</gm, "<").replace(/>/gm, ">").replace(/"/gm, """).replace(/\n/g, "<br>"); | |
572 | this.displayNode.innerHTML = renderVal || this.noValueIndicator; | |
573 | this._set("value", val); | |
574 | ||
575 | if(this._started){ | |
576 | // tell the world that we have changed | |
577 | setTimeout(lang.hitch(this, "onChange", val), 0); // setTimeout prevents browser freeze for long-running event handlers | |
578 | } | |
579 | // contextual (auto) text direction depends on the text value | |
580 | if(this.textDir == "auto"){ | |
581 | this.applyTextDir(this.displayNode, this.displayNode.innerText); | |
582 | } | |
583 | }, | |
584 | ||
585 | getValue: function(){ | |
586 | // summary: | |
587 | // Deprecated. Use get('value') instead. | |
588 | // tags: | |
589 | // deprecated | |
590 | kernel.deprecated("dijit.InlineEditBox.getValue() is deprecated. Use get('value') instead.", "", "2.0"); | |
591 | return this.get("value"); | |
592 | }, | |
593 | ||
594 | cancel: function(/*Boolean*/ focus){ | |
595 | // summary: | |
596 | // Revert to display mode, discarding any changes made in the editor | |
597 | // tags: | |
598 | // private | |
599 | ||
600 | if(this.disabled || !this.editing){ return; } | |
601 | this._set('editing', false); | |
602 | ||
603 | // tell the world that we have no changes | |
604 | setTimeout(lang.hitch(this, "onCancel"), 0); // setTimeout prevents browser freeze for long-running event handlers | |
605 | ||
606 | this._showText(focus); | |
607 | }, | |
608 | _setTextDirAttr: function(/*String*/ textDir){ | |
609 | // summary: | |
610 | // Setter for textDir. | |
611 | // description: | |
612 | // Users shouldn't call this function; they should be calling | |
613 | // set('textDir', value) | |
614 | // tags: | |
615 | // private | |
616 | if(!this._created || this.textDir != textDir){ | |
617 | this._set("textDir", textDir); | |
618 | this.applyTextDir(this.displayNode, this.displayNode.innerText); | |
619 | this.displayNode.align = this.dir == "rtl" ? "right" : "left"; //fix the text alignment | |
620 | } | |
621 | } | |
622 | }); | |
623 | ||
624 | InlineEditBox._InlineEditor = InlineEditor; // for monkey patching | |
625 | ||
626 | return InlineEditBox; | |
627 | }); |