[MediaWiki-commits] [Gerrit] Implement in View a declarative event map for DOM events - change (mediawiki...Mantle)
Kaldari has uploaded a new change for review. https://gerrit.wikimedia.org/r/183766 Change subject: Implement in View a declarative event map for DOM events .. Implement in View a declarative event map for DOM events Inspired by backbone.js Advantages: * Event handling definitions and code are defined in the same place, and handlers are defined at the root view level resulting in cleaner more comprehensible code overall * Uses event delegation, thus being more efficient that individual manual events. Previous discussion/patch: https://gerrit.wikimedia.org/r/#/c/180834/ Examples of views with this new feature: * https://gerrit.wikimedia.org/r/#/c/180835/ * https://gerrit.wikimedia.org/r/#/c/180836/ * https://gerrit.wikimedia.org/r/#/c/180837/ Change-Id: I22f2e9e12e28542a5b136bfbf478a47fc657ef3e (cherry picked from commit 40dd328e8e181620ee5c0e6bd1ec96c5920efcd7) --- M javascripts/common/View.js M tests/javascripts/common/test_View.js 2 files changed, 167 insertions(+), 3 deletions(-) git pull ssh://gerrit.wikimedia.org:29418/mediawiki/extensions/Mantle refs/changes/66/183766/1 diff --git a/javascripts/common/View.js b/javascripts/common/View.js index 1fcec8d..35ca9a8 100644 --- a/javascripts/common/View.js +++ b/javascripts/common/View.js @@ -1,6 +1,22 @@ ( function( M, $ ) { - var EventEmitter = M.require( 'eventemitter' ), View; + var EventEmitter = M.require( 'eventemitter' ), + View, + // Cached regex to split keys for `delegate`. + delegateEventSplitter = /^(\S+)\s*(.*)$/, + idCounter = 0; + + /** +* Generate a unique integer id (unique within the entire client session). +* Useful for temporary DOM ids. +* @ignore +* @param {String} prefix Prefix to be used when generating the id. +* @returns {String} +*/ + function uniqueId( prefix ) { + var id = ++idCounter + ''; + return prefix ? prefix + id : id; + } /** * Should be extended using extend(). @@ -28,6 +44,31 @@ * * append(), prepend(), before(), after() can be used to modify $el. on() * can be used to bind events. +* +* You can also use declarative DOM events binding by specifying an `events` +* map on the class. The keys will be 'event selector' and the value can be +* either the name of a method to call, or a function. All methods and +* functions will be executed on the context of the View. +* +* Inspired from Backbone.js +* https://github.com/jashkenas/backbone/blob/master/backbone.js#L1128 +* +* @example +* code +* var MyComponent = View.extend( { +* events: { +* 'mousedown .title': 'edit', +* 'click .button': 'save', +* 'click .open': function(e) { ... } +* }, +* edit: function ( ev ) { +* //... +* }, +* save: function ( ev ) { +* //... +* } +* } ); +* /code * * @class View * @extends EventEmitter @@ -84,6 +125,11 @@ defaults: {}, /** +* Default events map +*/ + events: null, + + /** * Run once during construction to set up the View * @method * @param {Object} options Object passed to the constructor. @@ -109,6 +155,10 @@ this.options = options; this.render( options ); + + // Assign a unique id for dom events binding/unbinding + this.cid = uniqueId( 'view' ); + this.delegateEvents(); }, /** @@ -154,9 +204,88 @@ * @param {string} query A jQuery CSS selector. * @return {jQuery.Object} jQuery object containing results of the search. */ - $: function( query ) { - return this.$el.find( query ); + $: function(query) { + return this.$el.find(query); + }, + + /** +* Set callbacks, where `this.events` is a hash of +* +* {event selector: callback} +* +* { +* 'mousedown .title': 'edit', +* 'click .button': 'save', +* 'click .open': function(e) { ... } +* } +* +* pairs. Callbacks will be bound to the view, with `this` set properly. +* Uses event delegation for efficiency. +
[MediaWiki-commits] [Gerrit] Implement in View a declarative event map for DOM events - change (mediawiki...Mantle)
jenkins-bot has submitted this change and it was merged. Change subject: Implement in View a declarative event map for DOM events .. Implement in View a declarative event map for DOM events Inspired by backbone.js Advantages: * Event handling definitions and code are defined in the same place, and handlers are defined at the root view level resulting in cleaner more comprehensible code overall * Uses event delegation, thus being more efficient that individual manual events. Previous discussion/patch: https://gerrit.wikimedia.org/r/#/c/180834/ Examples of views with this new feature: * https://gerrit.wikimedia.org/r/#/c/180835/ * https://gerrit.wikimedia.org/r/#/c/180836/ * https://gerrit.wikimedia.org/r/#/c/180837/ Change-Id: I22f2e9e12e28542a5b136bfbf478a47fc657ef3e (cherry picked from commit 40dd328e8e181620ee5c0e6bd1ec96c5920efcd7) --- M javascripts/common/View.js M tests/javascripts/common/test_View.js 2 files changed, 167 insertions(+), 3 deletions(-) Approvals: MaxSem: Looks good to me, approved jenkins-bot: Verified diff --git a/javascripts/common/View.js b/javascripts/common/View.js index 1fcec8d..35ca9a8 100644 --- a/javascripts/common/View.js +++ b/javascripts/common/View.js @@ -1,6 +1,22 @@ ( function( M, $ ) { - var EventEmitter = M.require( 'eventemitter' ), View; + var EventEmitter = M.require( 'eventemitter' ), + View, + // Cached regex to split keys for `delegate`. + delegateEventSplitter = /^(\S+)\s*(.*)$/, + idCounter = 0; + + /** +* Generate a unique integer id (unique within the entire client session). +* Useful for temporary DOM ids. +* @ignore +* @param {String} prefix Prefix to be used when generating the id. +* @returns {String} +*/ + function uniqueId( prefix ) { + var id = ++idCounter + ''; + return prefix ? prefix + id : id; + } /** * Should be extended using extend(). @@ -28,6 +44,31 @@ * * append(), prepend(), before(), after() can be used to modify $el. on() * can be used to bind events. +* +* You can also use declarative DOM events binding by specifying an `events` +* map on the class. The keys will be 'event selector' and the value can be +* either the name of a method to call, or a function. All methods and +* functions will be executed on the context of the View. +* +* Inspired from Backbone.js +* https://github.com/jashkenas/backbone/blob/master/backbone.js#L1128 +* +* @example +* code +* var MyComponent = View.extend( { +* events: { +* 'mousedown .title': 'edit', +* 'click .button': 'save', +* 'click .open': function(e) { ... } +* }, +* edit: function ( ev ) { +* //... +* }, +* save: function ( ev ) { +* //... +* } +* } ); +* /code * * @class View * @extends EventEmitter @@ -84,6 +125,11 @@ defaults: {}, /** +* Default events map +*/ + events: null, + + /** * Run once during construction to set up the View * @method * @param {Object} options Object passed to the constructor. @@ -109,6 +155,10 @@ this.options = options; this.render( options ); + + // Assign a unique id for dom events binding/unbinding + this.cid = uniqueId( 'view' ); + this.delegateEvents(); }, /** @@ -154,9 +204,88 @@ * @param {string} query A jQuery CSS selector. * @return {jQuery.Object} jQuery object containing results of the search. */ - $: function( query ) { - return this.$el.find( query ); + $: function(query) { + return this.$el.find(query); + }, + + /** +* Set callbacks, where `this.events` is a hash of +* +* {event selector: callback} +* +* { +* 'mousedown .title': 'edit', +* 'click .button': 'save', +* 'click .open': function(e) { ... } +* } +* +* pairs. Callbacks will be bound to the view, with `this` set properly. +* Uses event delegation for efficiency. +* Omitting the selector binds the event to
[MediaWiki-commits] [Gerrit] Implement in View a declarative event map for DOM events - change (mediawiki...Mantle)
jenkins-bot has submitted this change and it was merged. Change subject: Implement in View a declarative event map for DOM events .. Implement in View a declarative event map for DOM events Inspired by backbone.js Advantages: * Event handling definitions and code are defined in the same place, and handlers are defined at the root view level resulting in cleaner more comprehensible code overall * Uses event delegation, thus being more efficient that individual manual events. Previous discussion/patch: https://gerrit.wikimedia.org/r/#/c/180834/ Examples of views with this new feature: * https://gerrit.wikimedia.org/r/#/c/180835/ * https://gerrit.wikimedia.org/r/#/c/180836/ * https://gerrit.wikimedia.org/r/#/c/180837/ Change-Id: I22f2e9e12e28542a5b136bfbf478a47fc657ef3e --- M javascripts/common/View.js M tests/javascripts/common/test_View.js 2 files changed, 167 insertions(+), 3 deletions(-) Approvals: Jdlrobson: Looks good to me, approved Phuedx: Looks good to me, but someone else must approve jenkins-bot: Verified diff --git a/javascripts/common/View.js b/javascripts/common/View.js index 1fcec8d..35ca9a8 100644 --- a/javascripts/common/View.js +++ b/javascripts/common/View.js @@ -1,6 +1,22 @@ ( function( M, $ ) { - var EventEmitter = M.require( 'eventemitter' ), View; + var EventEmitter = M.require( 'eventemitter' ), + View, + // Cached regex to split keys for `delegate`. + delegateEventSplitter = /^(\S+)\s*(.*)$/, + idCounter = 0; + + /** +* Generate a unique integer id (unique within the entire client session). +* Useful for temporary DOM ids. +* @ignore +* @param {String} prefix Prefix to be used when generating the id. +* @returns {String} +*/ + function uniqueId( prefix ) { + var id = ++idCounter + ''; + return prefix ? prefix + id : id; + } /** * Should be extended using extend(). @@ -28,6 +44,31 @@ * * append(), prepend(), before(), after() can be used to modify $el. on() * can be used to bind events. +* +* You can also use declarative DOM events binding by specifying an `events` +* map on the class. The keys will be 'event selector' and the value can be +* either the name of a method to call, or a function. All methods and +* functions will be executed on the context of the View. +* +* Inspired from Backbone.js +* https://github.com/jashkenas/backbone/blob/master/backbone.js#L1128 +* +* @example +* code +* var MyComponent = View.extend( { +* events: { +* 'mousedown .title': 'edit', +* 'click .button': 'save', +* 'click .open': function(e) { ... } +* }, +* edit: function ( ev ) { +* //... +* }, +* save: function ( ev ) { +* //... +* } +* } ); +* /code * * @class View * @extends EventEmitter @@ -84,6 +125,11 @@ defaults: {}, /** +* Default events map +*/ + events: null, + + /** * Run once during construction to set up the View * @method * @param {Object} options Object passed to the constructor. @@ -109,6 +155,10 @@ this.options = options; this.render( options ); + + // Assign a unique id for dom events binding/unbinding + this.cid = uniqueId( 'view' ); + this.delegateEvents(); }, /** @@ -154,9 +204,88 @@ * @param {string} query A jQuery CSS selector. * @return {jQuery.Object} jQuery object containing results of the search. */ - $: function( query ) { - return this.$el.find( query ); + $: function(query) { + return this.$el.find(query); + }, + + /** +* Set callbacks, where `this.events` is a hash of +* +* {event selector: callback} +* +* { +* 'mousedown .title': 'edit', +* 'click .button': 'save', +* 'click .open': function(e) { ... } +* } +* +* pairs. Callbacks will be bound to the view, with `this` set properly. +* Uses event delegation for efficiency. +* Omitting the selector binds the event to `this.el`. +
[MediaWiki-commits] [Gerrit] Implement in View a declarative event map for DOM events - change (mediawiki...Mantle)
Jhernandez has uploaded a new change for review. https://gerrit.wikimedia.org/r/181734 Change subject: Implement in View a declarative event map for DOM events .. Implement in View a declarative event map for DOM events Inspired by backbone.js Advantages: * Event handling definitions and code are defined in the same place, and handlers are defined at the root view level resulting in cleaner more comprehensible code overall * Uses event delegation, thus being more efficient that individual manual events. Previous discussion/patch: https://gerrit.wikimedia.org/r/#/c/180834/ Examples of views with this new feature: * https://gerrit.wikimedia.org/r/#/c/180835/ * https://gerrit.wikimedia.org/r/#/c/180836/ * https://gerrit.wikimedia.org/r/#/c/180837/ Change-Id: I22f2e9e12e28542a5b136bfbf478a47fc657ef3e --- M javascripts/common/View.js M tests/javascripts/common/test_View.js 2 files changed, 166 insertions(+), 3 deletions(-) git pull ssh://gerrit.wikimedia.org:29418/mediawiki/extensions/Mantle refs/changes/34/181734/1 diff --git a/javascripts/common/View.js b/javascripts/common/View.js index 1fcec8d..c7bcd01 100644 --- a/javascripts/common/View.js +++ b/javascripts/common/View.js @@ -1,6 +1,21 @@ ( function( M, $ ) { - var EventEmitter = M.require( 'eventemitter' ), View; + var EventEmitter = M.require( 'eventemitter' ), + View, + // Cached regex to split keys for `delegate`. + delegateEventSplitter = /^(\S+)\s*(.*)$/, + idCounter = 0; + + /** +* Generate a unique integer id (unique within the entire client session). +* Useful for temporary DOM ids. +* @param {String} prefix Prefix to be used when generating the id. +* @returns {String} +*/ + function uniqueId( prefix ) { + var id = ++idCounter + ''; + return prefix ? prefix + id : id; + } /** * Should be extended using extend(). @@ -28,6 +43,31 @@ * * append(), prepend(), before(), after() can be used to modify $el. on() * can be used to bind events. +* +* You can also use declarative DOM events binding by specifying an `events` +* map on the class. The keys will be 'event selector' and the value can be +* either the name of a method to call, or a function. All methods and +* functions will be executed on the context of the View. +* +* Inspired from Backbone.js +* https://github.com/jashkenas/backbone/blob/master/backbone.js#L1128 +* +* @example +* code +* var MyComponent = View.extend( { +* events: { +* 'mousedown .title': 'edit', +* 'click .button': 'save', +* 'click .open': function(e) { ... } +* }, +* edit: function ( ev ) { +* //... +* }, +* save: function ( ev ) { +* //... +* } +* } ); +* /code * * @class View * @extends EventEmitter @@ -84,6 +124,11 @@ defaults: {}, /** +* Default events map +*/ + events: null, + + /** * Run once during construction to set up the View * @method * @param {Object} options Object passed to the constructor. @@ -109,6 +154,10 @@ this.options = options; this.render( options ); + + // Assign a unique id for dom events binding/unbinding + this.cid = uniqueId( 'view' ); + this.delegateEvents(); }, /** @@ -154,9 +203,88 @@ * @param {string} query A jQuery CSS selector. * @return {jQuery.Object} jQuery object containing results of the search. */ - $: function( query ) { - return this.$el.find( query ); + $: function(query) { + return this.$el.find(query); + }, + + /** +* Set callbacks, where `this.events` is a hash of +* +* {event selector: callback} +* +* { +* 'mousedown .title': 'edit', +* 'click .button': 'save', +* 'click .open': function(e) { ... } +* } +* +* pairs. Callbacks will be bound to the view, with `this` set properly. +* Uses event delegation for efficiency. +* Omitting the selector binds the event to `this.el`. +* +