dist/ember.js in ember-source-1.7.0.beta.2 vs dist/ember.js in ember-source-1.7.0.beta.3

- old
+ new

@@ -3,11 +3,11 @@ * @copyright Copyright 2011-2014 Tilde Inc. and contributors * Portions Copyright 2006-2011 Strobe Inc. * Portions Copyright 2008-2011 Apple Inc. All rights reserved. * @license Licensed under MIT license * See https://raw.github.com/emberjs/ember.js/master/LICENSE - * @version 1.7.0-beta.2 + * @version 1.7.0-beta.3 */ (function() { var define, requireModule, require, requirejs, Ember; @@ -2227,10 +2227,11 @@ @namespace Ember @extends Ember.Namespace */ var Application = Namespace.extend(DeferredMixin, { + _suppressDeferredDeprecation: true, /** The root DOM element of the Application. This can be specified as an element or a [jQuery-compatible selector string](http://api.jquery.com/category/selectors/). @@ -2806,10 +2807,21 @@ this.__container__.destroy(); }, initializer: function(options) { this.constructor.initializer(options); + }, + + /** + @method then + @private + @deprecated + */ + then: function() { + Ember.deprecate('Do not use `.then` on an instance of Ember.Application. Please use the `.ready` hook instead.'); + + this._super.apply(this, arguments); } }); Application.reopenClass({ initializers: {}, @@ -5005,10 +5017,39 @@ ```html <input type="text" value="Stanley" disabled="disabled" size="50"/> ``` + ## Actions + + The helper can send multiple actions based on user events. + + The action property defines the action which is send when + the user presses the return key. + + ```handlebars + {{input action="submit"}} + ``` + + The helper allows some user events to send actions. + + * `enter` + * `insert-newline` + * `escape-press` + * `focus-in` + * `focus-out` + * `key-press` + + For example, if you desire an action to be sent when the input is blurred, + you only need to setup the action name to the event name property. + + ```handlebars + {{input focus-in="alertMessage"}} + ``` + + See more about [Text Support Actions](api/classes/Ember.TextField.html) + ## Extension Internally, `{{input type="text"}}` creates an instance of `Ember.TextField`, passing arguments from the helper to `Ember.TextField`'s `create` method. You can extend the capabilities of text inputs in your applications by reopening this class. For example, @@ -5242,10 +5283,39 @@ <textarea id="ember2" class="ember-text-area"> Lots of text that IS bound </textarea> ``` + ## Actions + + The helper can send multiple actions based on user events. + + The action property defines the action which is send when + the user presses the return key. + + ```handlebars + {{input action="submit"}} + ``` + + The helper allows some user events to send actions. + + * `enter` + * `insert-newline` + * `escape-press` + * `focus-in` + * `focus-out` + * `key-press` + + For example, if you desire an action to be sent when the input is blurred, + you only need to setup the action name to the event name property. + + ```handlebars + {{textarea focus-in="alertMessage"}} + ``` + + See more about [Text Support Actions](api/classes/Ember.TextArea.html) + ## Extension Internally, `{{textarea}}` creates an instance of `Ember.TextArea`, passing arguments from the helper to `Ember.TextArea`'s `create` method. You can extend the capabilities of text areas in your application by reopening this @@ -6306,14 +6376,14 @@ _elementValueDidChange: function() { set(this, 'value', this.$().val()); }, /** - The action to be sent when the user inserts a new line. + Called when the user inserts a new line. Called by the `Ember.TextSupport` mixin on keyUp if keycode matches 13. - Uses sendAction to send the `enter` action to the controller. + Uses sendAction to send the `enter` action. @method insertNewline @param {Event} event */ insertNewline: function(event) { @@ -6323,11 +6393,11 @@ /** Called when the user hits escape. Called by the `Ember.TextSupport` mixin on keyUp if keycode matches 27. - Uses sendAction to send the `escape-press` action to the controller. + Uses sendAction to send the `escape-press` action. @method cancel @param {Event} event */ cancel: function(event) { @@ -6335,32 +6405,36 @@ }, /** Called when the text area is focused. + Uses sendAction to send the `focus-in` action. + @method focusIn @param {Event} event */ focusIn: function(event) { sendAction('focus-in', this, event); }, /** - Called when the text area is blurred. + Called when the text area is blurred. + Uses sendAction to send the `focus-out` action. + @method focusOut @param {Event} event */ focusOut: function(event) { sendAction('focus-out', this, event); }, /** - The action to be sent when the user presses a key. Enabled by setting + Called when the user presses a key. Enabled by setting the `onEvent` property to `keyPress`. - Uses sendAction to send the `keyPress` action to the controller. + Uses sendAction to send the `key-press` action. @method keyPress @param {Event} event */ keyPress: function(event) { @@ -9754,10 +9828,11 @@ this.path = path; this.pathRoot = pathRoot; this.isEscaped = isEscaped; this.templateData = templateData; + this._lastNormalizedValue = undefined; this.morph = Metamorph(); this.state = 'preRender'; this.updateId = null; this._parentView = null; this.buffer = null; @@ -9782,13 +9857,13 @@ propertyWillChange: K, propertyDidChange: K, normalizedValue: function() { - var path = this.path, - pathRoot = this.pathRoot, - result, templateData; + var path = this.path; + var pathRoot = this.pathRoot; + var result, templateData; // Use the pathRoot as the result if no path is provided. This // happens if the path is `this`, which gets normalized into // a `pathRoot` of the current Handlebars context and a path // of `''`. @@ -9810,16 +9885,16 @@ string += this.morph.endTag(); buffer.push(string); }, - render: function() { + render: function(value) { // If not invoked via a triple-mustache ({{{foo}}}), escape // the content of the template. var escape = this.isEscaped; - var result = this.normalizedValue(); - + var result = value || this.normalizedValue(); + this._lastNormalizedValue = result; if (result === null || result === undefined) { result = ""; } else if (!(result instanceof SafeString)) { result = String(result); } @@ -9844,11 +9919,14 @@ return this; }, update: function () { this.updateId = null; - this.morph.html(this.render()); + var value = this.normalizedValue(); + if (value !== this._lastNormalizedValue) { + this.morph.html(this.render(value)); + } }, _transitionTo: function(state) { this.state = state; } @@ -10533,23 +10611,24 @@ } __exports__["default"] = Ember; }); define("ember-metal/alias", - ["ember-metal/property_get","ember-metal/property_set","ember-metal/error","ember-metal/properties","ember-metal/platform","ember-metal/utils","ember-metal/dependent_keys","exports"], - function(__dependency1__, __dependency2__, __dependency3__, __dependency4__, __dependency5__, __dependency6__, __dependency7__, __exports__) { + ["ember-metal/property_get","ember-metal/property_set","ember-metal/error","ember-metal/properties","ember-metal/computed","ember-metal/platform","ember-metal/utils","ember-metal/dependent_keys","exports"], + function(__dependency1__, __dependency2__, __dependency3__, __dependency4__, __dependency5__, __dependency6__, __dependency7__, __dependency8__, __exports__) { "use strict"; var get = __dependency1__.get; var set = __dependency2__.set; var EmberError = __dependency3__["default"]; var Descriptor = __dependency4__.Descriptor; var defineProperty = __dependency4__.defineProperty; - var create = __dependency5__.create; - var meta = __dependency6__.meta; - var inspect = __dependency6__.inspect; - var addDependentKeys = __dependency7__.addDependentKeys; - var removeDependentKeys = __dependency7__.removeDependentKeys; + var ComputedProperty = __dependency5__.ComputedProperty; + var create = __dependency6__.create; + var meta = __dependency7__.meta; + var inspect = __dependency7__.inspect; + var addDependentKeys = __dependency8__.addDependentKeys; + var removeDependentKeys = __dependency8__.removeDependentKeys; function alias(altKey) { return new AliasedProperty(altKey); } @@ -10606,10 +10685,14 @@ function AliasedProperty_oneWaySet(obj, keyName, value) { defineProperty(obj, keyName, null); return set(obj, keyName, value); } + + // Backwards compatibility with Ember Data + AliasedProperty.prototype._meta = undefined; + AliasedProperty.prototype.meta = ComputedProperty.prototype.meta; }); define("ember-metal/array", ["exports"], function(__exports__) { "use strict"; @@ -10788,16 +10871,18 @@ // .......................................................... // BINDING // - var Binding = function(toPath, fromPath) { + function Binding(toPath, fromPath) { this._direction = 'fwd'; this._from = fromPath; this._to = toPath; this._directionMap = Map.create(); - }; + this._readyToSync = undefined; + this._oneWay = undefined; + } /** @class Binding @namespace Ember */ @@ -11057,11 +11142,10 @@ var C = this, binding = new C(null, from); return binding.oneWay(flag); } }); - /** An `Ember.Binding` connects the properties of two objects so that whenever the value of one property changes, the other property will be changed also. ## Automatic Creation of Bindings with `/^*Binding/`-named Properties @@ -11936,11 +12020,14 @@ this._suspended = obj; try { if (cacheable && cache[keyName] !== undefined) { - cachedValue = cache[keyName]; + if(cache[keyName] !== UNDEFINED) { + cachedValue = cache[keyName]; + } + hadCachedValue = true; } // Check if the CP has been wrapped. If it has, use the // length from the wrapped function. @@ -12814,11 +12901,11 @@ The core Runtime framework is based on the jQuery API with a number of performance optimizations. @class Ember @static - @version 1.7.0-beta.2 + @version 1.7.0-beta.3 */ if ('undefined' === typeof Ember) { // Create core object. Make it act like an instance of Ember.Namespace so that // objects assigned to it are given a sane string representation. @@ -12841,14 +12928,14 @@ /** @property VERSION @type String - @default '1.7.0-beta.2' + @default '1.7.0-beta.3' @static */ - Ember.VERSION = '1.7.0-beta.2'; + Ember.VERSION = '1.7.0-beta.3'; /** Standard environmental variables. You can define these in a global `EmberENV` variable before loading Ember to control various configuration settings. @@ -16889,11 +16976,11 @@ ```javascript jQuery(window).on('resize', run.bind(this, this.handleResize)); ``` @method bind - @namespace run + @namespace Ember @param {Object} [target] target of method to call @param {Function|String} method Method to invoke. May be a function or a string. If you pass a string then it will be looked up on the passed target. @param {Object} [args*] Any additional arguments you wish to pass to the method. @@ -17756,14 +17843,14 @@ @param {Function} superFunc The super function. @return {Function} wrapped function. */ function wrap(func, superFunc) { function superWrapper() { - var ret, sup = this.__nextSuper; - this.__nextSuper = superFunc; + var ret, sup = this && this.__nextSuper; + if(this) { this.__nextSuper = superFunc; } ret = apply(this, func, arguments); - this.__nextSuper = sup; + if(this) { this.__nextSuper = sup; } return ret; } superWrapper.wrappedFunction = func; superWrapper.wrappedFunction.__ember_arity__ = func.length; @@ -21864,31 +21951,33 @@ this.matches = []; } __exports__["default"] = DSL; DSL.prototype = { - resource: function(name, options, callback) { - Ember.assert("'basic' cannot be used as a resource name.", name !== 'basic'); - + route: function(name, options, callback) { if (arguments.length === 2 && typeof options === 'function') { callback = options; options = {}; } if (arguments.length === 1) { options = {}; } + var type = options.resetNamespace === true ? 'resource' : 'route'; + Ember.assert("'basic' cannot be used as a " + type + " name.", name !== 'basic'); + + if (typeof options.path !== 'string') { options.path = "/" + name; } - var createSubRoutes = false; - - createSubRoutes = true; - - if (createSubRoutes) { + if (canNest(this) && options.resetNamespace !== true) { + name = this.parent + "." + name; + } + + if (callback) { var dsl = new DSL(name); route(dsl, 'loading'); route(dsl, 'error', { path: "/_unused_dummy_error_path_route_" + name + "/:error" }); if (callback) { callback.call(dsl); } @@ -21896,31 +21985,38 @@ this.push(options.path, name, dsl.generate()); } else { this.push(options.path, name, null); } - }, push: function(url, name, callback) { var parts = name.split('.'); if (url === "" || url === "/" || parts[parts.length-1] === "index") { this.explicitIndex = true; } this.matches.push([url, name, callback]); }, - route: function(name, options) { - Ember.assert("'basic' cannot be used as a route name.", name !== 'basic'); + resource: function(name, options, callback) { + if (arguments.length === 2 && typeof options === 'function') { + callback = options; + options = {}; + } - route(this, name, options); - }, + if (arguments.length === 1) { + options = {}; + } + options.resetNamespace = true; + this.route(name, options, callback); + }, + generate: function() { var dslMatches = this.matches; if (!this.explicitIndex) { - this.route("index", { path: "/" }); + route(this, "index", { path: "/" }); } return function(match) { for (var i=0, l=dslMatches.length; i<l; i++) { var dslMatch = dslMatches[i]; @@ -21928,20 +22024,24 @@ } }; } }; + function canNest(dsl) { + return dsl.parent && dsl.parent !== 'application'; + } + function route(dsl, name, options) { Ember.assert("You must use `this.resource` to nest", typeof options !== 'function'); options = options || {}; if (typeof options.path !== 'string') { options.path = "/" + name; } - if (dsl.parent && dsl.parent !== 'application') { + if (canNest(dsl) && options.resetNamespace !== true) { name = dsl.parent + "." + name; } dsl.push(options.path, name, null); } @@ -23834,11 +23934,10 @@ }); ``` @method resetController @param {Controller} controller instance - @param {Object} model @param {Boolean} isExiting @param {Object} transition */ resetController: Ember.K }); @@ -28196,11 +28295,11 @@ return this.objectAt(idx); }, /** This is the handler for the special array content property. If you get - this property, it will return this. If you set this property it a new + this property, it will return this. If you set this property to a new array, it will replace the current content. This property overrides the default property defined in `Ember.Enumerable`. @property [] @@ -28856,10 +28955,12 @@ reject: function(value) { get(this, '_deferred').reject(value); }, _deferred: computed(function() { + Ember.deprecate('Usage of Ember.DeferredMixin or Ember.Deferred is deprecated.', this._suppressDeferredDeprecation); + return RSVP.defer('Ember: DeferredMixin - ' + this); }) }); }); define("ember-runtime/mixins/enumerable", @@ -29838,11 +29939,11 @@ return this; }, /** Invoke this method when the contents of your enumerable has changed. - This will notify any observers watching for content changes. If your are + This will notify any observers watching for content changes. If you are implementing an ordered enumerable (such as an array), also pass the start and end values where the content changed so that it can be used to notify range observers. @method enumerableContentDidChange @@ -30776,17 +30877,19 @@ /** To get multiple properties at once, call `getProperties` with a list of strings or an array: ```javascript - record.getProperties('firstName', 'lastName', 'zipCode'); // { firstName: 'John', lastName: 'Doe', zipCode: '10011' } + record.getProperties('firstName', 'lastName', 'zipCode'); + // { firstName: 'John', lastName: 'Doe', zipCode: '10011' } ``` is equivalent to: ```javascript - record.getProperties(['firstName', 'lastName', 'zipCode']); // { firstName: 'John', lastName: 'Doe', zipCode: '10011' } + record.getProperties(['firstName', 'lastName', 'zipCode']); + // { firstName: 'John', lastName: 'Doe', zipCode: '10011' } ``` @method getProperties @param {String...|Array} list of keys to get @return {Hash} @@ -32225,10 +32328,11 @@ var schedule = run.schedule; var applyMixin = Mixin._apply; var finishPartial = Mixin.finishPartial; var reopen = Mixin.prototype.reopen; var MANDATORY_SETTER = Ember.ENV.MANDATORY_SETTER; + var hasCachedComputedProperties = false; var undefinedDescriptor = { configurable: true, writable: true, enumerable: false, @@ -32920,30 +33024,48 @@ Ember.assert("metaForProperty() could not find a computed property with key '"+key+"'.", !!desc && desc instanceof ComputedProperty); return desc._meta || {}; }, + _computedProperties: Ember.computed(function() { + hasCachedComputedProperties = true; + var proto = this.proto(); + var descs = meta(proto).descs; + var property; + var properties = []; + + for (var name in descs) { + property = descs[name]; + + if (property instanceof ComputedProperty) { + properties.push({ + name: name, + meta: property._meta + }); + } + } + return properties; + }).readOnly(), + /** Iterate over each computed property for the class, passing its name and any associated metadata (see `metaForProperty`) to the callback. @method eachComputedProperty @param {Function} callback @param {Object} binding */ eachComputedProperty: function(callback, binding) { - var proto = this.proto(), - descs = meta(proto).descs, - empty = {}, - property; + var property, name; + var empty = {}; - for (var name in descs) { - property = descs[name]; + var properties = get(this, '_computedProperties'); - if (property instanceof ComputedProperty) { - callback.call(binding || this, name, property._meta || empty); - } + for (var i = 0, length = properties.length; i < length; i++) { + property = properties[i]; + name = property.name; + callback.call(binding || this, property.name, property.meta || empty); } } }); ClassMixin.ownerConstructor = CoreObject; @@ -32951,23 +33073,46 @@ if (Ember.config.overrideClassMixin) { Ember.config.overrideClassMixin(ClassMixin); } CoreObject.ClassMixin = ClassMixin; + ClassMixin.apply(CoreObject); + CoreObject.reopen({ + didDefineProperty: function(proto, key, value) { + if (hasCachedComputedProperties === false) { return; } + if (value instanceof Ember.ComputedProperty) { + var cache = Ember.meta(this.constructor).cache; + + if (cache._computedProperties !== undefined) { + cache._computedProperties = undefined; + } + } + + this._super(); + } + }); + + __exports__["default"] = CoreObject; }); define("ember-runtime/system/deferred", - ["ember-runtime/mixins/deferred","ember-metal/property_get","ember-runtime/system/object","exports"], - function(__dependency1__, __dependency2__, __dependency3__, __exports__) { + ["ember-metal/core","ember-runtime/mixins/deferred","ember-metal/property_get","ember-runtime/system/object","exports"], + function(__dependency1__, __dependency2__, __dependency3__, __dependency4__, __exports__) { "use strict"; - var DeferredMixin = __dependency1__["default"]; - var get = __dependency2__.get; - var EmberObject = __dependency3__["default"]; + var Ember = __dependency1__["default"]; + var DeferredMixin = __dependency2__["default"]; + var get = __dependency3__.get; + var EmberObject = __dependency4__["default"]; - var Deferred = EmberObject.extend(DeferredMixin); + var Deferred = EmberObject.extend(DeferredMixin, { + init: function() { + Ember.deprecate('Usage of Ember.Deferred is deprecated.'); + this._super(); + } + }); Deferred.reopenClass({ promise: function(callback, binding) { var deferred = Deferred.create(); callback.call(binding, deferred); @@ -33404,10 +33549,19 @@ paths.length = idx; // cut out last item } var STARTS_WITH_UPPERCASE = /^[A-Z]/; + function tryIsNamespace(lookup, prop) { + try { + var obj = lookup[prop]; + return obj && obj.isNamespace && obj; + } catch (e) { + // continue + } + } + function findNamespaces() { var lookup = Ember.lookup, obj, isNamespace; if (Namespace.PROCESSED) { return; } @@ -33418,18 +33572,12 @@ // Unfortunately, some versions of IE don't support window.hasOwnProperty if (lookup.hasOwnProperty && !lookup.hasOwnProperty(prop)) { continue; } // At times we are not allowed to access certain properties for security reasons. // There are also times where even if we can access them, we are not allowed to access their properties. - try { - obj = lookup[prop]; - isNamespace = obj && obj.isNamespace; - } catch (e) { - continue; - } - - if (isNamespace) { + obj = tryIsNamespace(lookup, prop); + if (obj) { obj[NAME_KEY] = prop; } } } @@ -36037,11 +36185,11 @@ adapter: null, /** Replacement for `Ember.RSVP.resolve` The only difference is this uses - and instance of `Ember.Test.Promise` + an instance of `Ember.Test.Promise` @public @method resolve @param {Mixed} The value to resolve @since 1.2.0 @@ -36644,27 +36792,27 @@ @default 'body' */ rootElement: 'body', /** - It enables events to be dispatched to the view `eventManager` which object - when present takes precedence over events of the same name handled through methods - on the view. + It enables events to be dispatched to the view's `eventManager.` When present, + this object takes precedence over handling of events on the view itself. - Most of the ember applications does not implement view `eventManagers`, - then disabling this property will provide some performance benefit - because it skips the search for the `eventManager` on the view tree. + Note that most Ember applications do not use this feature. If your app also + does not use it, consider setting this property to false to gain some performance + improvement by allowing the EventDispatcher to skip the search for the + `eventManager` on the view tree. ```javascript var EventDispatcher = Em.EventDispatcher.extend({ events: { click : 'click', focusin : 'focusIn', focusout : 'focusOut', change : 'change' }, - canDispatchToEventManager: false + canDispatchToEventManager: false }); container.register('event_dispatcher:main', EventDispatcher); ``` @property canDispatchToEventManager @@ -36688,11 +36836,10 @@ setup: function(addedEvents, rootElement) { var event, events = get(this, 'events'); jQuery.extend(events, addedEvents || {}); - if (!isNone(rootElement)) { set(this, 'rootElement', rootElement); } rootElement = jQuery(get(this, 'rootElement')); @@ -36711,24 +36858,17 @@ } } }, /** - Registers an event listener on the document. If the given event is + Registers an event listener on the rootElement. If the given event is triggered, the provided event handler will be triggered on the target view. If the target view does not implement the event handler, or if the handler returns `false`, the parent view will be called. The event will continue to bubble to each successive parent view until it reaches the top. - For example, to have the `mouseDown` method called on the target view when - a `mousedown` event is received from the browser, do the following: - - ```javascript - setupHandler('mousedown', 'mouseDown'); - ``` - @private @method setupHandler @param {Element} rootElement @param {String} event the browser-originated event to listen to @param {String} eventName the name of the method to call on the view @@ -36737,19 +36877,17 @@ var self = this; rootElement.on(event + '.ember', '.ember-view', function(evt, triggeringManager) { var view = View.views[this.id], result = true; - + var manager = self.canDispatchToEventManager ? self._findNearestEventManager(view, eventName) : null; if (manager && manager !== triggeringManager) { result = self._dispatchEvent(manager, evt, eventName, view); } else if (view) { result = self._bubbleEvent(view, evt, eventName); - } else { - evt.stopPropagation(); } return result; }); @@ -36805,9 +36943,10 @@ destroy: function() { var rootElement = get(this, 'rootElement'); jQuery(rootElement).off('.ember', '**').removeClass('ember-application'); return this._super(); }, + toString: function() { return '(EventDisptacher)'; } }); }); \ No newline at end of file