Skip to content
This repository
Browse code

Allow a one-time event listener on Ember.Evented

This commit allows you to listen for an event
once. Once the event fires, Ember immediately
unbinds it.

The API is modeled after jQuery's .one method.
  • Loading branch information...
commit 1809e65012b93c0a530bfcb95eec22d972069745 1 parent 332d214
authored June 18, 2012
19  packages/ember-runtime/lib/mixins/evented.js
@@ -16,6 +16,25 @@ Ember.Evented = Ember.Mixin.create({
16 16
     Ember.addListener(this, name, target, method, xform);
17 17
   },
18 18
 
  19
+  one: function(name, target, method) {
  20
+    if (!method) {
  21
+      method = target;
  22
+      target = null;
  23
+    }
  24
+
  25
+    var wrapped = function() {
  26
+      Ember.removeListener(this, name, target, wrapped);
  27
+
  28
+      // Internally, a `null` target means that the target is
  29
+      // the first parameter to addListener. That means that
  30
+      // the `this` passed into this function is the target
  31
+      // determined by the event system.
  32
+      method.apply(this, arguments);
  33
+    };
  34
+
  35
+    this.on(name, target, wrapped);
  36
+  },
  37
+
19 38
   trigger: function(name) {
20 39
    Ember.sendEvent.apply(null, [this, name].concat(a_slice.call(arguments, 1)));
21 40
   },
40  packages/ember-runtime/tests/system/object/events_test.js
@@ -16,6 +16,22 @@ test("a listener can be added to an object", function() {
16 16
   equal(count, 2, "the event was triggered");
17 17
 });
18 18
 
  19
+test("a listener can be added and removed automatically the first time it is triggerd", function() {
  20
+  var count = 0;
  21
+  var F = function() { count++; };
  22
+
  23
+  var obj = Ember.Object.create(Ember.Evented);
  24
+
  25
+  obj.one('event!', F);
  26
+  obj.trigger('event!');
  27
+
  28
+  equal(count, 1, "the event was triggered");
  29
+
  30
+  obj.trigger('event!');
  31
+
  32
+  equal(count, 1, "the event was not triggered again");
  33
+});
  34
+
19 35
 test("triggering an event can have arguments", function() {
20 36
   var self, args;
21 37
 
@@ -32,6 +48,30 @@ test("triggering an event can have arguments", function() {
32 48
   equal(self, obj);
33 49
 });
34 50
 
  51
+test("a listener can be added and removed automatically and have arguments", function() {
  52
+  var self, args, count = 0;
  53
+
  54
+  var obj = Ember.Object.create(Ember.Evented);
  55
+
  56
+  obj.one('event!', function() {
  57
+    args = [].slice.call(arguments);
  58
+    self = this;
  59
+    count++;
  60
+  });
  61
+
  62
+  obj.trigger('event!', "foo", "bar");
  63
+
  64
+  deepEqual(args, [ "foo", "bar" ]);
  65
+  equal(self, obj);
  66
+  equal(count, 1, "the event is triggered once");
  67
+
  68
+  obj.trigger('event!', "baz", "bat");
  69
+
  70
+  deepEqual(args, [ "foo", "bar" ]);
  71
+  equal(count, 1, "the event was not triggered again");
  72
+  equal(self, obj);
  73
+});
  74
+
35 75
 test("binding an event can specify a different target", function() {
36 76
   var self, args;
37 77
 

1 note on commit 1809e65

Josep Jaume Rey

Awesome! :D

Please sign in to comment.
Something went wrong with that request. Please try again.