ui: Adds `document` and `viewport` methods to the dom service (#5052)
`window` and `document` are easily injected anyhow, but this primarily this keeps everything dom related in the same place. Included here are changes to make all ember related objects use the dom service `document` and `viewport` instead of just `document` and `window`. Quote from a previous PR (#4924) which explains the thinking around this: > Now I have all these things in the dom service, it would make sense to get window from there also. I was thinking of making a viewport method, which would be a nice word whether window was a browser window, an iframe (not really a window) like when ember testing, or anything else. To me the viewport is what we are actually talking about here.
This commit is contained in:
parent
9a27b2c74d
commit
c4effc9734
|
@ -3,8 +3,6 @@ import { get, set } from '@ember/object';
|
||||||
import { inject as service } from '@ember/service';
|
import { inject as service } from '@ember/service';
|
||||||
export default Component.extend({
|
export default Component.extend({
|
||||||
dom: service('dom'),
|
dom: service('dom'),
|
||||||
// TODO: could this be dom.viewport() ?
|
|
||||||
win: window,
|
|
||||||
isDropdownVisible: false,
|
isDropdownVisible: false,
|
||||||
didInsertElement: function() {
|
didInsertElement: function() {
|
||||||
get(this, 'dom')
|
get(this, 'dom')
|
||||||
|
@ -19,11 +17,12 @@ export default Component.extend({
|
||||||
},
|
},
|
||||||
change: function(e) {
|
change: function(e) {
|
||||||
const dom = get(this, 'dom');
|
const dom = get(this, 'dom');
|
||||||
|
const win = dom.viewport();
|
||||||
const $root = dom.root();
|
const $root = dom.root();
|
||||||
const $body = dom.element('body');
|
const $body = dom.element('body');
|
||||||
if (e.target.checked) {
|
if (e.target.checked) {
|
||||||
$root.classList.add('template-with-vertical-menu');
|
$root.classList.add('template-with-vertical-menu');
|
||||||
$body.style.height = $root.style.height = get(this, 'win').innerHeight + 'px';
|
$body.style.height = $root.style.height = win.innerHeight + 'px';
|
||||||
} else {
|
} else {
|
||||||
$root.classList.remove('template-with-vertical-menu');
|
$root.classList.remove('template-with-vertical-menu');
|
||||||
$body.style.height = $root.style.height = null;
|
$body.style.height = $root.style.height = null;
|
||||||
|
|
|
@ -1,16 +1,19 @@
|
||||||
import Mixin from '@ember/object/mixin';
|
import Mixin from '@ember/object/mixin';
|
||||||
|
import { inject as service } from '@ember/service';
|
||||||
import { next } from '@ember/runloop';
|
import { next } from '@ember/runloop';
|
||||||
import { get } from '@ember/object';
|
import { get } from '@ember/object';
|
||||||
const isOutside = function(element, e) {
|
|
||||||
|
// TODO: Potentially move this to dom service
|
||||||
|
const isOutside = function(element, e, doc = document) {
|
||||||
if (element) {
|
if (element) {
|
||||||
const isRemoved = !e.target || !document.contains(e.target);
|
const isRemoved = !e.target || !doc.contains(e.target);
|
||||||
const isInside = element === e.target || element.contains(e.target);
|
const isInside = element === e.target || element.contains(e.target);
|
||||||
return !isRemoved && !isInside;
|
return !isRemoved && !isInside;
|
||||||
} else {
|
} else {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const handler = function(e) {
|
const handler = function(e) {
|
||||||
const el = get(this, 'element');
|
const el = get(this, 'element');
|
||||||
if (isOutside(el, e)) {
|
if (isOutside(el, e)) {
|
||||||
|
@ -18,6 +21,7 @@ const handler = function(e) {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
export default Mixin.create({
|
export default Mixin.create({
|
||||||
|
dom: service('dom'),
|
||||||
init: function() {
|
init: function() {
|
||||||
this._super(...arguments);
|
this._super(...arguments);
|
||||||
this.handler = handler.bind(this);
|
this.handler = handler.bind(this);
|
||||||
|
@ -26,12 +30,14 @@ export default Mixin.create({
|
||||||
onblur: function() {},
|
onblur: function() {},
|
||||||
didInsertElement: function() {
|
didInsertElement: function() {
|
||||||
this._super(...arguments);
|
this._super(...arguments);
|
||||||
|
const doc = get(this, 'dom').document();
|
||||||
next(this, () => {
|
next(this, () => {
|
||||||
document.addEventListener('click', this.handler);
|
doc.addEventListener('click', this.handler);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
willDestroyElement: function() {
|
willDestroyElement: function() {
|
||||||
this._super(...arguments);
|
this._super(...arguments);
|
||||||
document.removeEventListener('click', this.handler);
|
const doc = get(this, 'dom').document();
|
||||||
|
doc.removeEventListener('click', this.handler);
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,11 +1,12 @@
|
||||||
import Mixin from '@ember/object/mixin';
|
import Mixin from '@ember/object/mixin';
|
||||||
|
import { inject as service } from '@ember/service';
|
||||||
import { get } from '@ember/object';
|
import { get } from '@ember/object';
|
||||||
import { assert } from '@ember/debug';
|
import { assert } from '@ember/debug';
|
||||||
export default Mixin.create({
|
export default Mixin.create({
|
||||||
|
dom: service('dom'),
|
||||||
resize: function(e) {
|
resize: function(e) {
|
||||||
assert('with-resizing.resize needs to be overridden', false);
|
assert('with-resizing.resize needs to be overridden', false);
|
||||||
},
|
},
|
||||||
win: window,
|
|
||||||
init: function() {
|
init: function() {
|
||||||
this._super(...arguments);
|
this._super(...arguments);
|
||||||
this.handler = e => {
|
this.handler = e => {
|
||||||
|
@ -17,14 +18,18 @@ export default Mixin.create({
|
||||||
},
|
},
|
||||||
didInsertElement: function() {
|
didInsertElement: function() {
|
||||||
this._super(...arguments);
|
this._super(...arguments);
|
||||||
get(this, 'win').addEventListener('resize', this.handler, false);
|
get(this, 'dom')
|
||||||
|
.viewport()
|
||||||
|
.addEventListener('resize', this.handler, false);
|
||||||
this.didAppear();
|
this.didAppear();
|
||||||
},
|
},
|
||||||
didAppear: function() {
|
didAppear: function() {
|
||||||
this.handler({ target: get(this, 'win') });
|
this.handler({ target: get(this, 'dom').viewport() });
|
||||||
},
|
},
|
||||||
willDestroyElement: function() {
|
willDestroyElement: function() {
|
||||||
get(this, 'win').removeEventListener('resize', this.handler, false);
|
get(this, 'dom')
|
||||||
|
.viewport()
|
||||||
|
.removeEventListener('resize', this.handler, false);
|
||||||
this._super(...arguments);
|
this._super(...arguments);
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
|
@ -23,10 +23,17 @@ let $_;
|
||||||
const clickFirstAnchor = clickFirstAnchorFactory(closest);
|
const clickFirstAnchor = clickFirstAnchorFactory(closest);
|
||||||
export default Service.extend({
|
export default Service.extend({
|
||||||
doc: document,
|
doc: document,
|
||||||
|
win: window,
|
||||||
init: function() {
|
init: function() {
|
||||||
this._super(...arguments);
|
this._super(...arguments);
|
||||||
$_ = getComponentFactory(getOwner(this));
|
$_ = getComponentFactory(getOwner(this));
|
||||||
},
|
},
|
||||||
|
document: function() {
|
||||||
|
return get(this, 'doc');
|
||||||
|
},
|
||||||
|
viewport: function() {
|
||||||
|
return get(this, 'win');
|
||||||
|
},
|
||||||
// TODO: should this be here? Needs a better name at least
|
// TODO: should this be here? Needs a better name at least
|
||||||
clickFirstAnchor: clickFirstAnchor,
|
clickFirstAnchor: clickFirstAnchor,
|
||||||
closest: closest,
|
closest: closest,
|
||||||
|
|
|
@ -12,8 +12,13 @@ module('Integration | Mixin | with-resizing', function(hooks) {
|
||||||
addEventListener: this.stub(),
|
addEventListener: this.stub(),
|
||||||
removeEventListener: this.stub(),
|
removeEventListener: this.stub(),
|
||||||
};
|
};
|
||||||
|
const dom = {
|
||||||
|
viewport: function() {
|
||||||
|
return win;
|
||||||
|
},
|
||||||
|
};
|
||||||
const subject = EmberObject.extend(Mixin, {
|
const subject = EmberObject.extend(Mixin, {
|
||||||
win: win,
|
dom: dom,
|
||||||
}).create();
|
}).create();
|
||||||
const resize = this.stub(subject, 'resize');
|
const resize = this.stub(subject, 'resize');
|
||||||
subject.didInsertElement();
|
subject.didInsertElement();
|
||||||
|
|
Loading…
Reference in New Issue