8
0
Просмотр исходного кода

Merge pull request #84 from ckeditor/t/83

Fixed stopListening method of DOMEmitterMixin.
Piotrek Koszuliński 9 лет назад
Родитель
Сommit
3fb41994a2

+ 7 - 9
packages/ckeditor5-ui/src/domemittermixin.js

@@ -6,7 +6,6 @@
 import EmitterMixin from '../utils/emittermixin.js';
 import uid from '../utils/uid.js';
 import extend from '../utils/lib/lodash/extend.js';
-import log from '../utils/log.js';
 import isNative from '../utils/lib/lodash/isNative.js';
 
 /**
@@ -88,14 +87,12 @@ const DOMEmitterMixin = extend( {}, EmitterMixin, {
 		if ( isDomNode( emitter ) ) {
 			let proxy = this._getProxyEmitter( emitter );
 
-			if ( proxy ) {
-				args[ 0 ] = proxy;
-			} else {
-				log.error(
-					'domemittermixin-stoplistening: Stopped listening on a DOM Node that has no emitter or emitter is gone.',
-					emitter
-				);
+			// Element has no listeners.
+			if ( !proxy ) {
+				return;
 			}
+
+			args[ 0 ] = proxy;
 		}
 
 		// Execute parent class method with Emitter (or ProxyEmitter) instance.
@@ -241,7 +238,8 @@ extend( ProxyEmitter.prototype, EmitterMixin, {
 		// Remove native DOM listeners which are orphans. If no callbacks
 		// are awaiting given event, detach native DOM listener from DOM Node.
 		// See: {@link on}.
-		if ( !( events = this._events[ event ] ) || !events.callbacks.length ) {
+
+		if ( this._domListeners[ event ] && ( !( events = this._events[ event ] ) || !events.callbacks.length ) ) {
 			this._domListeners[ event ].removeListener();
 		}
 	},

+ 44 - 0
packages/ckeditor5-ui/tests/domemittermixin.js

@@ -197,6 +197,50 @@ describe( 'DOMEmitterMixin', () => {
 			expect( domEmitter ).to.not.have.property( '_listeningTo' );
 		} );
 
+		it( 'should stop listening to everything what left', () => {
+			const spy1 = testUtils.sinon.spy();
+			const spy2 = testUtils.sinon.spy();
+			const spy3 = testUtils.sinon.spy();
+			const spy4 = testUtils.sinon.spy();
+
+			const node1 = document.createElement( 'div' );
+			const node2 = document.createElement( 'div' );
+
+			domEmitter.listenTo( node1, 'event1', spy1 );
+			domEmitter.listenTo( node1, 'event2', spy2 );
+			domEmitter.listenTo( node2, 'event1', spy3 );
+			domEmitter.listenTo( node2, 'event2', spy4 );
+
+			expect( domEmitter ).to.have.property( '_listeningTo' );
+
+			domEmitter.stopListening( node1, 'event1', spy1 );
+			domEmitter.stopListening( node2, 'event1' );
+
+			node1.dispatchEvent( new Event( 'event1' ) );
+			node1.dispatchEvent( new Event( 'event2' ) );
+			node2.dispatchEvent( new Event( 'event1' ) );
+			node2.dispatchEvent( new Event( 'event2' ) );
+
+			sinon.assert.notCalled( spy1 );
+			sinon.assert.calledOnce( spy2 );
+			sinon.assert.notCalled( spy3 );
+			sinon.assert.calledOnce( spy4 );
+
+			domEmitter.stopListening();
+
+			node1.dispatchEvent( new Event( 'event1' ) );
+			node1.dispatchEvent( new Event( 'event2' ) );
+			node2.dispatchEvent( new Event( 'event1' ) );
+			node2.dispatchEvent( new Event( 'event2' ) );
+
+			sinon.assert.notCalled( spy1 );
+			sinon.assert.calledOnce( spy2 );
+			sinon.assert.notCalled( spy3 );
+			sinon.assert.calledOnce( spy4 );
+
+			expect( domEmitter ).to.not.have.property( '_listeningTo' );
+		} );
+
 		it( 'should not stop other nodes when a non-listened node is provided', () => {
 			const spy = testUtils.sinon.spy();