ceri-side-nav
Version:
a touch enabled, responsive side-nav
294 lines (290 loc) • 7.7 kB
JavaScript
// Generated by CoffeeScript 1.12.7
(function() {
var ceri;
ceri = require("ceri/lib/wrapper");
module.exports = ceri({
mixins: [require("ceri/lib/props"), require("ceri/lib/style"), require("ceri/lib/animate"), require("ceri/lib/directives"), require("ceri/lib/open"), require("ceri/lib/overlay"), require("ceri/lib/#if"), require("ceri/lib/draghandle")],
props: {
opacity: {
type: Number,
"default": 0.5
},
right: {
type: Boolean,
cbs: [
"setParentMargin", (function(val) {
if (val) {
this.style.right = 0;
return this.style.left = null;
} else {
this.style.right = null;
return this.style.left = null;
}
})
]
},
target: {
type: String
},
fixed: {
type: Boolean,
cbs: "processFixed",
delay: true
},
fixedScreenSize: {
type: Number,
"default": 992,
cbs: "processFixed"
},
zIndex: {
type: Number,
"default": 1000,
cbs: function(val, old) {
var s;
s = this.style;
if (s.zIndex && s.zIndex !== old) {
return;
}
return s.zIndex = val;
}
}
},
data: function() {
return {
isFixed: null,
keepOpen: true,
dhZIndex: null
};
},
overlay: {
zIndex: "zIndex",
active: "dismissable",
animate: "toggleAnimate",
delay: true,
onClose: function() {
this.style.zIndex = this.zIndex;
this.dhZIndex = this.zIndex - 1;
return this.hide.call(this);
},
onOpen: function(zIndex) {
this.style.zIndex = zIndex + 2;
return this.dhZIndex = zIndex + 1;
}
},
draghandle: {
__parentElement: {
active: function() {
return !this.isFixed;
},
initStyle: {
position: "absolute",
top: 0,
bottom: 0
},
style: function() {
return {
zIndex: this.dhZIndex,
width: this.open ? null : "20px",
left: !this.right || this.open ? 0 : null,
right: this.right || this.open ? 0 : null
};
},
onClick: function() {
if (this.open) {
return this.hide();
}
},
onFirstMove: function(o) {
var w;
if (!this.open) {
this.style.transform = "translateX(" + (this.fac * 100) + "%)";
this._attach();
}
o.wasOpened = this.open;
w = this.offsetWidth * this.fac;
if (this.right) {
o.shouldShow = function(move) {
return move < 0;
};
return o.shouldHide = function(move) {
return move > w;
};
} else {
o.shouldShow = function(move) {
return move > 0;
};
return o.shouldHide = function(move) {
return move < w;
};
}
},
onMove: function(delta, o) {
var move;
move = 2 * delta.x + this.offsetWidth * this.fac * !o.wasOpened;
if (o.shouldShow(move)) {
this._setOpen();
this.style.transform = null;
return o.move = 0;
} else if (o.shouldHide(move)) {
this._setClose();
this.style.transform = "translateX(" + (this.fac * 100) + "%)";
return o.move = -this.offsetWidth;
} else {
this.style.transform = "translateX(" + move + "px)";
return o.move = move;
}
},
onEnd: function(delta, o) {
if (this.open && o.move < 0) {
return this.animation = this.enter({
_percent: 1 - o.move / this.offsetWidth * this.fac
});
} else if (!this.open && o.move > -this.offsetWidth) {
return this.animation = this.leave({
_percent: o.move / this.offsetWidth * this.fac,
done: this._detach
});
}
}
}
},
events: {
click: {
"this": {
active: "dismissable",
notPrevented: true,
prevent: true,
cbs: ["toggle"]
},
_target: {
active: function() {
return (this._target != null) && !this.isFixed;
},
notPrevented: true,
prevent: true,
cbs: ["toggle"],
destroy: true
}
},
resize: {
window: {
el: window,
active: "fixed",
throttled: true,
destroy: true,
cbs: "processFixed"
}
}
},
directives: {
_target: {
type: "#",
name: "if",
activate: "_target",
value: "isFixed",
not: true
}
},
initStyle: {
position: "fixed",
height: "100%"
},
computedStyle: {
"this": function() {
return {
willChange: this.isFixed ? null : "transform"
};
}
},
computed: {
_target: function() {
if (!this.target) {
return null;
}
return document.querySelector(this.target);
},
fac: function() {
return this.right * 2 - 1;
},
dismissable: function() {
return this.openingOrOpen && !this.isFixed;
}
},
methods: {
makeFixed: function(fixed) {
if (fixed !== this.isFixed) {
this.isFixed = fixed;
return this.$emit({
name: "fixed",
detail: fixed
});
}
},
setParentMargin: function() {
var el, i, len, ref, results, width;
if (this.parentElement) {
if (this.isFixed) {
width = this.offsetWidth + "px";
} else {
width = null;
}
ref = this.parentElement.children;
results = [];
for (i = 0, len = ref.length; i < len; i++) {
el = ref[i];
if (el !== this) {
results.push(this.$style.set(el, {
marginLeft: this.right ? null : width,
marginRight: this.right ? width : null
}));
} else {
results.push(void 0);
}
}
return results;
}
},
processFixed: function() {
var old;
if (this.fixed) {
old = this.isFixed;
this.makeFixed(window.innerWidth > this.fixedScreenSize);
if (old !== this.isFixed) {
this.wasOpened = this.open;
if (this.isFixed) {
this.show(false);
return this.setParentMargin();
} else {
this.setParentMargin();
return this.hide(false);
}
}
} else {
this.makeFixed(false);
this.setParentMargin();
if (!this.openingOrOpen || !this.wasOpened) {
return this.hide(false);
}
}
},
enter: function(o) {
o.style = {
translateX: [this.fac * 100, 0, "%"]
};
return this.$animate(o);
},
leave: function(o) {
o.style = {
translateX: [0, this.fac * 100, "%"]
};
return this.$animate(o);
},
beforeToggle: function() {
return !this.isFixed;
},
onHide: function() {
return this.wasOpened = false;
}
}
});
}).call(this);