Compare commits
3 Commits
f0edd3b63e
...
7805c2fe06
Author | SHA1 | Date |
---|---|---|
|
7805c2fe06 | 7 years ago |
|
34842e4803 | 7 years ago |
|
e5e352247b | 7 years ago |
@ -0,0 +1,53 @@
|
||||
'use strict';
|
||||
|
||||
const defaultValue = require("default-value");
|
||||
|
||||
const validateSync = require("./validate-sync");
|
||||
|
||||
let originAliases = {
|
||||
top: 0,
|
||||
left: 0,
|
||||
center: "50%",
|
||||
bottom: "100%",
|
||||
right: "100%"
|
||||
}
|
||||
|
||||
function tryAlias(value) {
|
||||
if (originAliases[value] != null) {
|
||||
return originAliases[value];
|
||||
} else {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
||||
function calculateOffset(value, origin) {
|
||||
if (typeof origin === "number") {
|
||||
return -origin;
|
||||
} else {
|
||||
let match = /^(-?[0-9]+(?:\.[0-9]+)?)%$/.exec(origin);
|
||||
|
||||
if (match == null) {
|
||||
throw new Error(`Encountered invalid origin value: ${origin}`);
|
||||
} else {
|
||||
let percentage = match[1];
|
||||
return -(value * (parseFloat(percentage) / 100));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = function calculateOriginOffsets(options) {
|
||||
validateSync(options, {
|
||||
width: "required",
|
||||
height: "required",
|
||||
originX: "required",
|
||||
originY: "required"
|
||||
});
|
||||
|
||||
let originX = tryAlias(options.originX);
|
||||
let originY = tryAlias(options.originY);
|
||||
|
||||
return {
|
||||
x: calculateOffset(options.width, originX),
|
||||
y: calculateOffset(options.height, originY)
|
||||
}
|
||||
}
|
@ -0,0 +1,93 @@
|
||||
'use strict';
|
||||
|
||||
const dotty = require("dotty");
|
||||
const defaultValue = require("default-value");
|
||||
|
||||
const createObject = require("./create-object");
|
||||
const createPropertyMapper = require("./property-mapper");
|
||||
const max = require("./util/max");
|
||||
const min = require("./util/min");
|
||||
|
||||
function getPosition(object) {
|
||||
return {
|
||||
x: defaultValue(object.x, 0),
|
||||
y: defaultValue(object.y, 0)
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = function createCompositeObject(options) {
|
||||
let mapProperties = createPropertyMapper(options.propertyMap);
|
||||
|
||||
let compositeObject = createObject(Object.assign({
|
||||
onSet: function setCompositeProperties(properties) {
|
||||
let mappedProperties = mapProperties(properties);
|
||||
|
||||
Object.keys(mappedProperties).forEach((objectName) => {
|
||||
if (objectName !== "_") {
|
||||
if (this.objects[objectName] != null) {
|
||||
this.objects[objectName].set(mappedProperties[objectName]);
|
||||
} else {
|
||||
throw new Error(`The object specified in the property map as '${objectName}' does not exist`);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
/* We return the `_` object here, which contains all the unmapped
|
||||
* properties - we assume that all unmapped properties are meant to
|
||||
* apply to the composite object rather than its child objects. The
|
||||
* original `.set` method (as defined in createObject) will then use
|
||||
* this result. */
|
||||
return defaultValue(mappedProperties._, {});
|
||||
},
|
||||
onRender: function onRender(context) {
|
||||
Object.keys(this.objects).forEach((objectName) => {
|
||||
let object = this.objects[objectName];
|
||||
let position = getPosition(object);
|
||||
|
||||
object.render(context, {
|
||||
x: object.x - this.renderOffsetX,
|
||||
y: object.y - this.renderOffsetY
|
||||
});
|
||||
});
|
||||
},
|
||||
onRecalculateSize: function onRecalculateSize() {
|
||||
let objectMetrics = Object.keys(this.objects).map((objectName) => {
|
||||
let object = this.objects[objectName];
|
||||
let position = getPosition(object);
|
||||
|
||||
console.log(object.type, [object.x, object.y], [position.x, position.y], object.renderWidth, object.renderHeight);
|
||||
|
||||
return {
|
||||
x1: position.x,
|
||||
y1: position.y,
|
||||
x2: position.x + object.renderWidth,
|
||||
y2: position.y + object.renderHeight
|
||||
}
|
||||
});
|
||||
|
||||
let x1 = min(objectMetrics.map(object => object.x1));
|
||||
let y1 = min(objectMetrics.map(object => object.y1));
|
||||
let x2 = max(objectMetrics.map(object => object.x2));
|
||||
let y2 = max(objectMetrics.map(object => object.y2));
|
||||
|
||||
return {
|
||||
width: x2 - x1,
|
||||
height: y2 - y1,
|
||||
offsetX: x1,
|
||||
offsetY: y1
|
||||
}
|
||||
}
|
||||
}, options));
|
||||
|
||||
Object.keys(compositeObject.objects).forEach((objectName) => {
|
||||
compositeObject.objects[objectName].on("recalculatedSize", () => {
|
||||
compositeObject.recalculateSize();
|
||||
});
|
||||
|
||||
compositeObject.objects[objectName].on("renderedToCache", () => {
|
||||
compositeObject.bustCache();
|
||||
});
|
||||
});
|
||||
|
||||
return compositeObject;
|
||||
};
|
@ -0,0 +1,5 @@
|
||||
'use strict';
|
||||
|
||||
module.exports = function max(values) {
|
||||
return Math.max(...values);
|
||||
}
|
@ -0,0 +1,5 @@
|
||||
'use strict';
|
||||
|
||||
module.exports = function min(values) {
|
||||
return Math.min(...values);
|
||||
}
|
Loading…
Reference in New Issue