Univention Bugzilla – Attachment 4727 Details for
Bug 26214
MultiInput-Widgets informieren Form nicht über erfolgreiche Initialisierung
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
Patch für umc-frontend
umc.patch (text/plain), 20.13 KB, created by
Alexander Kläser
on 2012-10-19 22:02:23 CEST
(
hide
)
Description:
Patch für umc-frontend
Filename:
MIME Type:
Creator:
Alexander Kläser
Created:
2012-10-19 22:02:23 CEST
Size:
20.13 KB
patch
obsolete
>Index: umc/widgets/Form.js >=================================================================== >--- umc/widgets/Form.js (Revision 36481) >+++ umc/widgets/Form.js (Arbeitskopie) >@@ -26,19 +26,19 @@ > * /usr/share/common-licenses/AGPL-3; if not, see > * <http://www.gnu.org/licenses/>. > */ >-/*global define */ >+/*global define require console*/ > > define([ > "dojo/_base/declare", > "dojo/_base/lang", > "dojo/_base/array", > "dojo/Deferred", >- "dojo/on", >+ "dojo/promise/all", > "dojo/dom-style", > "dijit/form/Form", > "umc/tools", > "umc/render" >-], function(declare, lang, array, Deferred, on, style, Form, tools, render) { >+], function(declare, lang, array, Deferred, all, style, Form, tools, render) { > > // in order to break circular dependencies (umc.dialog needs a Form and > // Form needs umc/dialog), we define umc/dialog as an empty object and >@@ -121,13 +121,14 @@ > > //'class': 'umcNoBorder', > >- _initializingElements: 0, >+ _allReady: null, > >- _initializedDeferred: null, >- > postMixInProperties: function() { > this.inherited(arguments); > >+ // initialize with empty list >+ this._allReady = []; >+ > // in case no layout is specified and no content, either, create one automatically > if ((!this.layout || !this.layout.length) && !this.content) { > this.layout = []; >@@ -183,8 +184,6 @@ > buildRendering: function() { > this.inherited(arguments); > >- this._initializedDeferred = new Deferred(); >- > if (this.scrollable) { > style.set(this.containerNode, { > overflow: 'auto' >@@ -225,47 +224,19 @@ > } > } > >- >- // send an event when all dynamic elements have been initialized >- this._initializingElements = 0; >- //console.log('# Form.buildRendering()'); >- tools.forIn(this._widgets, function(iname, iwidget) { >- // only consider elements that load values dynamically >- //console.log('# iwidget:', iwidget.name); >- if ('onValuesLoaded' in iwidget && !(iwidget._valuesLoaded && !iwidget._deferredOrValues)) { >- // widget values have not been loaded completely so far >- //console.log('# -> has event "valuesLoaded"'); >- ++this._initializingElements; >- on.once(iwidget, 'valuesLoaded', lang.hitch(this, function() { >- //console.log('# -> valuesLoaded:', iwidget.name, iwidget.get('value')); >- // decrement the internal counter >- --this._initializingElements; >- //console.log('# _initializingElements:', this._initializingElements); >- >- // send event when the last element has been initialized >- if (0 === this._initializingElements) { >- this._initializedDeferred.resolve(); >- } >- })); >- } >- }, this); >- >- // maybe all elements are already initialized >- if (!this._initializingElements) { >- this._initializedDeferred.resolve(); >- } >- >+ this._updateAllReady(); > }, > > startup: function() { >+ //console.log('### Form: startup - container:', this._container); > this.inherited(arguments); > if (this._container) { > // call the containers startup function if necessary > this._container.startup(); > } >- this._initializedDeferred.then(lang.hitch(this, function() { >+ this.ready().then(lang.hitch(this, function() { >+ //console.log('### Form: all ready'); > this.onValuesInitialized(); >- //console.log('# valuesInitialized'); > })); > }, > >@@ -553,8 +524,31 @@ > dialog.notify(error_msg); > } > })); >- } >+ }, > >+ _updateAllReady: function() { >+ // wait for all widgets to be ready >+ this._allReady = []; >+ //console.log('### Form: iterate over widgets.ready'); >+ tools.forIn(this._widgets, function(iname, iwidget) { >+ //console.log('### ' + iname + ' -> ', iwidget.ready ? iwidget.ready() : null); >+ this._allReady.push(iwidget.ready ? iwidget.ready() : null); >+ }, this); >+ }, >+ >+ ready: function() { >+ // update the internal list in order to wait until everybody is ready >+ if (!this._allReady.length) { >+ _updateAllReady(); >+ } >+ var ret = all(this._allReady); >+ >+ // empty list when all widgets are ready >+ ret.then(lang.hitch(this, function() { >+ this._allReady = []; >+ })); >+ return ret; >+ } > }); > }); > >Index: umc/widgets/MultiInput.js >=================================================================== >--- umc/widgets/MultiInput.js (Revision 36481) >+++ umc/widgets/MultiInput.js (Arbeitskopie) >@@ -32,13 +32,15 @@ > "dojo/_base/declare", > "dojo/_base/lang", > "dojo/_base/array", >+ "dojo/Deferred", >+ "dojo/promise/all", > "dijit/form/Button", > "umc/tools", > "umc/render", > "umc/widgets/ContainerWidget", > "umc/widgets/_FormWidgetMixin", > "umc/widgets/LabelPane" >-], function(declare, lang, array, Button, tools, render, ContainerWidget, _FormWidgetMixin, LabelPane) { >+], function(declare, lang, array, Deferred, all, Button, tools, render, ContainerWidget, _FormWidgetMixin, LabelPane) { > return declare("umc.widgets.MultiInput", [ ContainerWidget, _FormWidgetMixin ], { > // summary: > // Widget for a small list of simple and complex entries. An entry can be one or >@@ -77,6 +79,12 @@ > > _lastDepends: null, > >+ _valuesLoaded: false, >+ >+ _readyDeferred: null, >+ >+ _startupDeferred: null, >+ > _createHandler: function(ifunc) { > // This handler will be called by all subwidgets of the MultiInput widget. > // When the first request comes in, we will execute the function to compute >@@ -106,8 +114,14 @@ > postMixInProperties: function() { > this.inherited(arguments); > >+ // delete the size class > this.sizeClass = null; > >+ // the _readyDeferred is being resolved as soon as everything has been set up >+ this._readyDeferred = new Deferred(); >+ >+ this._startupDeferred = new Deferred(); >+ > // check the property 'subtypes' > tools.assert(this.subtypes instanceof Array, > 'umc/widgets/ContainerWidget: The property subtypes needs to be a string or an array of strings: ' + this.subtypes); >@@ -149,6 +163,12 @@ > this._appendElements(1); > }, > >+ startup: function() { >+ this.inherited(arguments); >+ >+ this._startupDeferred.resolve(); >+ }, >+ > _loadValues: function(depends) { > // delegate the call to _loadValues to all widgets > this._lastDepends = depends; >@@ -316,6 +336,11 @@ > return; > } > >+ // initiate a new Deferred object in case there is none already pending >+ if (this._readyDeferred.isFulfilled()) { >+ this._readyDeferred = new Deferred(); >+ } >+ > // remove the 'new' button > this._removeNewButton(); > >@@ -403,7 +428,7 @@ > // add row > this._widgets.push(visibleWidgets); > this._rowContainers.push(rowContainer); >- rowContainer.startup(); >+ this._startupDeferred.then(lang.hitch(rowContainer, 'startup')); > this.addChild(rowContainer); > > // call the _loadValues method by hand >@@ -415,6 +440,21 @@ > }, this); > } > >+ // wait for all widgets to be ready >+ var allReady = []; >+ var i, j; >+ for (i = 0; i < this._widgets.length; ++i) { >+ for (j = 0; j < this._widgets[i].length; ++j) { >+ //console.log(lang.replace('### MultiInput: widget[{0}][{1}]: waiting -> ', [i, j]), this._widgets[i][j].ready()); >+ allReady.push(this._widgets[i][j].ready ? this._widgets[i][j].ready() : null); >+ } >+ } >+ all(allReady).then(lang.hitch(this, function() { >+ //console.log('### MultiInput: all resolved'); >+ this._readyDeferred.resolve(); >+ this.onValuesLoaded(); >+ })); >+ > // add the new button > if (this._nRenderedElements < this.max) { > this._addNewButton(); >@@ -494,6 +534,19 @@ > if (this._widget) { > tools.delegateCall(this, arguments, this._widget); > } >+ }, >+ >+ onValuesLoaded: function(values) { >+ // summary: >+ // This event is triggered when all values (static and dynamic) have been loaded. >+ // values: >+ // Array containing all dynamic and static values. >+ }, >+ >+ // ready: >+ // Similiar to `umc/widgets/_FormWidgetMixin:ready`. >+ ready: function() { >+ return this._readyDeferred; > } > }); > }); >Index: umc/widgets/_SelectMixin.js >=================================================================== >--- umc/widgets/_SelectMixin.js (Revision 36481) >+++ umc/widgets/_SelectMixin.js (Arbeitskopie) >@@ -34,13 +34,12 @@ > "dojo/_base/array", > "dojo/Deferred", > "dojo/when", >- "dojo/on", > "dojo/json", > "dojo/Stateful", > // TODO: should use dojo/store/ > "dojo/data/ItemFileWriteStore", > "umc/tools" >-], function(declare, lang, array, Deferred, when, on, json, Stateful, ItemFileWriteStore, tools) { >+], function(declare, lang, array, Deferred, when, json, Stateful, ItemFileWriteStore, tools) { > return declare("umc.widgets._SelectMixin", Stateful, { > // umcpCommand: > // Reference to the umcpCommand the widget should use. >@@ -105,6 +104,8 @@ > > _deferredOrValues: null, > >+ _readyDeferred: null, >+ > _createStore: function() { > return new ItemFileWriteStore({ > data: { >@@ -128,6 +129,10 @@ > this.inherited(arguments); > > this._saveInitialValue(); >+ >+ // the _readyDeferred is being resolved as soon as everything has been set up >+ //console.log('### _SelectMixin ['+this.name+']: initiate _readyDeferred'); >+ this._readyDeferred = new Deferred(); > }, > > postCreate: function() { >@@ -382,7 +387,7 @@ > }, > > _loadValues: function(/*Object?*/ _dependValues) { >- //console.log('###', this.name, ' _loadValues(', _dependValues, ')'); >+ //console.log('### _SelectMixin ['+this.name+']: _loadValues'); > this._valuesLoaded = true; > > // unify `depends` property to be an array >@@ -404,6 +409,7 @@ > > // only load dynamic values in case all dependencies are fullfilled > if (dependList.length != nDepValues) { >+ //console.log('### _SelectMixin ['+this.name+']: return'); > return; > } > >@@ -420,9 +426,16 @@ > // block concurrent events for value loading > if (this._deferredOrValues) { > // another request is pending >+ //console.log('### _SelectMixin ['+this.name+']: return (2)'); > return; > } > >+ // initiate a new Deferred object in case there is none already pending >+ if (this._readyDeferred.isFulfilled()) { >+ //console.log('### _SelectMixin ['+this.name+']: re-initiate _readyDeferred'); >+ this._readyDeferred = new Deferred(); >+ } >+ > // get dynamic values > var func = tools.stringOrFunction(this.dynamicValues, this.umcpCommand); > var deferredOrValues = func(params); >@@ -439,9 +452,11 @@ > this._clearValues(); > this._setStaticValues(); > this._setDynamicValues(res); >- this.onDynamicValuesLoaded(res); > > // values have been loaded >+ //console.log('### _SelectMixin ['+this.name+']: resolved _readyDeferred'); >+ this._readyDeferred.resolve(this.getAllItems()); >+ this.onDynamicValuesLoaded(res); > this.onValuesLoaded(this.getAllItems()); > > // unblock value loading >@@ -452,6 +467,8 @@ > this._setStaticValues(); > > // error handler >+ //console.log('### _SelectMixin ['+this.name+']: resolved _readyDeferred'); >+ this._readyDeferred.resolve([]); > this.onDynamicValuesLoaded([]); > this.onValuesLoaded(this.getAllItems()); > >@@ -465,6 +482,8 @@ > this._setStaticValues(); > > // values have been loaded >+ //console.log('### _SelectMixin ['+this.name+']: resolved _readyDeferred'); >+ this._readyDeferred.resolve(this.getAllItems()); > this.onValuesLoaded(this.getAllItems()); > > // unblock value loading >@@ -532,6 +551,13 @@ > if (this._valuesLoaded) { > this._loadValues(); > } >+ }, >+ >+ // ready: >+ // Returns null or a Deferred which resolves as soon as any >+ // loading activity of the widget is finished. >+ ready: function() { >+ return this._readyDeferred; > } > }); > }); >Index: umc/widgets/MixedInput.js >=================================================================== >--- umc/widgets/MixedInput.js (Revision 36481) >+++ umc/widgets/MixedInput.js (Arbeitskopie) >@@ -31,6 +31,7 @@ > define([ > "dojo/_base/declare", > "dojo/_base/lang", >+ "dojo/Deferred", > "dojo/json", > "dijit/layout/ContentPane", > "umc/tools", >@@ -38,7 +39,7 @@ > "umc/widgets/TextBox", > "umc/widgets/ComboBox", > "umc/widgets/CheckBox" >-], function(declare, lang, json, ContentPane, tools, _FormWidgetMixin) { >+], function(declare, lang, Deferred, json, ContentPane, tools, _FormWidgetMixin) { > return declare("umc.widgets.MixedInput", [ ContentPane, _FormWidgetMixin ], { > // umcpCommand: > // Reference to the umcpCommand the widget should use. >@@ -74,6 +75,8 @@ > > style: 'padding: 0', > >+ _readyDeferred: null, >+ > constructor: function(/*Object*/ props) { > // mixin in the 'disabled' property > props.disabled = this.disabled; >@@ -94,6 +97,8 @@ > > this._userProperties.sizeClass = this.sizeClass; > this.sizeClass = null; >+ >+ this._readyDeferred = new Deferred(); > }, > > buildRendering: function() { >@@ -135,6 +140,11 @@ > return; > } > >+ // initiate a new Deferred object in case there is none already pending >+ if (this._readyDeferred.isFulfilled()) { >+ this._readyDeferred = new Deferred(); >+ } >+ > // mixin additional options for the UMCP command > if (this.dynamicOptions && typeof this.dynamicOptions == "object") { > lang.mixin(params, this.dynamicOptions); >@@ -199,6 +209,7 @@ > this._widget.startup(); > > this.onValuesLoaded(); >+ this._readyDeferred.resolve(); > }, > > _setValueAttr: function(newVal) { >@@ -249,6 +260,13 @@ > if (lang.getObject('_widget.focus', false, this)) { > this._widget.focus(); > } >+ }, >+ >+ // ready: >+ // Returns null or a Deferred which resolves as soon as any >+ // loading activity of the widget is finished. >+ ready: function() { >+ return this._readyDeferred; > } > }); > }); >Index: umc/widgets/LabelPane.js >=================================================================== >--- umc/widgets/LabelPane.js (Revision 36481) >+++ umc/widgets/LabelPane.js (Arbeitskopie) >@@ -31,13 +31,14 @@ > define([ > "dojo/_base/declare", > "dojo/_base/lang", >+ "dojo/Deferred", > "dojo/dom-class", > "dojo/dom-attr", > "dijit/_WidgetBase", > "dijit/_TemplatedMixin", > "dijit/_Container", > "umc/tools" >-], function(declare, lang, domClass, attr, _WidgetBase, _TemplatedMixin, _Container, tools) { >+], function(declare, lang, Deferred, domClass, attr, _WidgetBase, _TemplatedMixin, _Container, tools) { > lang.extend(_WidgetBase, { > // isLabelDisplayed: Boolean? > // If specified as true, LabelPane assumes that the widget itself will take >@@ -81,6 +82,18 @@ > > labelNodeRight: null, > >+ _startupDeferred: null, >+ >+ constructor: function(params) { >+ this._startupDeferred = new Deferred(); >+ >+ // lang._mixin() would not work sometimes, leaving this.content empty, see >+ // https://forge.univention.org/bugzilla/show_bug.cgi?id=26214#c3 >+ tools.forIn(params, function(ikey, ival) { >+ this[ikey] = ival; >+ }, this); >+ }, >+ > postMixInProperties: function() { > this.inherited(arguments); > >@@ -120,6 +133,15 @@ > domClass.toggle(this.domNode, 'dijitHidden', this.content.visible === false); > }, > >+ startup: function() { >+ this.inherited(arguments); >+ >+ this._startupDeferred.resolve(); >+ if (lang.getObject('content.startup', false, this)) { >+ this.content.startup(); >+ } >+ }, >+ > _setLabelAttr: function(label) { > if (lang.getObject('content.isLabelDisplayed', false, this)) { > // the widget displays the label itself >@@ -164,6 +186,12 @@ > else if (lang.getObject('domNode', false, content) && lang.getObject('declaredClass', false, content)) { > this.contentNode.innerHTML = ''; > this.addChild(content); >+ if (content.startup) { >+ this._startupDeferred.then(function() { >+ // call widget's startup after we have been started up >+ content.startup(); >+ }); >+ } > } > this.set( 'disabled', this.disabled ); > }, >Index: umc/widgets/ComplexInput.js >=================================================================== >--- umc/widgets/ComplexInput.js (Revision 36481) >+++ umc/widgets/ComplexInput.js (Arbeitskopie) >@@ -57,6 +57,13 @@ > > umcpCommand: tools.umcpCommand, > >+ _allReady: null, >+ >+ constructor: function() { >+ // initialize with empty list >+ this._allReady = []; >+ }, >+ > buildRendering: function() { > this.inherited(arguments); > >@@ -101,6 +108,7 @@ > } > }, this); > >+ this._updateAllReady(); > }, > > _getValueAttr: function() { >@@ -127,6 +135,28 @@ > var iisValid = areValid instanceof Array ? areValid[i] : areValid; > this._widgets[ iname ].setValid( iisValid, imessage ); > }, this ); >+ }, >+ >+ _updateAllReady: function() { >+ // wait for all widgets to be ready >+ this._allReady = []; >+ tools.forIn(this._widgets, function(iname, iwidget) { >+ this._allReady.push(iwidget.ready ? iwidget.ready() : null); >+ }, this); >+ }, >+ >+ ready: function() { >+ // update the internal list in order to wait until everybody is ready >+ if (!this._allReady.length) { >+ _updateAllReady(); >+ } >+ var ret = all(this._allReady); >+ >+ // empty list when all widgets are ready >+ ret.then(lang.hitch(this, function() { >+ this._allReady = []; >+ })); >+ return ret; > } > }); > }); >Index: umc/widgets/LoginDialog.js >=================================================================== >--- umc/widgets/LoginDialog.js (Revision 36481) >+++ umc/widgets/LoginDialog.js (Arbeitskopie) >@@ -88,7 +88,6 @@ > style: 'margin-left: auto; margin-right: auto; margin-top: 1em; width: 280px;', > content: '' > }); >- this._text.placeAt(this.containerNode, 'first'); > > // create the language_combobox > this._languageBox = new ComboBox({ >@@ -100,14 +99,6 @@ > label: _('Language'), > content: this._languageBox > }); >- // we need to manually startup the widgets >- this._languageBox.startup(); >- this._languageLabel.startup(); >- this._languageLabel.placeAt('umc_LoginDialog_FormContainer'); >- // register onchange event >- this.own(this._languageBox.watch('value', function(name, oldLang, newLang) { >- i18nTools.setLanguage(newLang); >- })); > > // automatically resize the DialogUnderlay container > this.own(on(win.global, 'resize', lang.hitch(this, function() { >@@ -117,6 +108,26 @@ > }))); > }, > >+ postCreate: function() { >+ this.inherited(arguments); >+ >+ this._text.placeAt(this.containerNode, 'first'); >+ this._languageLabel.placeAt('umc_LoginDialog_FormContainer'); >+ }, >+ >+ startup: function() { >+ this.inherited(arguments); >+ >+ // we need to manually startup the widgets >+ this._languageBox.startup(); >+ this._languageLabel.startup(); >+ >+ // register onchange event >+ this.own(this._languageBox.watch('value', function(name, oldLang, newLang) { >+ i18nTools.setLanguage(newLang); >+ })); >+ }, >+ > _initForm: function() { > // wait until the iframe is completely loaded > setTimeout(lang.hitch(this, function() { >Index: tests/depends.html >=================================================================== >--- tests/depends.html (Revision 36481) >+++ tests/depends.html (Arbeitskopie) >@@ -30,7 +30,7 @@ > async: true > }; > </script> >- <script type="text/javascript" src="/univention-management-console/js/dojo/dojo.js"></script> >+ <script type="text/javascript" src="/univention-management-console/js/dojo/dojo.js.uncompressed.js"></script> > <script type="text/javascript"> > require([ > "dojo/_base/window", >@@ -244,6 +244,27 @@ > }, { > type: 'Text', > label: '', >+ name: 'test8', >+ content: '<h1>Test case: MultiInput w/ComboBox & dynamicValues -> check for onValuesLoaded</h1>' >+ }, { >+ type: 'Text', >+ label: '', >+ name: 'Text8', >+ style: 'color:red; font-weight: bold;', >+ content: 'values are loading...' >+ }, { >+ type: 'MultiInput', >+ name: 'MultiInput8', >+ subtypes: [{ >+ type: 'ComboBox', >+ dynamicOptions: { _data: valuesColors }, >+ dynamicValues: valuesAsync, >+ label: 'Test' >+ }], >+ label: 'MultiInput' >+ }, { >+ type: 'Text', >+ label: '', > name: 'test7', > content: '<h1>Test case: disabled ComboBoxes with staticValues and dynamicValues</h1>' > }, { >@@ -300,9 +321,13 @@ > 'test4', ['MultiInput4-1', 'ComboBox4-1'], > 'test5', ['MultiSelect5-1', 'ComboBox5-1'], > 'test6', 'MultiInput6', >- 'test7', 'MultiInput7-1', 'MultiInput7-2', 'ComboBox7-1', 'ComboBox7-2' >+ 'test7', 'MultiInput7-1', 'MultiInput7-2', 'ComboBox7-1', 'ComboBox7-2', >+ 'test8', 'MultiInput8', 'Text8' > ] > }); >+ /*form.getWidget('MultiInput8').ready().then(function() { >+ form.getWidget('Text8').set('content', 'Values have been loaded succesfully'); >+ });*/ > form.startup(); > form.placeAt(win.body()); > });
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 26214
:
4209
| 4727 |
4728