1361 lines
52 KiB
JavaScript
1361 lines
52 KiB
JavaScript
(function(f){if(typeof exports==="object"&&typeof module!=="undefined"){module.exports=f()}else if(typeof define==="function"&&define.amd){define([],f)}else{var g;if(typeof window!=="undefined"){g=window}else if(typeof global!=="undefined"){g=global}else if(typeof self!=="undefined"){g=self}else{g=this}g.jiboAnimDb = f()}})(function(){var define,module,exports;return (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s})({1:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const Utils_1 = require("./Utils");
|
|
const Classes_1 = require("./Classes");
|
|
const AnimUtils_1 = require("./AnimUtils");
|
|
class AnimCollection {
|
|
constructor(parent) {
|
|
this.parent = parent;
|
|
this.animations = [];
|
|
this.categories = [];
|
|
this._animationsByName = new Map();
|
|
this._categoriesByName = new Map();
|
|
}
|
|
addAnimation(animation) {
|
|
const nameLower = animation.name.toLowerCase();
|
|
if (!this._animationsByName.has(nameLower)) {
|
|
this._animationsByName.set(nameLower, animation);
|
|
this.animations.push(animation);
|
|
}
|
|
}
|
|
addCategory(category) {
|
|
const nameLower = category.name.toLowerCase();
|
|
if (!this._categoriesByName.has(nameLower)) {
|
|
this._categoriesByName.set(nameLower, category);
|
|
this.categories.push(category);
|
|
}
|
|
}
|
|
getCategoryByName(name) {
|
|
return this._categoriesByName.get(name.toLowerCase());
|
|
}
|
|
getAnimByName(name) {
|
|
return this._animationsByName.get(name.toLowerCase());
|
|
}
|
|
getAnimationNames() {
|
|
return Array.from(this._animationsByName.keys());
|
|
}
|
|
getAnimationCategories() {
|
|
return Array.from(this._categoriesByName.keys());
|
|
}
|
|
search(searchTerm) {
|
|
let term = searchTerm.toLowerCase();
|
|
let res = new Classes_1.SearchResults();
|
|
this._search(term, res);
|
|
return res;
|
|
}
|
|
query(query) {
|
|
AnimUtils_1.AnimUtils.insertDefaultAnimQueryParams(query);
|
|
let res = new Classes_1.AnimResults();
|
|
this._query(query, res);
|
|
let matchingNoDupes = [];
|
|
new Set(res.matching).forEach(elm => matchingNoDupes.push(elm));
|
|
res.matching = matchingNoDupes;
|
|
let nonMatchingNoDupes = [];
|
|
new Set(res.nonMatching).forEach(elm => nonMatchingNoDupes.push(elm));
|
|
res.nonMatching = nonMatchingNoDupes;
|
|
return res;
|
|
}
|
|
_search(term, res) {
|
|
let catByName = this._categoriesByName.get(term);
|
|
if (catByName) {
|
|
res.category = catByName;
|
|
}
|
|
let animByName = this._animationsByName.get(term);
|
|
if (animByName) {
|
|
res.name = animByName;
|
|
}
|
|
this.animations.forEach(anim => {
|
|
anim.meta.metaTerms.forEach(meta => {
|
|
if (meta === term) {
|
|
res.meta.push(anim);
|
|
}
|
|
});
|
|
});
|
|
}
|
|
_query(query, res) {
|
|
if (query.categories.length) {
|
|
query.categories.forEach(catName => {
|
|
let category = this._categoriesByName.get(catName);
|
|
if (category) {
|
|
category._query(query, res);
|
|
}
|
|
});
|
|
}
|
|
else {
|
|
Utils_1.Utils.getAnimationsByQuery(this.animations, res, query);
|
|
}
|
|
}
|
|
}
|
|
exports.AnimCollection = AnimCollection;
|
|
|
|
},{"./AnimUtils":4,"./Classes":7,"./Utils":10}],2:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const Classes_1 = require("./Classes");
|
|
const AnimUtils_1 = require("./AnimUtils");
|
|
class AnimDB {
|
|
constructor(jibo) {
|
|
this.collections = [];
|
|
this.jibo = jibo;
|
|
}
|
|
push(animCollection) {
|
|
this.collections.push(animCollection);
|
|
}
|
|
pop() {
|
|
return this.collections.pop();
|
|
}
|
|
getAnimByName(animName) {
|
|
let anim;
|
|
for (let i = 0; i < this.collections.length; i++) {
|
|
let animDB = this.collections[i];
|
|
let a = animDB.getAnimByName(animName);
|
|
if (a) {
|
|
anim = a;
|
|
break;
|
|
}
|
|
}
|
|
return anim;
|
|
}
|
|
getAnimationNames() {
|
|
let names = [];
|
|
for (let i = 0; i < this.collections.length; i++) {
|
|
names = names.concat(this.collections[i].getAnimationNames());
|
|
}
|
|
return names;
|
|
}
|
|
getAnimationCategories() {
|
|
let names = [];
|
|
for (let i = 0; i < this.collections.length; i++) {
|
|
names = names.concat(this.collections[i].getAnimationCategories());
|
|
}
|
|
return names;
|
|
}
|
|
search(searchTerm) {
|
|
let term = searchTerm.toLowerCase();
|
|
let res = new Classes_1.SearchResults();
|
|
this.collections.forEach(animColl => {
|
|
animColl._search(term, res);
|
|
});
|
|
return res;
|
|
}
|
|
query(query) {
|
|
AnimUtils_1.AnimUtils.insertDefaultAnimQueryParams(query);
|
|
let res = new Classes_1.AnimResults();
|
|
this.collections.forEach(animColl => {
|
|
animColl._query(query, res);
|
|
});
|
|
let matchingNoDupes = [];
|
|
new Set(res.matching).forEach(elm => matchingNoDupes.push(elm));
|
|
res.matching = matchingNoDupes;
|
|
let nonMatchingNoDupes = [];
|
|
new Set(res.nonMatching).forEach(elm => nonMatchingNoDupes.push(elm));
|
|
res.nonMatching = nonMatchingNoDupes;
|
|
return res;
|
|
}
|
|
}
|
|
exports.AnimDB = AnimDB;
|
|
|
|
},{"./AnimUtils":4,"./Classes":7}],3:[function(require,module,exports){
|
|
"use strict";
|
|
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
return new (P || (P = Promise))(function (resolve, reject) {
|
|
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
|
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
});
|
|
};
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const path = require("path");
|
|
const fs = require("fs");
|
|
const jibo_cai_utils_1 = require("jibo-cai-utils");
|
|
const AnimDB_1 = require("./AnimDB");
|
|
const AnimCollection_1 = require("./AnimCollection");
|
|
const Animation_1 = require("./Animation");
|
|
const Category_1 = require("./Category");
|
|
const AnimUtils_1 = require("./AnimUtils");
|
|
const Utils_1 = require("./Utils");
|
|
const Classes_1 = require("./Classes");
|
|
const Range_1 = require("./Range");
|
|
const stringify = require('json-stable-stringify');
|
|
class AnimDBParser {
|
|
static readAnimDB(jibo, animDBPath, ...moreAnimDBPaths) {
|
|
moreAnimDBPaths.unshift(animDBPath);
|
|
let animDB = new AnimDB_1.AnimDB(jibo);
|
|
let promises = moreAnimDBPaths.map((rootDir) => {
|
|
return AnimDBParser.readAndAddAnimCollection(animDB, rootDir);
|
|
});
|
|
return Promise.all(promises)
|
|
.then(() => animDB);
|
|
}
|
|
static readAndAddAnimCollection(animDB, animDBPath) {
|
|
const rootDir = path.dirname(animDBPath);
|
|
return jibo_cai_utils_1.FileUtils.readFile(animDBPath)
|
|
.then(animStr => {
|
|
const animMetaMap = JSON.parse(animStr);
|
|
AnimDBParser.addAnimCollection(animDB, rootDir, animMetaMap);
|
|
});
|
|
}
|
|
static addAnimCollection(animDB, rootDir, animMetaMap) {
|
|
let collection = new AnimCollection_1.AnimCollection(animDB);
|
|
AnimDBParser.addToAnimCollection(collection, rootDir, animMetaMap);
|
|
animDB.push(collection);
|
|
}
|
|
static addToAnimCollection(collection, rootDir, animMetadataCollection) {
|
|
let kvAnimMetaArray;
|
|
if (animMetadataCollection instanceof Array) {
|
|
kvAnimMetaArray = animMetadataCollection;
|
|
}
|
|
else {
|
|
kvAnimMetaArray = [];
|
|
Object.keys(animMetadataCollection).forEach(key => {
|
|
kvAnimMetaArray.push([key, animMetadataCollection[key]]);
|
|
});
|
|
}
|
|
for (let [animName, animMeta] of kvAnimMetaArray) {
|
|
if (!animMeta.name) {
|
|
throw new Error(`Missing anim name: ${animName}`);
|
|
}
|
|
animName = animMeta.name.toLowerCase();
|
|
const anim = new Animation_1.Animation(collection, animMeta, rootDir);
|
|
let existingAnim = collection.getAnimByName(anim.name);
|
|
if (existingAnim) {
|
|
const paths = [existingAnim.meta.path, animMeta.path];
|
|
throw new Error(`Duplicate animation name: '${animName}' at paths: ${paths}`);
|
|
}
|
|
collection.addAnimation(anim);
|
|
anim.meta.categories.forEach(categoryName => {
|
|
let cat = collection.getCategoryByName(categoryName);
|
|
if (!cat) {
|
|
cat = new Category_1.Category(categoryName);
|
|
collection.addCategory(cat);
|
|
}
|
|
cat.addAnimation(anim);
|
|
});
|
|
}
|
|
}
|
|
static createAndWriteAnimMetaData(jibo, rootDir, outName) {
|
|
return AnimDBParser.createAnimMetaData(jibo, rootDir)
|
|
.then(allAnimData => {
|
|
const outPath = path.join(rootDir, outName + '.json');
|
|
const outData = stringify(allAnimData, { space: ' ' });
|
|
return jibo_cai_utils_1.PromiseUtils.promisify(h => fs.writeFile(outPath, outData, 'utf8', h));
|
|
});
|
|
}
|
|
static createAnimMetaData(jibo, rootDir) {
|
|
const animsDir = path.join(rootDir, 'animations');
|
|
return jibo_cai_utils_1.FileUtils.findAllFilesWithExt(animsDir, 'keys')
|
|
.then((filePaths) => {
|
|
const goodPaths = filePaths.filter(filePath => {
|
|
const relFilePath = path.relative(animsDir, filePath);
|
|
const pathElements = relFilePath.split(path.sep);
|
|
return !pathElements.some(el => el.startsWith('_'));
|
|
});
|
|
return AnimDBParser._createAnimMetaData(jibo, rootDir, goodPaths);
|
|
});
|
|
}
|
|
static _createAnimMetaData(jibo, rootDir, paths) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
let cachedAnimDB = jibo.animDB._animDB;
|
|
jibo.animDB._animDB = new AnimDB_1.AnimDB(jibo);
|
|
let collection = new AnimCollection_1.AnimCollection(jibo.animDB._animDB);
|
|
jibo.animDB.push(collection);
|
|
let completeMetadata = {};
|
|
let unparsed = [];
|
|
let parsed = [];
|
|
while (paths.length > 0) {
|
|
const unparsedCount = paths.length;
|
|
for (const path of paths) {
|
|
try {
|
|
const meta = yield AnimDBParser.parseAnimation(jibo, path, rootDir);
|
|
parsed.push(meta);
|
|
}
|
|
catch (err) {
|
|
if (err instanceof ReferenceError) {
|
|
unparsed.push(path);
|
|
}
|
|
else {
|
|
throw err;
|
|
}
|
|
}
|
|
}
|
|
if (unparsedCount === unparsed.length) {
|
|
throw new Error(`Could not resolve ${unparsedCount} animations: ${unparsed}`);
|
|
}
|
|
else {
|
|
paths = unparsed;
|
|
}
|
|
const rootDirResolved = path.resolve(rootDir);
|
|
let kvAnimMetaArray = [];
|
|
parsed.forEach(animData => {
|
|
const firstPart = animData.path.substring(0, rootDirResolved.length);
|
|
if (firstPart !== rootDirResolved) {
|
|
throw new Error(`Animation doesn't have the expected root path: ${[animData.path, rootDirResolved]}`);
|
|
}
|
|
animData.path = animData.path.substring(rootDirResolved.length + path.sep.length);
|
|
kvAnimMetaArray.push([animData.name, animData]);
|
|
});
|
|
AnimDBParser.addToAnimCollection(collection, rootDir, kvAnimMetaArray);
|
|
let tempAnimMetaMap = {};
|
|
kvAnimMetaArray.forEach(([key, value]) => {
|
|
tempAnimMetaMap[key] = value;
|
|
});
|
|
Object.assign(completeMetadata, tempAnimMetaMap);
|
|
parsed = [];
|
|
unparsed = [];
|
|
}
|
|
jibo.animDB._animDB = cachedAnimDB;
|
|
return completeMetadata;
|
|
});
|
|
}
|
|
static parseAnimation(jibo, filePath, rootDir) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
const animData = yield AnimDBParser.loadKeys(jibo, filePath, rootDir);
|
|
return AnimDBParser.parseAnimationFromAnim(animData, filePath);
|
|
});
|
|
}
|
|
static loadKeys(jibo, keysPath, rootDir) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
return new jibo.rendering.animation.KeysLoader(keysPath, rootDir).load();
|
|
});
|
|
}
|
|
static parseAnimationFromAnim(animData, filePath) {
|
|
let animdbTag;
|
|
let scale, speed, name;
|
|
try {
|
|
const defaultName = filePath ? path.basename(filePath, path.extname(filePath)) : 'UNKNOWN_ANIM';
|
|
animdbTag = animData.animdb || {};
|
|
name = Utils_1.Utils.parseString(animdbTag.name, defaultName);
|
|
scale = [
|
|
Utils_1.Utils.parseNumber(animdbTag.scaleMin, 1),
|
|
Utils_1.Utils.parseNumber(animdbTag.scaleMax, 1)
|
|
];
|
|
speed = [
|
|
Utils_1.Utils.parseNumber(animdbTag.speedMin, 1),
|
|
Utils_1.Utils.parseNumber(animdbTag.speedMax, 1)
|
|
];
|
|
}
|
|
catch (error) {
|
|
throw new Error(`Error parsing animation at path '${filePath}': '${error}'`);
|
|
}
|
|
if ((speed[0] <= 0) || (speed[0] > speed[1])) {
|
|
throw new Error(`Invalid speed bounds '${JSON.stringify(speed)}' for animation '${filePath}'`);
|
|
}
|
|
if (scale[0] > scale[1]) {
|
|
throw new Error(`Invalid scale bounds '${JSON.stringify(scale)}' for animation '${filePath}'`);
|
|
}
|
|
const categoryString = animdbTag.categories || '';
|
|
let categories = [];
|
|
categoryString.split(',').forEach(category => {
|
|
let catName = category.trim().toLowerCase();
|
|
if (catName.length) {
|
|
categories.push(catName);
|
|
}
|
|
});
|
|
const metaString = animdbTag.meta || '';
|
|
let metaTerms = [];
|
|
metaString.split(',').forEach(_metaTerm => {
|
|
let metaName = _metaTerm.trim().toLowerCase();
|
|
if (metaName.length) {
|
|
metaTerms.push(metaName);
|
|
}
|
|
});
|
|
const holdSafeKF = AnimUtils_1.AnimUtils.hasHoldSafe(animData, name);
|
|
let durationRange = [
|
|
speed[0] * animData.duration,
|
|
speed[1] * animData.duration
|
|
];
|
|
if (holdSafeKF !== -1) {
|
|
durationRange[1] = Range_1.INFINITE_DURATION;
|
|
}
|
|
let layers = AnimUtils_1.AnimUtils.checkLayers(animData);
|
|
if (metaTerms.indexOf(AnimUtils_1.AUDIO_ONLY_META) !== -1) {
|
|
Object.keys(layers).forEach(layer => {
|
|
if (layers[layer] && (layer !== Classes_1.LayerName.AudioEvent.short)) {
|
|
layers[layer] = false;
|
|
}
|
|
});
|
|
}
|
|
const animMetadata = {
|
|
name,
|
|
scale,
|
|
speed,
|
|
durationRange,
|
|
categories,
|
|
metaTerms,
|
|
holdSafeKF,
|
|
path: filePath,
|
|
duration: animData.duration,
|
|
startsNeutral: AnimUtils_1.AnimUtils.startsNeutral(animData),
|
|
endsNeutral: AnimUtils_1.AnimUtils.endsNeutral(animData),
|
|
hasAudio: AnimUtils_1.AnimUtils.hasAudio(animData),
|
|
orientation: AnimUtils_1.AnimUtils.calculateOrientation(animData),
|
|
layers
|
|
};
|
|
return animMetadata;
|
|
}
|
|
}
|
|
exports.AnimDBParser = AnimDBParser;
|
|
|
|
},{"./AnimCollection":1,"./AnimDB":2,"./AnimUtils":4,"./Animation":5,"./Category":6,"./Classes":7,"./Range":9,"./Utils":10,"fs":undefined,"jibo-cai-utils":undefined,"json-stable-stringify":undefined,"path":undefined}],4:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const Classes_1 = require("./Classes");
|
|
const LayerMocks_1 = require("./animation_formats/LayerMocks");
|
|
const BODY_ANGLE_EPSILON = 3;
|
|
const HOLD_SAFE_EVENT_NAME = 'HOLD_SAFE';
|
|
exports.AUDIO_ONLY_META = "audio-only";
|
|
class AnimUtils {
|
|
static _addMockLayer(animData, type) {
|
|
animData.layers.push(LayerMocks_1.LayerTemplate.generateLayer(type, type));
|
|
}
|
|
static scaleTimeInPlace(animData, scale) {
|
|
animData.layers.forEach((layer) => {
|
|
layer.keyframes.forEach(kf => {
|
|
kf.time = Math.round(kf.time * scale);
|
|
});
|
|
});
|
|
animData.duration = Math.round(animData.duration * scale);
|
|
}
|
|
static scaleBodyInPlace(animData, scale) {
|
|
AnimUtils.forEachLayerType(animData, Classes_1.LayerName.Body, (layer) => {
|
|
layer.keyframes.forEach(kf => {
|
|
kf.value.Head *= scale;
|
|
kf.value.Pelvis *= scale;
|
|
kf.value.Torso *= scale;
|
|
});
|
|
});
|
|
}
|
|
static flipScreenLeftRight(animData) {
|
|
let handler = (layer) => {
|
|
layer.keyframes.forEach(kf => {
|
|
kf.value.Translate.x *= -1;
|
|
});
|
|
};
|
|
AnimUtils.forEachLayerType(animData, Classes_1.LayerName.Eye, handler);
|
|
AnimUtils.forEachLayerType(animData, Classes_1.LayerName.Overlay, handler);
|
|
}
|
|
static startsNeutral(animData) {
|
|
let ret = true;
|
|
let earliestFrame = animData.duration;
|
|
AnimUtils.forEachLayerType(animData, Classes_1.LayerName.Body, (layer) => {
|
|
if (layer.keyframes.length) {
|
|
let kf = layer.keyframes[0];
|
|
if (kf.time < earliestFrame) {
|
|
earliestFrame = kf.time;
|
|
if (Math.abs(kf.value.Pelvis) > BODY_ANGLE_EPSILON ||
|
|
Math.abs(kf.value.Head) > BODY_ANGLE_EPSILON ||
|
|
Math.abs(kf.value.Torso) > BODY_ANGLE_EPSILON) {
|
|
ret = false;
|
|
}
|
|
}
|
|
}
|
|
});
|
|
return ret;
|
|
}
|
|
static endsNeutral(animData) {
|
|
let ret = true;
|
|
let latestTime = -1;
|
|
AnimUtils.forEachLayerType(animData, Classes_1.LayerName.Body, (layer) => {
|
|
if (layer.keyframes.length) {
|
|
let kf = layer.keyframes[layer.keyframes.length - 1];
|
|
if (kf.time > latestTime) {
|
|
latestTime = kf.time;
|
|
if (Math.abs(kf.value.Pelvis) > BODY_ANGLE_EPSILON ||
|
|
Math.abs(kf.value.Head) > BODY_ANGLE_EPSILON ||
|
|
Math.abs(kf.value.Torso) > BODY_ANGLE_EPSILON) {
|
|
ret = false;
|
|
}
|
|
}
|
|
}
|
|
});
|
|
return ret;
|
|
}
|
|
static checkLayers(animData, strict = true) {
|
|
let layerPresence = {};
|
|
Classes_1.LayerName.Layers.forEach(layerName => {
|
|
if (AnimUtils.hasLayer(animData, layerName, strict)) {
|
|
layerPresence[layerName.short] = true;
|
|
}
|
|
});
|
|
return layerPresence;
|
|
}
|
|
static hasAudio(animData) {
|
|
return AnimUtils.hasLayer(animData, Classes_1.LayerName.AudioEvent);
|
|
}
|
|
static hasLayer(animData, layerName, strict = true) {
|
|
let layerCheck = [];
|
|
AnimUtils.forEachLayerType(animData, layerName, (layer) => {
|
|
if (strict) {
|
|
layerCheck.push(layer.visible && (layer.keyframes.length !== 0));
|
|
}
|
|
else {
|
|
layerCheck.push(true);
|
|
}
|
|
});
|
|
return layerCheck.some(hasContent => hasContent);
|
|
}
|
|
static hasHoldSafe(animData, name) {
|
|
let kf = -1;
|
|
AnimUtils.forEachLayerType(animData, Classes_1.LayerName.Event, (layer) => {
|
|
layer.keyframes.forEach(layerKF => {
|
|
if (layerKF.value.Event.name === HOLD_SAFE_EVENT_NAME) {
|
|
if (kf !== -1) {
|
|
throw new Error(`Two HOLD_SAFE keyframes defined in animation` +
|
|
` '${name}' at frames ${kf} and ${layerKF.time}`);
|
|
}
|
|
kf = layerKF.time;
|
|
}
|
|
});
|
|
});
|
|
return kf;
|
|
}
|
|
static calculateOrientation(animData) {
|
|
let headSum = 0;
|
|
let pelvisSum = 0;
|
|
let torsoSum = 0;
|
|
let numFrames = 0;
|
|
AnimUtils.forEachLayerType(animData, Classes_1.LayerName.Body, (layer) => {
|
|
layer.keyframes.forEach(layerKF => {
|
|
numFrames++;
|
|
headSum += layerKF.value.Head;
|
|
pelvisSum += layerKF.value.Pelvis;
|
|
torsoSum += layerKF.value.Torso;
|
|
});
|
|
});
|
|
headSum /= numFrames;
|
|
pelvisSum /= numFrames;
|
|
torsoSum /= numFrames;
|
|
let bodySum = (torsoSum + pelvisSum) / 2;
|
|
if (Math.abs(bodySum) > 10) {
|
|
return (bodySum > 0) ? Classes_1.Orientation.LEFT : Classes_1.Orientation.RIGHT;
|
|
}
|
|
else {
|
|
return (headSum > 0) ? Classes_1.Orientation.LEFT : Classes_1.Orientation.RIGHT;
|
|
}
|
|
}
|
|
static forEachLayerType(animData, layerTypeName, handler) {
|
|
let name = layerTypeName.long || layerTypeName.short;
|
|
animData.layers.forEach(layer => {
|
|
if (layer.type === name) {
|
|
handler(layer);
|
|
}
|
|
});
|
|
}
|
|
static insertDefaultAnimQueryParams(query) {
|
|
if (!query.categories) {
|
|
query.categories = [];
|
|
}
|
|
if (query.category) {
|
|
query.categories.push(query.category);
|
|
}
|
|
for (let i = 0; i < query.categories.length; i++) {
|
|
query.categories[i] = query.categories[i].toLowerCase();
|
|
}
|
|
query.includeCat = query.includeCat || [];
|
|
query.includeSomeCat = query.includeSomeCat || [];
|
|
query.excludeCat = query.excludeCat || [];
|
|
query.includeMeta = query.includeMeta || [];
|
|
query.includeSomeMeta = query.includeSomeMeta || [];
|
|
query.excludeMeta = query.excludeMeta || [];
|
|
const filters = [query.includeCat, query.includeSomeCat, query.excludeCat, query.includeMeta, query.includeSomeMeta, query.excludeMeta];
|
|
filters.forEach(array => {
|
|
for (let i = 0; i < array.length; i++) {
|
|
array[i] = array[i].toLowerCase();
|
|
}
|
|
});
|
|
if (!query.durationError) {
|
|
query.durationError = 0;
|
|
}
|
|
if (!query.duration) {
|
|
query.duration = -1;
|
|
}
|
|
if (typeof query.hasAudio === 'undefined') {
|
|
query.hasAudio = Classes_1.HasAudio.DONT_CARE;
|
|
}
|
|
}
|
|
}
|
|
exports.AnimUtils = AnimUtils;
|
|
|
|
},{"./Classes":7,"./animation_formats/LayerMocks":12}],5:[function(require,module,exports){
|
|
"use strict";
|
|
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
return new (P || (P = Promise))(function (resolve, reject) {
|
|
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
|
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
});
|
|
};
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const Range_1 = require("./Range");
|
|
const Utils_1 = require("./Utils");
|
|
const Playback_1 = require("./Playback");
|
|
const Classes_1 = require("./Classes");
|
|
const log_1 = require("./log");
|
|
const log = log_1.default.createChild("Animation");
|
|
class Animation {
|
|
constructor(parent, meta, resourceRoot, animData) {
|
|
this.parent = parent;
|
|
this.meta = meta;
|
|
this.resourceRoot = resourceRoot;
|
|
this.animData = animData;
|
|
this.animDataCache = {};
|
|
this.name = meta.name;
|
|
this.durationRange = new Range_1.Range(meta.durationRange[0], meta.durationRange[1]);
|
|
}
|
|
createFromConfig(config = { cache: null }) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
log.debug(`Configuring Animation ${this.name} for configuration: `, config);
|
|
let transformation = this._getTransformation(config);
|
|
const playback = new Playback_1.Playback(transformation, config.cache, this);
|
|
return playback.init(config);
|
|
});
|
|
}
|
|
play(config = { cache: null }, options) {
|
|
log.debug(`Configuring Animation ${this.name} with config: `, config, ` for immediate playback with options: `, options);
|
|
let transformation = this._getTransformation(config);
|
|
const playback = new Playback_1.Playback(transformation, config.cache, this);
|
|
return {
|
|
playback: playback,
|
|
result: playback.initAndPlay(config, options)
|
|
};
|
|
}
|
|
_getTransformation(options) {
|
|
let trans = new Classes_1.Transform();
|
|
if (options) {
|
|
if (options.orientation) {
|
|
let reqOrientation = options.orientation;
|
|
if (reqOrientation !== this.meta.orientation) {
|
|
trans.shouldFlipLeftRight = true;
|
|
}
|
|
}
|
|
if (options.speed) {
|
|
trans.speed = Utils_1.Utils.limitToRange(options.speed, this.meta.speed);
|
|
}
|
|
if (options.exaggerate) {
|
|
trans.exaggerate = Utils_1.Utils.limitToRange(options.exaggerate, this.meta.scale);
|
|
}
|
|
if (options.duration) {
|
|
if (options.duration < this.meta.durationRange[0]) {
|
|
trans.speed = this.meta.speed[0];
|
|
}
|
|
else if (options.duration < trans.speed * this.meta.duration) {
|
|
trans.speed = options.duration / this.meta.duration;
|
|
trans.speed = Utils_1.Utils.limitToRange(trans.speed, this.meta.speed);
|
|
}
|
|
else if (this.meta.holdSafeKF !== -1) {
|
|
trans.framesToHold = options.duration - trans.speed * this.meta.duration;
|
|
}
|
|
else if (options.duration > trans.speed * this.meta.duration) {
|
|
if (typeof options.speed !== 'number') {
|
|
trans.speed = options.duration / this.meta.duration;
|
|
trans.speed = Utils_1.Utils.limitToRange(trans.speed, this.meta.speed);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
return trans;
|
|
}
|
|
}
|
|
exports.Animation = Animation;
|
|
|
|
},{"./Classes":7,"./Playback":8,"./Range":9,"./Utils":10,"./log":15}],6:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const Utils_1 = require("./Utils");
|
|
const AnimUtils_1 = require("./AnimUtils");
|
|
const Classes_1 = require("./Classes");
|
|
class Category {
|
|
constructor(name) {
|
|
this.name = name;
|
|
this.animations = [];
|
|
this.animationsByName = new Map();
|
|
}
|
|
addAnimation(anim) {
|
|
this.animations.push(anim);
|
|
this.animationsByName.set(anim.name, anim);
|
|
}
|
|
query(query) {
|
|
AnimUtils_1.AnimUtils.insertDefaultAnimQueryParams(query);
|
|
let res = new Classes_1.AnimResults();
|
|
this._query(query, res);
|
|
return res;
|
|
}
|
|
_query(query, res) {
|
|
Utils_1.Utils.getAnimationsByQuery(this.animations, res, query);
|
|
}
|
|
}
|
|
exports.Category = Category;
|
|
|
|
},{"./AnimUtils":4,"./Classes":7,"./Utils":10}],7:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
class Transform {
|
|
constructor() {
|
|
this.framesToHold = -1;
|
|
this.speed = 1;
|
|
this.exaggerate = 1;
|
|
this.shouldFlipLeftRight = false;
|
|
}
|
|
}
|
|
exports.Transform = Transform;
|
|
var Orientation;
|
|
(function (Orientation) {
|
|
Orientation["LEFT"] = "LEFT";
|
|
Orientation["RIGHT"] = "RIGHT";
|
|
})(Orientation = exports.Orientation || (exports.Orientation = {}));
|
|
var HasAudio;
|
|
(function (HasAudio) {
|
|
HasAudio["YES"] = "YES";
|
|
HasAudio["NO"] = "NO";
|
|
HasAudio["DONT_CARE"] = "DONT_CARE";
|
|
})(HasAudio = exports.HasAudio || (exports.HasAudio = {}));
|
|
class AnimResults {
|
|
constructor() {
|
|
this.matching = [];
|
|
this.nonMatching = [];
|
|
}
|
|
}
|
|
exports.AnimResults = AnimResults;
|
|
class SearchResults {
|
|
constructor() {
|
|
this.meta = [];
|
|
}
|
|
}
|
|
exports.SearchResults = SearchResults;
|
|
class LayerName {
|
|
constructor(short, long) {
|
|
this.short = short;
|
|
this.long = long;
|
|
}
|
|
}
|
|
LayerName.Body = new LayerName('Body');
|
|
LayerName.Eye = new LayerName('Eye');
|
|
LayerName.EyeTexture = new LayerName('EyeTexture', 'Eye Texture');
|
|
LayerName.Overlay = new LayerName('Overlay');
|
|
LayerName.OverlayTexture = new LayerName('OverlayTexture', 'Overlay Texture');
|
|
LayerName.AudioEvent = new LayerName('AudioEvent', 'Audio Event');
|
|
LayerName.Event = new LayerName('Event');
|
|
LayerName.Pixi = new LayerName('Pixi');
|
|
LayerName.BackgroundTexture = new LayerName('BackgroundTexture', 'Background Texture');
|
|
LayerName.LED = new LayerName('LED');
|
|
LayerName.Layers = [
|
|
LayerName.Body,
|
|
LayerName.Eye,
|
|
LayerName.EyeTexture,
|
|
LayerName.Overlay,
|
|
LayerName.OverlayTexture,
|
|
LayerName.AudioEvent,
|
|
LayerName.Event,
|
|
LayerName.Pixi,
|
|
LayerName.BackgroundTexture,
|
|
LayerName.LED
|
|
];
|
|
exports.LayerName = LayerName;
|
|
var BuilderLayer;
|
|
(function (BuilderLayer) {
|
|
BuilderLayer["BEAT"] = "beat";
|
|
BuilderLayer["DEFAULT"] = "default";
|
|
BuilderLayer["POSTURE"] = "posture";
|
|
})(BuilderLayer = exports.BuilderLayer || (exports.BuilderLayer = {}));
|
|
|
|
},{}],8:[function(require,module,exports){
|
|
"use strict";
|
|
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
return new (P || (P = Promise))(function (resolve, reject) {
|
|
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
|
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
});
|
|
};
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const uuid = require("uuid");
|
|
const path = require("path");
|
|
const events = require("events");
|
|
const jibo_cai_utils_1 = require("jibo-cai-utils");
|
|
const jibo_expression_client_1 = require("jibo-expression-client");
|
|
const Classes_1 = require("./Classes");
|
|
const AnimUtils_1 = require("./AnimUtils");
|
|
const log_1 = require("./log");
|
|
const log = log_1.default.createChild("Playback");
|
|
const FRAMERATE = 30;
|
|
const defaultOptions = {
|
|
ownerInformation: 'AnimDB',
|
|
disableSetFaceAnim: false,
|
|
screenCenterOverride: true
|
|
};
|
|
class ExtPromise {
|
|
constructor() {
|
|
this.promise = new Promise((res, rej) => {
|
|
this.resolve = res;
|
|
this.reject = rej;
|
|
});
|
|
}
|
|
}
|
|
class Playback extends events.EventEmitter {
|
|
constructor(transform, cacheName, animation) {
|
|
super();
|
|
this.transform = transform;
|
|
this.cacheName = cacheName;
|
|
this.animation = animation;
|
|
this.runtimeKeys = false;
|
|
this.holdSafeDuration = 0;
|
|
this.runtimeKeys = !this.animation.meta.path;
|
|
this.jibo = this.animation.parent.parent.jibo;
|
|
}
|
|
init(config) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
this._init(config);
|
|
this.keysAnimation = yield this.loadAnimation();
|
|
this.instance = this.keysAnimation.instance;
|
|
log.debug(`Initialized playback ${this.animation.name}`);
|
|
return this;
|
|
});
|
|
}
|
|
initAndPlay(config, options) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
this.playExtPr = new ExtPromise();
|
|
this._init(config);
|
|
this.resolvePlaybackOptions(options);
|
|
this.keysAnimation = yield this.loadAnimation(true);
|
|
this.instance = this.keysAnimation.instance;
|
|
this.registerEventsAndHandlers();
|
|
const state = yield this.playExtPr.promise;
|
|
yield this.handlePlaybackCompletion(state);
|
|
return state;
|
|
});
|
|
}
|
|
play(options) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
this.playExtPr = new ExtPromise();
|
|
this.resolvePlaybackOptions(options);
|
|
this.registerEventsAndHandlers();
|
|
if ((this.options.screenCenterOverride === false) && this.hasScreenDOFs) {
|
|
try {
|
|
yield this.jibo.expression.centerRobot({
|
|
requestor: this.options.ownerInformation,
|
|
centerGlobally: false,
|
|
dofs: this.jibo.expression.dofs.SCREEN
|
|
});
|
|
}
|
|
catch (err) {
|
|
this.playExtPr.reject(err);
|
|
}
|
|
}
|
|
try {
|
|
if (!this.hasBeenStopped) {
|
|
log.debug(`Playback ${this.animation.name} playing with these options: `, this.options);
|
|
yield this.keysAnimation.instance.play(this.options.ownerInformation);
|
|
}
|
|
}
|
|
catch (err) {
|
|
this.playExtPr.reject(err);
|
|
}
|
|
const state = yield this.playExtPr.promise;
|
|
yield this.handlePlaybackCompletion(state);
|
|
return state;
|
|
});
|
|
}
|
|
stop() {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
if (this.keysAnimation) {
|
|
try {
|
|
yield this.keysAnimation.instance.stop();
|
|
}
|
|
catch (error) {
|
|
log.warn(`Could not stop instance that no longer exists: `, error);
|
|
}
|
|
}
|
|
if (this.assetToken) {
|
|
this.assetToken.unload();
|
|
this.assetToken = null;
|
|
}
|
|
});
|
|
}
|
|
_init(config) {
|
|
if (!config) {
|
|
config = {
|
|
cache: this.jibo.loader.activeCache
|
|
};
|
|
}
|
|
log.debug(`Initializing playback ${this.animation.name} with config: `, config);
|
|
if (this.runtimeKeys) {
|
|
this.filePath = this.animation.resourceRoot;
|
|
}
|
|
else {
|
|
this.filePath = path.join(this.animation.resourceRoot, this.animation.meta.path);
|
|
}
|
|
if (this.animation.meta.metaTerms.indexOf(AnimUtils_1.AUDIO_ONLY_META) !== -1) {
|
|
config.layer = Classes_1.BuilderLayer.BEAT;
|
|
}
|
|
if (this.transform.shouldFlipLeftRight || this.transform.exaggerate) {
|
|
let flipMult = this.transform.shouldFlipLeftRight ? -1 : 1;
|
|
let flipAndExagMult = flipMult * (this.transform.exaggerate || 1);
|
|
if ((flipMult !== 1) || (flipAndExagMult !== 1)) {
|
|
let dofs = {
|
|
bottomSection_r: 1,
|
|
middleSection_r: 1,
|
|
topSection_r: 1,
|
|
eyeSubRootBn_t: 1
|
|
};
|
|
Object.keys(dofs).forEach(dof => {
|
|
if (dof === "eyeSubRootBn_t_2") {
|
|
dofs[dof] *= flipMult;
|
|
}
|
|
else {
|
|
dofs[dof] *= flipAndExagMult;
|
|
}
|
|
});
|
|
config.scale = dofs;
|
|
}
|
|
}
|
|
if (this.transform.framesToHold !== -1) {
|
|
this.holdSafeDuration = ((this.transform.framesToHold / FRAMERATE) * 1000);
|
|
}
|
|
if (this.transform.speed !== 1) {
|
|
config.speed = this.transform.speed;
|
|
}
|
|
this.duration = this.animation.meta.duration;
|
|
if (this.transform.speed !== -1) {
|
|
this.duration *= this.transform.speed;
|
|
}
|
|
if (this.transform.framesToHold !== -1) {
|
|
this.duration += this.transform.framesToHold;
|
|
}
|
|
this.config = config;
|
|
}
|
|
resolvePlaybackOptions(options) {
|
|
const playOptions = Object.assign({}, defaultOptions, options);
|
|
this.options = playOptions;
|
|
}
|
|
registerEventsAndHandlers() {
|
|
const dofsInScreen = this.jibo.expression.dofs.SCREEN;
|
|
const dofsInAnim = this.keysAnimation.instance.dofs;
|
|
const dofsNotInAnim = dofsInScreen.minus(dofsInAnim);
|
|
this.hasScreenDOFs = (dofsNotInAnim.getDOFs().length !== dofsInScreen.getDOFs().length);
|
|
if (this.hasScreenDOFs && !this.options.disableSetFaceAnim) {
|
|
this.jibo.face.eye.addAnimation(this.keysAnimation);
|
|
}
|
|
const stopHandler = (state) => {
|
|
this.hasBeenStopped = true;
|
|
log.debug(`Playback ${this.animation.name} was stopped with state ${state}`);
|
|
this._cleanup();
|
|
this.playExtPr.resolve(state);
|
|
};
|
|
const holdSafeHandler = () => __awaiter(this, void 0, void 0, function* () {
|
|
try {
|
|
if (this.keysAnimation) {
|
|
yield this.keysAnimation.instance.pause();
|
|
yield jibo_cai_utils_1.TimeUtils.wait(this.holdSafeDuration);
|
|
}
|
|
if (this.keysAnimation) {
|
|
yield this.keysAnimation.instance.resume();
|
|
}
|
|
}
|
|
catch (error) {
|
|
log.warn(`Error in hold-safe logic for animation ${this.animation.name}: `, error);
|
|
}
|
|
});
|
|
this.keysAnimation.instance.events.stopped.on(() => stopHandler(jibo_expression_client_1.AnimationState.STOPPED));
|
|
this.keysAnimation.instance.events.cancelled.on(() => stopHandler(jibo_expression_client_1.AnimationState.CANCELLED));
|
|
this.keysAnimation.instance.events.rejected.on(() => stopHandler(jibo_expression_client_1.AnimationState.REJECTED));
|
|
if (this.holdSafeDuration > 0) {
|
|
this.keysAnimation.instance.events.holdSafe.on(holdSafeHandler);
|
|
}
|
|
}
|
|
handlePlaybackCompletion(state) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
if (state === jibo_expression_client_1.AnimationState.REJECTED) {
|
|
log.warn(`Playback ${this.animation.name} was rejected! (See DOFArbiter debug for more details)`);
|
|
}
|
|
else if (this.options.forceReturnToIdle) {
|
|
log.debug(`Returning playback ${this.animation.name} to idle pose.`);
|
|
if (!Playback.DOFS_TO_CENTER) {
|
|
const dofs = this.jibo.expression.dofs;
|
|
Playback.DOFS_TO_CENTER = dofs.ALL.minus(dofs.BASE).minus(dofs.EYE_TRANSLATE);
|
|
}
|
|
yield this.jibo.expression.centerRobot({
|
|
requestor: this.options.ownerInformation,
|
|
dofs: Playback.DOFS_TO_CENTER,
|
|
centerGlobally: false
|
|
});
|
|
}
|
|
});
|
|
}
|
|
_cleanup() {
|
|
if (this.keysAnimation) {
|
|
if (this.hasScreenDOFs && !this.options.disableSetFaceAnim) {
|
|
this.jibo.face.eye.removeAnimation(this.keysAnimation);
|
|
}
|
|
else {
|
|
this.keysAnimation.destroy();
|
|
}
|
|
this.keysAnimation = null;
|
|
if (this.assetToken) {
|
|
this.assetToken.unload();
|
|
this.assetToken = null;
|
|
}
|
|
}
|
|
this.instance = null;
|
|
}
|
|
loadAnimation(andPlay = false) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
const id = this.filePath;
|
|
if (this.runtimeKeys) {
|
|
this.filePath = path.join(id, uuid.v4());
|
|
}
|
|
return new Promise((resolve, reject) => {
|
|
const load = this.jibo.loader.load({
|
|
id: id,
|
|
cache: this.cacheName,
|
|
options: this.config,
|
|
data: this.runtimeKeys ? this.animation.animData : null,
|
|
src: this.filePath,
|
|
upload: true,
|
|
root: this.animation.resourceRoot,
|
|
type: 'keys',
|
|
}, (error, keysData) => {
|
|
if (error) {
|
|
reject(error);
|
|
}
|
|
else {
|
|
if (!this.assetToken) {
|
|
return;
|
|
}
|
|
if (andPlay && this.options) {
|
|
resolve(keysData.getAndPlayAnim(Object.assign({ src: this.filePath }, this.config), this.options.ownerInformation));
|
|
}
|
|
else {
|
|
resolve(keysData.getAnim(Object.assign({ src: this.filePath }, this.config)));
|
|
}
|
|
}
|
|
});
|
|
this.assetToken = load.tokens[0];
|
|
});
|
|
});
|
|
}
|
|
}
|
|
exports.Playback = Playback;
|
|
|
|
},{"./AnimUtils":4,"./Classes":7,"./log":15,"events":undefined,"jibo-cai-utils":undefined,"jibo-expression-client":undefined,"path":undefined,"uuid":undefined}],9:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
exports.INFINITE_DURATION = 1e6;
|
|
class Range {
|
|
constructor(min, max) {
|
|
this.min = min;
|
|
this.max = max;
|
|
if (min > max) {
|
|
throw new Error(`Invalid bounds ${this.toString()}`);
|
|
}
|
|
}
|
|
toString() {
|
|
return `[${this.min}, ${this.max}]`;
|
|
}
|
|
limit(num) {
|
|
if (num < this.min) {
|
|
return this.min;
|
|
}
|
|
else if (num > this.max) {
|
|
return this.max;
|
|
}
|
|
else {
|
|
return num;
|
|
}
|
|
}
|
|
isUpperInfinite() {
|
|
return (this.max === exports.INFINITE_DURATION);
|
|
}
|
|
distanceFrom(num) {
|
|
if (num < this.min) {
|
|
return this.min - num;
|
|
}
|
|
else if (num > this.max) {
|
|
return num - this.max;
|
|
}
|
|
else {
|
|
return 0;
|
|
}
|
|
}
|
|
}
|
|
exports.Range = Range;
|
|
|
|
},{}],10:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const Classes_1 = require("./Classes");
|
|
let SemverUtils = require('semver-utils');
|
|
class Utils {
|
|
static parseString(input, defaultVal) {
|
|
if (!input || !(input.length)) {
|
|
return defaultVal;
|
|
}
|
|
return input;
|
|
}
|
|
static parseNumber(input, defaultVal) {
|
|
if (typeof input === 'number') {
|
|
return input;
|
|
}
|
|
if (!input || !(input.length)) {
|
|
return defaultVal;
|
|
}
|
|
try {
|
|
let num = parseFloat(input);
|
|
return num;
|
|
}
|
|
catch (e) {
|
|
return defaultVal;
|
|
}
|
|
}
|
|
static parseSemVer(input) {
|
|
let parse = SemverUtils.parse(input);
|
|
return {
|
|
semver: parse.semver,
|
|
version: parse.version,
|
|
major: parseInt(parse.major),
|
|
minor: parseInt(parse.minor),
|
|
patch: parseInt(parse.patch),
|
|
release: parse.release
|
|
};
|
|
}
|
|
static getAnimationsByQuery(animations, interimResults, query) {
|
|
animations.forEach(anim => {
|
|
if (Utils.audioMatch(anim, query.hasAudio) &&
|
|
Utils.catMatch(anim, query.includeCat, query.includeSomeCat, query.excludeCat) &&
|
|
Utils.metaMatch(anim, query.includeMeta, query.includeSomeMeta, query.excludeMeta)) {
|
|
Utils.addIfDurationMatch(anim, query.duration, query.durationError, interimResults);
|
|
}
|
|
});
|
|
}
|
|
static audioMatch(animation, shouldHaveAudio) {
|
|
return (shouldHaveAudio === Classes_1.HasAudio.DONT_CARE) ||
|
|
(shouldHaveAudio === Classes_1.HasAudio.YES && animation.meta.hasAudio) ||
|
|
(shouldHaveAudio === Classes_1.HasAudio.NO && !animation.meta.hasAudio);
|
|
}
|
|
static catMatch(animation, allOfCat, someOfCat, noneOfCat) {
|
|
const categories = animation.meta.categories;
|
|
const allOfMatch = (allOfCat.length > 0) ? allOfCat.every(cat => categories.indexOf(cat) !== -1) : true;
|
|
const someOfMatch = (someOfCat.length > 0) ? someOfCat.some(cat => categories.indexOf(cat) !== -1) : true;
|
|
const noneOfMatch = (noneOfCat.length > 0) ? noneOfCat.every(cat => categories.indexOf(cat) === -1) : true;
|
|
return (allOfMatch && someOfMatch && noneOfMatch);
|
|
}
|
|
static metaMatch(animation, allOfMeta, someOfMeta, noneOfMeta) {
|
|
const metas = animation.meta.metaTerms;
|
|
const allOfMatch = (allOfMeta.length > 0) ? allOfMeta.every(meta => metas.indexOf(meta) !== -1) : true;
|
|
const someOfMatch = (someOfMeta.length > 0) ? someOfMeta.some(meta => metas.indexOf(meta) !== -1) : true;
|
|
const noneOfMatch = (noneOfMeta.length > 0) ? noneOfMeta.every(meta => metas.indexOf(meta) === -1) : true;
|
|
return (allOfMatch && someOfMatch && noneOfMatch);
|
|
}
|
|
static addIfDurationMatch(animation, duration, durationError, res) {
|
|
if (duration === -1) {
|
|
res.matching.push(animation);
|
|
}
|
|
else {
|
|
let dist = Utils.distanceFromRange(duration, animation.meta.durationRange);
|
|
if (dist === 0) {
|
|
res.matching.push(animation);
|
|
}
|
|
else if (dist <= durationError) {
|
|
res.nonMatching.push(animation);
|
|
}
|
|
}
|
|
}
|
|
static limitToRange(num, range) {
|
|
if (num < range[0]) {
|
|
return range[0];
|
|
}
|
|
else if (num > range[1]) {
|
|
return range[1];
|
|
}
|
|
else {
|
|
return num;
|
|
}
|
|
}
|
|
static distanceFromRange(num, range) {
|
|
if (num < range[0]) {
|
|
return range[0] - num;
|
|
}
|
|
else if (num > range[1]) {
|
|
return num - range[1];
|
|
}
|
|
else {
|
|
return 0;
|
|
}
|
|
}
|
|
}
|
|
exports.Utils = Utils;
|
|
|
|
},{"./Classes":7,"semver-utils":undefined}],11:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
|
},{}],12:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
let generateId = require('jibo-keyframes').generateId;
|
|
class LayerTemplate {
|
|
static generateLayer(name, type) {
|
|
let layer = {};
|
|
layer.id = generateId();
|
|
layer.name = name;
|
|
layer.type = type;
|
|
layer.visible = true;
|
|
layer.locked = false;
|
|
layer.keyframes = [];
|
|
return layer;
|
|
}
|
|
}
|
|
exports.LayerTemplate = LayerTemplate;
|
|
|
|
},{"jibo-keyframes":undefined}],13:[function(require,module,exports){
|
|
"use strict";
|
|
function __export(m) {
|
|
for (var p in m) if (!exports.hasOwnProperty(p)) exports[p] = m[p];
|
|
}
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
__export(require("./LayerMocks"));
|
|
const format_0_6_x = require("./0_6_X");
|
|
exports.format_0_6_x = format_0_6_x;
|
|
|
|
},{"./0_6_X":11,"./LayerMocks":12}],14:[function(require,module,exports){
|
|
"use strict";
|
|
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
return new (P || (P = Promise))(function (resolve, reject) {
|
|
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
|
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
});
|
|
};
|
|
function __export(m) {
|
|
for (var p in m) if (!exports.hasOwnProperty(p)) exports[p] = m[p];
|
|
}
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const path = require("path");
|
|
const fs = require("fs");
|
|
const AnimDBParser_1 = require("./AnimDBParser");
|
|
exports.AnimDBParser = AnimDBParser_1.AnimDBParser;
|
|
const AnimCollection_1 = require("./AnimCollection");
|
|
exports.AnimCollection = AnimCollection_1.AnimCollection;
|
|
const Animation_1 = require("./Animation");
|
|
exports.Animation = Animation_1.Animation;
|
|
const AnimDB_1 = require("./AnimDB");
|
|
exports.AnimDB = AnimDB_1.AnimDB;
|
|
const Playback_1 = require("./Playback");
|
|
exports.Playback = Playback_1.Playback;
|
|
__export(require("./animation_formats"));
|
|
__export(require("./Classes"));
|
|
function init(jibo, animDBPath, ...moreAnimDBPaths) {
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
if (!animDBPath) {
|
|
exports._animDB = new AnimDB_1.AnimDB(jibo);
|
|
}
|
|
else {
|
|
exports._animDB = yield AnimDBParser_1.AnimDBParser.readAnimDB(jibo, animDBPath, ...moreAnimDBPaths);
|
|
}
|
|
});
|
|
}
|
|
exports.init = init;
|
|
function isInitialized() {
|
|
return !!exports._animDB;
|
|
}
|
|
exports.isInitialized = isInitialized;
|
|
function resolveAnimDB(jibo, dir) {
|
|
let animDBPath;
|
|
let packjson;
|
|
if (!dir) {
|
|
const adaPath = jibo.utils.PathUtils.resolve('jibo-anim-db-animations');
|
|
dir = adaPath ? path.dirname(adaPath) : undefined;
|
|
}
|
|
try {
|
|
packjson = require(path.resolve(dir, 'package.json'));
|
|
}
|
|
catch (error) {
|
|
return undefined;
|
|
}
|
|
if (packjson && packjson.jibo) {
|
|
if (packjson.jibo.animdb && (path.extname(packjson.jibo.animdb).toLowerCase() === '.json')) {
|
|
animDBPath = path.resolve(dir, packjson.jibo.animdb);
|
|
}
|
|
else {
|
|
animDBPath = path.resolve(dir, 'animdb.json');
|
|
}
|
|
}
|
|
if (fs.existsSync(animDBPath)) {
|
|
return animDBPath;
|
|
}
|
|
return undefined;
|
|
}
|
|
exports.resolveAnimDB = resolveAnimDB;
|
|
function getAnimByName(animName) {
|
|
return exports._animDB.getAnimByName(animName);
|
|
}
|
|
exports.getAnimByName = getAnimByName;
|
|
function getAnimationNames() {
|
|
return exports._animDB.getAnimationNames();
|
|
}
|
|
exports.getAnimationNames = getAnimationNames;
|
|
function getAnimationCategories() {
|
|
return exports._animDB.getAnimationCategories();
|
|
}
|
|
exports.getAnimationCategories = getAnimationCategories;
|
|
function search(searchTerm) {
|
|
return exports._animDB.search(searchTerm);
|
|
}
|
|
exports.search = search;
|
|
function query(query) {
|
|
return exports._animDB.query(query);
|
|
}
|
|
exports.query = query;
|
|
function push(animCollection) {
|
|
exports._animDB.push(animCollection);
|
|
}
|
|
exports.push = push;
|
|
function pop() {
|
|
return exports._animDB.pop();
|
|
}
|
|
exports.pop = pop;
|
|
|
|
},{"./AnimCollection":1,"./AnimDB":2,"./AnimDBParser":3,"./Animation":5,"./Classes":7,"./Playback":8,"./animation_formats":13,"fs":undefined,"path":undefined}],15:[function(require,module,exports){
|
|
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
const jibo_log_1 = require("jibo-log");
|
|
exports.default = new jibo_log_1.Log('Jibo.AnimDB');
|
|
|
|
},{"jibo-log":undefined}],16:[function(require,module,exports){
|
|
"use strict";
|
|
function __export(m) {
|
|
for (var p in m) if (!exports.hasOwnProperty(p)) exports[p] = m[p];
|
|
}
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
__export(require("./AnimDB"));
|
|
__export(require("./Range"));
|
|
__export(require("./AnimDBParser"));
|
|
__export(require("./AnimUtils"));
|
|
__export(require("./AnimCollection"));
|
|
__export(require("./Playback"));
|
|
__export(require("./Animation"));
|
|
__export(require("./Classes"));
|
|
__export(require("./AnimUtils"));
|
|
__export(require("./Utils"));
|
|
const api = require("./api");
|
|
exports.api = api;
|
|
const animation_formats = require("./animation_formats");
|
|
exports.animation_formats = animation_formats;
|
|
|
|
},{"./AnimCollection":1,"./AnimDB":2,"./AnimDBParser":3,"./AnimUtils":4,"./Animation":5,"./Classes":7,"./Playback":8,"./Range":9,"./Utils":10,"./animation_formats":13,"./api":14}],17:[function(require,module,exports){
|
|
"use strict";
|
|
function __export(m) {
|
|
for (var p in m) if (!exports.hasOwnProperty(p)) exports[p] = m[p];
|
|
}
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
__export(require("./main"));
|
|
|
|
},{"./main":16}]},{},[17])(17)
|
|
});
|
|
|
|
//# sourceMappingURL=jibo-anim-db.js.map
|