Commit 5b915d1d authored by rockyl's avatar rockyl

砖块0的情况

parents
Pipeline #109299 failed with stages
in 0 seconds
# Created by .ignore support plugin (hsz.mobi)
### Node template
# Logs
logs
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*
# Runtime data
pids
*.pid
*.seed
*.pid.lock
# Directory for instrumented libs generated by jscoverage/JSCover
lib-cov
# Coverage directory used by tools like istanbul
coverage
# nyc test coverage
.nyc_output
# Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files)
.grunt
# Bower dependency directory (https://bower.io/)
bower_components
# node-waf configuration
.lock-wscript
# Compiled binary addons (https://nodejs.org/api/addons.html)
build/Release
# Dependency directories
node_modules/
jspm_packages/
# TypeScript v1 declaration files
typings/
# Optional npm cache directory
.npm
# Optional eslint cache
.eslintcache
# Optional REPL history
.node_repl_history
# Output of 'npm pack'
*.tgz
# Yarn Integrity file
.yarn-integrity
# dotenv environment variables file
.env
# parcel-bundler cache (https://parceljs.org/)
.cache
# next.js build output
.next
# nuxt.js build output
.nuxt
# vuepress build output
.vuepress/dist
# Serverless directories
.serverless
/.rpt2_cache/
{
"name": "scilla",
"version": "1.0.0",
"main": "./dist/bundle.js",
"types": "./types/index.d.ts",
"license": "MIT",
"scripts": {
"build": "rollup -c"
},
"dependencies": {
"tslib": "^1.9.3"
},
"devDependencies": {
"rollup": "^0.66.6",
"rollup-plugin-commonjs": "^9.2.0",
"rollup-plugin-node-resolve": "^3.4.0",
"rollup-plugin-typescript2": "^0.18.0",
"rollup-plugin-uglify": "^6.0.0",
"tslib": "^1.9.3",
"typescript": "^3.1.6"
}
}
/**
* Created by rockyl on 2018/11/16.
*/
const resolve = require('rollup-plugin-node-resolve');
const commonjs = require('rollup-plugin-commonjs');
const typescript = require('rollup-plugin-typescript2');
const {uglify} = require('rollup-plugin-uglify');
export default {
input: 'src/index.ts',
output: {
file: 'dist/bundle.js',
format: 'umd',
name: 'scilla',
//sourcemap: true,
},
plugins: [
resolve({
browser: true,
}),
typescript({
typescript: require('typescript'),
tslib: require('tslib'),
useTsconfigDeclarationDir: true,
}),
commonjs(),
uglify({}),
]
};
<?xml version="1.0" encoding="UTF-8"?>
<module type="WEB_MODULE" version="4">
<component name="NewModuleRootManager" inherit-compiler-output="true">
<exclude-output />
<content url="file://$MODULE_DIR$" />
<orderEntry type="sourceFolder" forTests="false" />
</component>
</module>
\ No newline at end of file
export type color = string;
export type resource = any;
export type raw = any;
/**
* Created by rockyl on 2018/7/11.
*
* 资源管理
* 加载资源
*/
import {createTexture} from '../core/Texture'
import {FrameAnimation, getFrameAnimation, putFrameAnim} from '../core/FrameAnimation'
import {Sheet} from '../core/Sheet'
import {Texture} from "../core";
import {EngineConfig} from "../engine-config";
let resCache = {};
let resPath = '';
const resLoaderType = {
'.json': loadJson,
'.json5': loadJson5,
'.txt': loadTxt,
'.png': loadTexture,
'.jpg': loadTexture,
'.svg': loadTexture,
'.bimg': loadTextureFromBlob,
'.sht': loadSheet,
'.sht-disperse': loadSheetDisperse,
'.fnt': loadFont,
'.anim': loadAnim,
};
/**
* 设置资源根路径
* @param path
*/
export function setResPath(path) {
resPath = path;
}
/**
* 加载一批资源
* @param items 资源数组: ['aaa.png', {uuid: 'bbb', url: 'alias.png'}]
* @param progress 进度回调,参数为加载百分比
* @return Promise<Array<any>> 资源组
*/
export function loadResItems(items: Array<any | string>, progress?: (percentage: number) => void): Promise<Array<any>> {
let total = items.length;
let count = 0;
return Promise.all(
items.map(item => {
let uuid, url, config, ext;
if (typeof item === 'string') {
url = item;
} else {
url = item.url;
}
if (!url) {
return Promise.resolve();
}
if (typeof item === 'string') {
uuid = getUUIDFromUrl(url);
} else {
uuid = item.uuid || getUUIDFromUrl(url);
ext = item.ext;
config = item.config;
}
let loader = getLoader(ext, url);
return loader(url, uuid, true, config).then((res) => {
count++;
progress && progress(count / total);
return res;
})
})
);
}
/**
* 加载任意网络资源
* @param url url
* @param uuid
* @param type 类型(json|text|arraybuffer|blob)
* @param cache
* @param config
* @param options 请求配置
* @return Promise<any> 资源
*/
export async function loadAny(url, uuid?, cache = true, config?, options = {}, type = 'arraybuffer'): Promise<any> {
let response = await fetch(resolveUrl(url), options);
let result;
switch (type) {
case 'json':
result = response.json();
break;
case 'text':
result = response.text();
break;
case 'arraybuffer':
result = response.arrayBuffer();
break;
case 'blob':
result = response.blob();
break;
}
return await result;
}
/**
* 加载文本资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export function loadTxt(url, uuid?, cache = true, config?): Promise<string> {
let p = loadAny(url, uuid, cache, config, undefined, 'text');
if (cache) {
p.then(data => {
cacheRes(data, url, uuid);
return data;
})
}
return p;
}
/**
* 加载json资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export function loadJson(url, uuid?, cache = true, config?): Promise<any> {
let p = loadAny(url, uuid, cache, config, undefined, 'json');
if (cache) {
p.then(data => {
cacheRes(data, url, uuid);
return data;
})
}
return p;
}
/**
* 加载json5资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export async function loadJson5(url, uuid?, cache = true, config?): Promise<any> {
let txt = await loadTxt(url, uuid);
const jsonData = window['eval'](`(${txt})`);
cacheRes(jsonData, url, uuid);
return jsonData;
}
/**
* 加载图集资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export function loadSheet(url, uuid?, cache = true, config?): Promise<Sheet> {
let pngFile = url.substring(0, url.lastIndexOf('.')) + '.png';
return Promise.all([
loadJson(url, null, false),
loadImage(pngFile, null, false),
]).then(
(result) => {
let data: any = result[0];
let img: any = result[1];
let sheet: Sheet = new Sheet(img, data.frames);
sheet.generateAll();
if (cache) {
cacheRes(sheet, url, uuid);
if (config) {
for (let textureConfig of config.textures) {
const {name, uuid} = textureConfig;
const texture = sheet.getTexture(name);
cacheRes(texture, name, uuid);
}
} else {
let textures = sheet.getAllTextures();
for (let key in textures) {
cacheRes(textures[key], key, key);
}
}
}
return sheet;
}
)
}
/**
* 加载散列的图集
* @param url
* @param uuid
* @param cache
* @param config
*/
export async function loadSheetDisperse(url, uuid?, cache = true, config?): Promise<Sheet> {
for(let {name, uuid} of config.textures){
let subUrl = url.replace('-disperse', '') + '/' + name.replace('_', '/') + '.png';
await loadTexture(subUrl, uuid);
}
return null;
}
/**
* 加载文图字资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export function loadFont(url, uuid?, cache = true, config?): Promise<Sheet> {
return loadSheet(url, null, false).then(
sheet => {
if (cache) {
cacheRes(sheet, url, uuid);
}
return sheet;
}
)
}
function findAnimConfig(animations, name) {
let result;
animations.some((item: any) => {
if (item.name === name) {
result = item;
return true;
}
});
return result;
}
/**
* 加载帧动画资源(多个)
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export function loadAnim(url, uuid?, cache = true, config?): Promise<FrameAnimation[]> {
let pngFile = url.substring(0, url.lastIndexOf('.')) + '.png';
return Promise.all([
loadJson(url, null, false),
loadImage(pngFile, null, false),
]).then(
(result) => {
let data: any = result[0];
let img: any = result[1];
putFrameAnim(img, data);
const animations = [];
for (let name in data.mc) {
const animation = getFrameAnimation(name);
if (cache) {
let uuid = name;
if (config) {
const cfg = findAnimConfig(config.animations, name);
uuid = cfg.uuid;
}
cacheRes(animation, name, uuid);
}
animations.push(animation);
}
return animations;
}
)
}
/**
* 加载图片资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export function loadImage(url, uuid?, cache = true, config?): Promise<any> {
return new Promise((resolve, reject) => {
let img = new Image();
if (EngineConfig.imgCrossOrigin) {
img.setAttribute('crossOrigin', 'anonymous');
}
img.onload = function (e) {
resolve(img);
};
img.onerror = function (e) {
reject(e);
};
img.src = resolveUrl(url);
});
}
/**
* 加载blob图片资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export async function loadImageFromBlob(url, uuid?, cache = true, config?): Promise<any> {
try {
const imgBlob = await loadAny(url, uuid, false, config, undefined, 'blob');
return await blobToImage(imgBlob);
} catch (e) {
console.log(e);
}
}
/**
* 加载纹理资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export async function loadTexture(url, uuid?, cache = true, config?): Promise<Texture> {
const img: any = await loadImage(url, uuid, false);
const texture = createTexture(img);
if (cache) {
cacheRes(texture, url, uuid);
}
return texture;
}
/**
* 加载blob纹理资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export async function loadTextureFromBlob(url, uuid?, cache = true, config?): Promise<Texture> {
const img: any = await loadImageFromBlob(url, uuid, false);
const texture = createTexture(img);
if (cache) {
cacheRes(texture, url, uuid);
}
return texture;
}
/**
* 处理url
* @param url url
* @return string 处理后的url
*/
function resolveUrl(url): string {
if (url.indexOf('//') === 0 || url.indexOf('http:') === 0 || url.indexOf('https:') === 0) {
return url;
}
return resPath + url;
}
/**
* 获取一个加载器
* @param ext
* @param url
*/
function getLoader(ext, url) {
ext = ext || url.substr(url.lastIndexOf('.'));
return resLoaderType[ext] || loadAny;
}
/**
* 根据url推断名称,只是获取短文件名
* @param url
*/
function getUUIDFromUrl(url) {
return url.substring(url.lastIndexOf('/') + 1, url.lastIndexOf('.'))
}
/**
* 缓存资源
* @param res
* @param url
* @param uuid
*/
export function cacheRes(res, url, uuid?) {
uuid = uuid || getUUIDFromUrl(url);
resCache[uuid] = res;
}
/**
* 增加加载器
* @param ext 需加载的文件后缀
* @param loader 加载方法,返回携带最终资源的Promise
*/
export function addLoader(ext, loader) {
resLoaderType[ext] = loader;
}
/**
* 获取资源
* @param uuid
*/
export function getRes(uuid) {
return resCache[uuid];
}
/**
* 销毁资源
* @param uuidOrUuids
*/
export function destroyRes(uuidOrUuids) {
if (Array.isArray(uuidOrUuids)) {
while (uuidOrUuids.length > 0) {
delete resCache[uuidOrUuids.pop()];
}
} else {
delete resCache[uuidOrUuids];
}
}
/**
* 销毁全部资源
*/
export function destroyAllRes() {
for (let key in resCache) {
destroyRes(key);
}
}
/**
* 获取所有uuid值
*/
export function getAllResUuids() {
return Object.keys(resCache);
}
function fileOrBlobToDataURL(obj): Promise<string> {
return new Promise((resolve, reject) => {
let a = new FileReader();
a.readAsDataURL(obj);
a.onload = function (e) {
resolve(e.target['result']);
};
a.onerror = function (e) {
reject(e);
}
});
}
async function blobToImage(blob) {
const dataUrl = await fileOrBlobToDataURL(blob);
return new Promise((resolve, reject) => {
let img = new Image();
if (EngineConfig.imgCrossOrigin) {
img.setAttribute('crossOrigin', 'anonymous');
}
img.onload = function () {
resolve(img);
};
img.onerror = function (e) {
reject(e);
};
img.src = dataUrl;
})
}
/**
* Created by rockyl on 2018/11/5.
*/
import HashObject from "./HashObject";
import {ScillaComponent} from "./ScillaComponent";
import {EngineConfig} from "../engine-config";
/**
* 节点遍历(先序遍历)
* @param target 目标节点
* @param hitChild 遇到子节点回调
* @param level 深度,默认全部遍历
* @param includeSelf 是否包括自身
* @param fullCallback 子节点遍历完后回调
* @param params 其他参数
*/
export function traverse(target: Entity, hitChild: (child: Entity, ...params) => boolean, level = -1, includeSelf = false, fullCallback?: (current: Entity) => void, ...params) {
let interrupt;
if (includeSelf) {
hitChild(target, ...params);
}
if (level !== 0) {
for (let child of target.children) {
if (hitChild(child, ...params)) {
interrupt = true;
continue;
}
traverse(child, hitChild, level - 1, false, fullCallback, ...params);
}
}
!interrupt && fullCallback && fullCallback(target);
}
/**
* 节点遍历(后序遍历且倒序)
* @param target 目标节点
* @param hitChild 遇到子节点回调
* @param level 深度,默认全部遍历
* @param includeSelf 是否包括自身
* @param fullCallback 子节点遍历完后回调
* @param params 其他参数
*/
export function traversePostorder(target: Entity, hitChild: (child: Entity, ...params) => boolean, level = -1, includeSelf = false, fullCallback?: (current: Entity) => void, ...params) {
let interrupt;
if (level !== 0) {
for (let i = target.children.length - 1; i >= 0; i--) {
const child = target.children[i];
if(traversePostorder(child, hitChild, level - 1, false, fullCallback, ...params)){
return true;
}
if (hitChild(child, ...params)) {
return true;
}
}
}
if (includeSelf) {
hitChild(target, ...params);
}
!interrupt && fullCallback && fullCallback(target);
}
/**
* 节点冒泡
* @param target 目标节点
* @param hitParent 遇到父节点回调
* @param includeSelf 是否包括自身
* @param params 其他参数
*/
export function bubbling(target: Entity, hitParent: (parent: Entity, ...params) => boolean, includeSelf = false, ...params) {
if (includeSelf) {
hitParent(target, ...params);
}
let entity = target;
while (entity = entity.parent) {
if (hitParent(entity, ...params)) {
break;
}
}
}
/**
* 实体类
* 实体类只是单纯的父子节点逻辑,不含有其他逻辑
*/
export class Entity extends HashObject {
name: string = 'Entity';
protected _uuid: string;
//是否游离状态
protected _isFree: boolean = true;
//是否有效
protected _enabled: boolean = EngineConfig.entityEnabled;
protected _parent: Entity = null;
protected _children: Entity[] = [];
protected _components: ScillaComponent[] = [];
constructor(name?, uuid?) {
super();
if (name) {
this.name = name;
}
if (uuid) {
this._uuid = uuid;
}
}
get uuid(): string {
return this._uuid;
}
/**
* 是否有效状态
*/
get enabled(): boolean {
return this._enabled;
}
set enabled(value: boolean) {
if (this._enabled !== value) {
this._enabled = value;
traverse(this, function (child: Entity) {
child._invokeEnabledState(value);
return false;
}, -1, true)
}
}
_invokeEnabledState(enabled) {
if (this._enabled && enabled) {
this.onEnable();
} else if (!this._enabled && !enabled) {
this.onDisable();
}
}
get isParentActive() {
return this._parent && this._parent.enabled && !this._parent.isFree;
}
get isActive() {
return this.isParentActive && this._enabled;
}
/**
* 是否游离状态
*/
get isFree() {
return this._isFree;
}
/**
* 使游离
*/
_free() {
this._isFree = true;
let that = this;
traverse(this, function(child: Entity) {
/*if (child.isParentActive) {
that._invokeEnabledState(false);
}*/
child._free();
return false;
}, 1)
}
/**
* 使约束
*/
_restrict() {
this._isFree = false;
let that = this;
traverse(this, function(child: Entity) {
/*if (child.isParentActive) {
that._invokeEnabledState(true);
}*/
child._restrict();
return false;
}, 1)
}
//----- tree
/**
* 获取父节点
*/
get parent() {
return this._parent;
}
/**
* 是否含有子节点
* @param child
*/
containsChild(child: Entity) {
return this.getChildIndex(child) >= 0;
}
/**
* 添加子节点时
* @param child
* @private
*/
protected _onChildAdded(child: Entity) {
child._parent = this;
if (!this._isFree && child._isFree) {
if (child.isParentActive) {
child._invokeEnabledState(true);
}
child._restrict();
}
}
/**
* 子节点被移除时
* @param child
* @private
*/
_onChildRemoved(child: Entity) {
child._parent = null;
if (!this._isFree && !child._isFree) {
if (child.isActive) {
child._invokeEnabledState(false);
}
child._free();
}
}
/**
* 添加子节点,重复添加则会加到最后
* @param child
*/
addChild(child: Entity) {
this.addChildAt(child, this._children.length);
}
/**
* 添加子节点到指定索引,重复添加可作为顺序交换
* @param child
* @param index
*/
addChildAt(child: Entity, index) {
if (child.parent && child.parent !== this) {
child.parent.removeChild(child);
}
const currentIndex = this.getChildIndex(child);
if (index < 0 || currentIndex == index) { //如果索引小于0或没变化
return;
}
index = Math.min(this._children.length, index);
if (currentIndex >= 0 || index < this._children.length) {
if (currentIndex >= 0) {
this._children.splice(currentIndex, 1);
}
this._children.splice(index, 0, child);
} else {
this._children.push(child);
}
this._onChildAdded(child);
}
/**
* 移除节点
* @param child
*/
removeChild(child: Entity) {
const index = this.getChildIndex(child);
if (index >= 0) {
this.removeChildAt(index);
}
}
/**
* 移除指定索引的节点
* @param index
*/
removeChildAt(index) {
const child = this._children[index];
this._onChildRemoved(child);
this._children.splice(index, 1);
}
/**
* 根据节点获取索引
* @param child
*/
getChildIndex(child: Entity) {
return this._children.indexOf(child)
}
/**
* 获取指定索引的节点
* @param index
*/
getChildByIndex(index) {
return this._children[index];
}
/**
* 移除所有子节点
*/
removeChildren() {
while (this._children.length > 0) {
this.removeChildAt(0);
}
}
/**
* 获取所有子节点
*/
get children() {
return this._children;
}
//----- component
/**
* 增加组件
* @param component
*/
addComponent(component: ScillaComponent) {
this.onAddComponent(component);
this._components.push(component);
}
/**
* 在指定索引增加组件,重复添加可作为顺序交换
* @param component
* @param index
*/
addComponentAt(component: ScillaComponent, index) {
const currentIndex = this._components.indexOf(component);
if (currentIndex == index) {
return;
}
if (currentIndex >= 0) {
this._components.splice(currentIndex, 1);
}
this._components.splice(index, 0, component);
this.onAddComponent(component);
}
/**
* 移除组件
* @param component
*/
removeComponent(component: ScillaComponent) {
this.onRemoveComponent(component);
const index = this._components.indexOf(component);
if (index >= 0) {
this._components.splice(index, 1);
}
}
/**
* 移除所有组件
*/
removeAllComponents() {
while (this._components.length > 0) {
this.removeComponent(this._components[0]);
}
}
/**
* 获取指定类的组件列表
* @param clazz
*/
getComponents(clazz: any): any[] {
return this._components.filter((component: any) => {
return typeof clazz === 'string' ? component.constructor.__class__ === clazz : component instanceof clazz;
});
}
/**
* 获取指定类的组件
* @param clazz
*/
getComponent(clazz: any) {
return this.getComponents(clazz)[0];
}
/**
* 获取所有组件
*/
get components() {
return this._components;
}
//----- lifecycle
/**
* 遍历所有组件
* @param func
*/
forEachComponent(func: (component) => boolean) {
for (let component of this._components) {
if (func(component)) {
break;
}
}
}
/**
* 当组件生效时
*/
onEnable() {
this.forEachComponent(comp => {
if (comp.enabled) {
return comp.onAwake();
}
});
}
/**
* 当组件失效时
*/
onDisable() {
this.forEachComponent(comp => {
if (comp.enabled) {
return comp.onSleep();
}
});
}
/**
* 当始终更新时
* @param t
*/
onUpdate(t) {
this.forEachComponent(comp => {
if (comp.enabled) {
return comp.$onUpdate(t);
}
});
}
/**
* 当子节点遍历结束后
*/
afterUpdate() {
this.forEachComponent(comp => {
if(comp.enabled){
return comp.afterUpdate();
}
});
}
/**
* 当交互时
* @param type
* @param event
*/
onInteract(type, event) {
if (!this.isFree && this.enabled) {
let interrupt = false;
this.forEachComponent(comp => {
if (comp.enabled && comp.interactable) {
const r = comp.onInteract(type, event);
if (r) {
interrupt = true;
}
return false;
}
});
return interrupt;
} else {
return false;
}
}
/**
* 当添加组件时
* @param component
*/
onAddComponent(component: ScillaComponent) {
component._setup(this);
if (EngineConfig.awakeComponentWhenAdded) {
this.awakeComponent(component);
}
}
/**
* 唤醒组件
* @param component
*/
awakeComponent(component) {
if (!this._isFree && this._enabled) {
component.onAwake();
}
}
/**
* 当移除组件时
* @param component
*/
onRemoveComponent(component: ScillaComponent) {
if (EngineConfig.sleepComponentWhenRemoved) {
this.sleepComponent(component);
}
component._unSetup();
}
/**
* 睡眠组件
* @param component
*/
sleepComponent(component) {
if (!this._isFree && this._enabled) {
component.onSleep();
}
}
/**
* 向下广播
* 如果某组件调用后返回true,将结束整条链
* @param method 方法名
* @param level 深度,默认全部遍历
* @param params 参数
*/
broadcast(method, level = -1, ...params) {
traverse(this, this.invokeOnEntity, level, true, null, method, ...params)
}
/**
* 向上冒泡
* 如果某组件调用后返回true,将结束整条链
* @param method 方法名
* @param params 参数
*/
bubbling(method, ...params) {
bubbling(this, this.invokeOnEntity, false, method, ...params);
}
/**
* 调用实体上的组件的方法
* @param hitEntity 遇到的实体
* @param method 方法名
* @param params 参数
*/
private invokeOnEntity = (hitEntity: Entity, method, ...params): boolean => {
let hitBreak = false;
hitEntity.forEachComponent(comp => {
const m = comp[method];
if (m) {
const result = m.apply(comp, params);
if (result) {
hitBreak = true;
}
}
return false;
});
if (hitBreak) {
return true;
}
};
}
/**
* Created by rockyl on 2018-11-30.
*/
import {Sheet} from "./Sheet";
const animationMap = {};
const animDataMap = {};
const textureMap = {};
/**
* 获取一个帧动画资源
* @param name
*/
export function getFrameAnimation(name): FrameAnimation {
let animation: FrameAnimation = animationMap[name];
if (!animation) {
animation = animationMap[name] = new FrameAnimationImpl(name);
animation.fillMcData(name);
}
return animation;
}
/**
* 放置帧动画图片和数据
* @param img
* @param data
*/
export function putFrameAnim(img, data) {
const {mc, res} = data;
let sheet: Sheet = new Sheet(img, res);
for (let key in mc) {
const animData = animDataMap[key] = mc[key];
animData.sheet = sheet;
}
}
/**
* 帧动画资源
*/
export interface FrameAnimation {
/**
* 填充帧数据
* @param name
*/
fillMcData(name);
/**
* 获取帧率
*/
readonly fps: number;
/**
* 获取所有帧标签
*/
readonly labels: any[];
/**
* 获取帧数
*/
readonly frameCount: number;
/**
* 根据名字获取帧标签
* @param name
*/
getLabel(name): any;
/**
* 获取帧
* @param frameIndex
*/
getFrame(frameIndex): any;
/**
* 销毁自身
*/
destroy()
}
/**
* 帧动画资源实现
*/
export class FrameAnimationImpl implements FrameAnimation {
private readonly _name: string;
private _animData;
constructor(name) {
this._name = name;
}
get name(): string {
return this._name;
}
fillMcData(name) {
const animData = animDataMap[name];
if (animData) {
this._animData = animData;
} else {
console.warn(`anim data [${name}] is not exist`)
}
}
get fps(): number {
return this._animData.frameRate;
}
get labels(): any[] {
return this._animData.labels;
}
get frameCount(): number {
return this._animData.frames.length;
}
getLabel(name): any {
let result;
for (let label of this._animData.labels) {
if (label.name == name) {
result = label;
break;
}
}
return result;
}
getFrame(frameIndex): any {
const {_animData,} = this;
let texture, frameData;
if (_animData) {
const {frames} = _animData;
frameData = frames[frameIndex];
if (frameData) {
const res = frameData.res;
texture = textureMap[res];
if (!texture) {
texture = textureMap[res] = _animData.sheet.getTexture(res);
}
}
}
return {
texture,
data: frameData,
};
}
destroy() {
this._animData = null;
}
}
/**
* Created by rockyl on 2018/11/5.
*/
let HASH_CODE_INK = 0;
function getHashCode() {
return ++HASH_CODE_INK;
}
/**
* 哈希对象
*/
export default class HashObject {
_hashCode;
constructor() {
this._hashCode = getHashCode();
}
get hashCode() {
return this._hashCode;
}
}
/**
* Created by rockyl on 2018-12-03.
*/
import {Entity} from "./Entity";
import {loadResItems} from "../assets-manager";
export class Scene {
name: string;
root: Entity;
resourceGroups: any = {
preload: [],
delay: [],
};
config: any;
initByConfig(config){
this.config = config;
this.name = config.name;
const resourceGroups = config['resource-groups'];
for(let key in resourceGroups){
this.resourceGroups[key] = resourceGroups[key];
}
}
async loadResGroup(name, progress?){
await loadResItems(this.resourceGroups[name], progress);
}
}
/**
* Created by rockyl on 2018/11/5.
*/
import HashObject from "./HashObject";
import {Entity, } from "./Entity";
import {EngineConfig} from "../engine-config";
const interactiveMap = [
'_dealGlobalTouchBegin',
'_dealGlobalTouchMove',
'_dealGlobalTouchEnd',
];
/**
* 组件基类
*/
export class ScillaComponent extends HashObject {
/**
* 所依附的实体
*/
entity: Entity;
protected delayCallbacks = [];
private _firstUpdate: boolean;
//是否有效
protected _enabled: boolean = EngineConfig.componentEnabled;
/**
* 是否有效状态
*/
get enabled(): boolean {
return this._enabled;
}
set enabled(value: boolean) {
if (this._enabled !== value) {
this._enabled = value;
if (this.entity && this.entity.isActive) {
if (this._enabled) {
this.onEnable();
} else {
this.onDisable();
}
}
}
}
/**
* 装配实体
* @param entity
*/
_setup(entity: Entity) {
this.entity = entity;
this.onCreate();
}
/**
* 卸载实体
*/
_unSetup() {
this.entity = null;
this.onDestroy();
}
/**
* 当组件被创建时
*/
onCreate() {
}
/**
* 当组件被唤醒时
*/
onAwake() {
this._firstUpdate = true;
}
/**
* 当组件生效时
*/
onEnable(){
}
/**
* 当组件失效时
*/
onDisable(){
}
$onUpdate(t) {
this.onUpdate(t);
if(!this._firstUpdate){
this.invokeDelayCallback(t);
}
this._firstUpdate = false;
}
private invokeDelayCallback(t){
const removed = [];
if(this.entity.name.indexOf('progress') >= 0){
console.log();
}
for (let i = 0, li = this.delayCallbacks.length; i < li; i++) {
let {callback, once} = this.delayCallbacks[i];
if(once){
removed.push(i);
}
callback.call(this, t);
}
for(let item of removed){
this.delayCallbacks.splice(item, 1);
}
}
/**
* 当时钟更新时
* @param t 从引擎开始到当前的毫秒数
*/
onUpdate(t) {
}
/**
* 当子节点的时钟更新结束后
*/
afterUpdate() {
}
/**
* 当组件沉睡时
*/
onSleep() {
}
/**
* 当组件被销毁时
*/
onDestroy() {
}
/**
* 当被监听的属性被修改时
* @param value
* @param key
* @param oldValue
*/
protected onModify(value, key, oldValue){
}
private getDelayCallback(callback){
let result;
for(let item of this.delayCallbacks){
if(item.callback == callback){
result = item;
break;
}
}
return result;
}
/**
* 执行延迟回调
* @param callback
* @param once 是否只执行一次
*/
callOnNextTick(callback, once = true) {
const item = this.getDelayCallback(callback);
if (!item) {
this.delayCallbacks.push({callback, once});
}
}
cancelOnNextTick(callback){
const item = this.getDelayCallback(callback);
const index = this.delayCallbacks.indexOf(item);
if(index >= 0){
this.delayCallbacks.splice(index, 1);
}
}
/**
* 当交互时
* @param type
* @param event
*/
onInteract(type, event) {
try {
const hitOn = this[interactiveMap[type]](event);
return hitOn && this['touchInterrupt'];
} catch (e) {
console.warn(e);
}
}
_dealGlobalTouchBegin(e) {
return this.onGlobalTouchBegin(e);
}
_dealGlobalTouchMove(e) {
return this.onGlobalTouchMove(e);
}
_dealGlobalTouchEnd(e) {
return this.onGlobalTouchEnd(e);
}
/**
* 当全局触摸开始
* @param e
*/
onGlobalTouchBegin(e) {
}
/**
* 当全触摸移动
* @param e
*/
onGlobalTouchMove(e) {
}
/**
* 当全触摸结束
* @param e
*/
onGlobalTouchEnd(e) {
}
get transform(){
return this.entity.getComponent('components/base/Transform');
}
/**
* 向下广播
* 如果某组件调用后返回true,将结束整条链
* @param method 方法名
* @param level 深度,默认全部遍历
* @param params 参数
*/
broadcast(method, level = -1, ...params) {
this.entity.broadcast(method, level, ...params);
}
/**
* 向上冒泡
* 如果某组件调用后返回true,将结束整条链
* @param method 方法名
* @param params 参数
*/
bubbling(method, ...params) {
this.entity.bubbling(method, ...params);
}
}
/**
* Created by rockyl on 2018-11-27.
*/
/**
* 单一事件类
* 一对多形式的订阅分发机制
*/
export class ScillaEvent {
private _subscribers: any[];
constructor() {
this._subscribers = [];
}
private findListener(callback) {
const {_subscribers} = this;
let result;
for (let i = 0, li = _subscribers.length; i < li; i++) {
const subscriber = _subscribers[i];
if (subscriber.callback == callback) {
result = {
subscriber,
index: i,
};
break;
}
}
return result;
}
/**
* 添加侦听
* @param callback
* @param thisObj
* @param priority
* @param params
*/
addListener(callback, thisObj?, priority = 0, ...params) {
if (!callback) {
return;
}
const {_subscribers} = this;
const listener = this.findListener(callback);
if (!listener) {
_subscribers.push({
callback,
thisObj,
priority,
params,
});
}
}
/**
* 添加单次侦听
* @param callback
* @param thisObj
* @param priority
* @param params
*/
once(callback, thisObj?, priority = 0, ...params) {
if (!callback) {
return;
}
const {_subscribers} = this;
const listener = this.findListener(callback);
if (!listener) {
_subscribers.push({
callback,
thisObj,
priority,
params,
once: true,
});
}
}
/**
* 移除侦听
* @param callback
*/
removeListener(callback) {
if (!callback) {
return;
}
const {_subscribers} = this;
const listener = this.findListener(callback);
if (listener) {
_subscribers.splice(listener.index, 1);
}
}
/**
* 是否已经侦听
* @param callback
*/
hasListener(callback) {
return !!this.findListener(callback);
}
/**
* 调用派发
* @param paramsNew
*/
invoke(...paramsNew) {
const {_subscribers} = this;
//按优先级降序
_subscribers.sort((a, b) => {
return a.priority - b.priority;
});
for (const subscriber of _subscribers) {
if(subscriber){
const {callback, thisObj, once, params}= subscriber;
const allParams = params.concat(paramsNew);
try {
callback.apply(thisObj, allParams);
}catch (e) {
console.log(e);
}
if(once){
this.removeListener(callback);
}
}
}
}
}
/**
* Created by rockyl on 2018-11-30.
*/
import HashObject from "../core/HashObject";
import {createTexture} from "./Texture";
/**
* 图集
*/
export class Sheet extends HashObject{
/**
* 图集原图
*/
img: any;
/**
* 图集分割配置
*/
frames: any;
private _textureCache: any = {};
constructor(img?, frames?) {
super();
if(img){
this.img = img;
}
if(frames){
this.frames = frames;
}
}
/**
* 生成全部纹理
*/
generateAll() {
for (let key in this.frames) {
this.generateTexture(key);
}
}
/**
* 生成一个纹理
* @param name
* @param force
*/
generateTexture(name, force = false) {
const {img, frames, _textureCache} = this;
if (!force && _textureCache[name]) {
return _textureCache[name];
}
const frame = frames[name];
if (frame) {
return _textureCache[name] = createTexture(img, frame);
}
}
/**
* 是否有这个纹理
* @param name
*/
hasTexture(name) {
return !!frames[name];
}
/**
* 获取纹理
* @param name
*/
getTexture(name) {
let texture = this._textureCache[name];
if (texture) {
return texture;
} else {
return this.generateTexture(name);
}
}
/**
* 获取全部存在的纹理
*/
getAllTextures() {
return this._textureCache;
}
/**
* 销毁自身
*/
destroy() {
this.img = null;
for (let key in this._textureCache) {
this._textureCache[key].destroy();
delete this._textureCache[key];
}
}
}
/**
* Created by rockyl on 2018/7/12.
*/
import Bounds from "../support/Bounds";
import HashObject from "../core/HashObject";
import {createCanvas} from "./context/RenderContext";
/**
* 纹理类
*/
export default class Texture extends HashObject {
img: any;
bounds: Bounds;
_cacheCanvas;
constructor() {
super();
this.bounds = new Bounds();
}
/**
* 设置图集中的坐标和尺寸
* @param frame
*/
setFrame(frame) {
let {x, y, w, h} = frame;
this.bounds.setTo(x, y, w, h);
}
/**
* 设置图片
* @param img
*/
setImg(img) {
this.img = img;
}
/**
* 获取纹理宽度
*/
get width() {
return this.bounds.width;
}
/**
* 获取纹理高度
*/
get height() {
return this.bounds.height;
}
/**
* 产生一个缓存画布
*/
getCacheCanvas() {
const {width, height} = this.bounds;
let canvas = this._cacheCanvas;
if (!canvas) {
canvas = this._cacheCanvas = createCanvas();
}
canvas.width = width;
canvas.height = height;
const context = canvas.getContext('2d');
this.drawToCanvas(context);
return canvas;
}
/**
* 绘制到一个画布上
* @param context
* @param dx
* @param dy
* @param sx
* @param sy
* @param dw
* @param dh
*/
drawToCanvas(context, dx = 0, dy = 0, sx?, sy?, dw?, dh?) {
const {x, y, width, height} = this.bounds;
context.drawImage(this.img, sx || x, sy || y, width, height, dx, dy, dw || width, dh || height);
}
/**
* 销毁自身
*/
destroy() {
this.img = null;
this.bounds = null;
this.destroyCacheCanvas();
}
/**
* 销毁缓存画布
*/
destroyCacheCanvas(){
this._cacheCanvas = null;
}
}
/**
* 快捷创建纹理
* @param img
* @param frame
*/
export function createTexture(img, frame?): Texture {
const texture = new Texture();
texture.setImg(img);
texture.setFrame(frame || {x: 0, y: 0, w: img.width, h: img.height});
return texture;
}
/**
* Created by rockyl on 2018/11/7.
*
* 交互上下文
*/
let _canvas;
let _touchHandler;
let _scaleX, _scaleY, _rotation;
const ua = navigator.userAgent.toLowerCase();
const isMobile = (ua.indexOf('mobile') !== -1 || ua.indexOf('android') !== -1);
/**
* 装配上下文
* @param options
*/
export function setupContext(options:any = {}) {
const {canvas, touchHandler} = options;
_touchHandler = touchHandler;
_canvas = canvas;
addListeners();
}
/**
* 更新缩放模式
* @param scaleX
* @param scaleY
* @param rotation
*/
export function updateScaleMode(scaleX, scaleY, rotation) {
_scaleX = scaleX;
_scaleY = scaleY;
_rotation = rotation;
}
/**
* 适配鼠标事件
*/
function addListeners() {
if (window.navigator.msPointerEnabled) {
_canvas.addEventListener("MSPointerDown", (event) => {
event.identifier = event.pointerId;
onTouchBegin(event);
prevent(event);
}, false);
_canvas.addEventListener("MSPointerMove", (event) => {
event.identifier = event.pointerId;
onTouchMove(event);
prevent(event);
}, false);
_canvas.addEventListener("MSPointerUp", (event) => {
event.identifier = event.pointerId;
onTouchEnd(event);
prevent(event);
}, false);
}
else {
if (!isMobile) {
addMouseListener();
}
addTouchListener();
}
}
/**
* 阻断页面拖动
* @param event
*/
function prevent(event) {
event.stopPropagation();
if (event["isScroll"] != true && !_canvas['userTyping']) {
event.preventDefault();
}
}
/**
* 增加鼠标事件
*/
function addMouseListener() {
_canvas.addEventListener("mousedown", onTouchBegin);
_canvas.addEventListener("mousemove", onMouseMove);
_canvas.addEventListener("mouseup", onTouchEnd);
}
/**
* 增加触摸事件
*/
function addTouchListener() {
_canvas.addEventListener("touchstart", (event) => {
let l = event.changedTouches.length;
for (let i = 0; i < l; i++) {
onTouchBegin(event.changedTouches[i]);
}
prevent(event);
}, false);
_canvas.addEventListener("touchmove", (event) => {
let l = event.changedTouches.length;
for (let i = 0; i < l; i++) {
onTouchMove(event.changedTouches[i]);
}
prevent(event);
}, false);
_canvas.addEventListener("touchend", (event) => {
let l = event.changedTouches.length;
for (let i = 0; i < l; i++) {
onTouchEnd(event.changedTouches[i]);
}
prevent(event);
}, false);
_canvas.addEventListener("touchcancel", (event) => {
let l = event.changedTouches.length;
for (let i = 0; i < l; i++) {
onTouchEnd(event.changedTouches[i]);
}
prevent(event);
}, false);
}
function onTouchBegin(event) {
let location = getLocation(event);
_touchHandler.onTouchBegin(location);
}
function onMouseMove(event) {
if (event.buttons === 0) {
onTouchEnd(event);
} else {
onTouchMove(event);
}
}
function onTouchMove(event) {
let location = getLocation(event);
_touchHandler.onTouchMove(location);
}
function onTouchEnd(event) {
let location = getLocation(event);
_touchHandler.onTouchEnd(location);
}
/**
* 获取当前点
*/
function getLocation(event) {
let doc = document.documentElement;
let box = _canvas.getBoundingClientRect();
let left = box.left + window.pageXOffset - doc.clientLeft;
let top = box.top + window.pageYOffset - doc.clientTop;
let x = event.pageX - left, newX = x;
let y = event.pageY - top, newY = y;
if (_rotation === 90) {
newX = y;
newY = box.width - x;
}
else if (_rotation === -90) {
newX = box.height - y;
newY = x;
}
newX = newX / _scaleX;
newY = newY / _scaleY;
return {
x: Math.round(newX),
y: Math.round(newY),
identifier: event.identifier || 0,
};
}
\ No newline at end of file
/**
* Created by rockyl on 2018/11/5.
*
* 渲染上下文
*/
import {updateScaleMode} from "./InteractContext";
import Bounds from "../../support/Bounds";
let _canvas, context, width, height;
let scaleX, scaleY, rotation = 0;
let _designWidth, _designHeight, _scaleMode, _modifyCanvasSize;
let shortcutCanvas;
/**
* 缩放模式
*
* SHOW_ALL: 全可见
* FIXED_WIDTH: 宽度固定
* FIXED_HEIGHT: 高度固定
*/
export const ScaleMode = {
SHOW_ALL: 'showAll',
FIXED_WIDTH: 'fixedWidth',
FIXED_HEIGHT: 'fixedHeight',
};
/**
* 装配上下文
* @param options
*/
export function setupContext(options: any = {}) {
const {canvas, designWidth, designHeight, scaleMode = ScaleMode.SHOW_ALL, modifyCanvasSize = false} = options;
_designWidth = designWidth;
_designHeight = designHeight;
_scaleMode = scaleMode;
_modifyCanvasSize = modifyCanvasSize;
_canvas = canvas;
context = canvas.getContext('2d');
updateScaleModeSelf();
}
/**
* 清空渲染上下文
*/
export function clear() {
context.setTransform(1, 0, 0, 1, 0, 0);
context.clearRect(0, 0, width, height);
}
/**
* 获取渲染上下文
*/
export function getContext() {
return context;
}
/**
* 获取舞台尺寸
*/
export function getStageSize() {
return {
width,
height,
}
}
/**
* 获取舞台缩放
*/
export function getStageScale() {
return {
x: scaleX,
y: scaleY,
}
}
/**
* 获取舞台中心
*/
export function getStageCenter() {
return {
x: width / 2,
y: height / 2,
}
}
/**
* 创建canvas
*/
export function createCanvas() {
return document.createElement('canvas');
}
interface ShortcutParams {
imgType: string;
zoomToDom?: boolean;
quality?: number;
bounds?: Bounds;
}
/**
* 截图
* @param type 目标格式 0:Image, 1:DataURL
* @param params
*/
export async function shortcut(type: number = 0, params: ShortcutParams) {
let targetImg;
if(params.bounds || params.zoomToDom){
const dataUrl = _canvas.toDataURL('image/png');
const img = await dataUrlToImage(dataUrl);
targetImg = await shortcutWithSize(img, type, params.imgType, params.quality, params.bounds, params.zoomToDom ? scaleX : 1);
}else{
targetImg = _canvas.toDataURL(params.imgType, params.quality);
}
return targetImg;
}
function dataUrlToImage(dataUrl) {
return new Promise((resolve, reject) => {
const image = new Image();
image.onload = function () {
resolve(image);
};
image.onerror = function (e) {
reject(e);
};
image.src = dataUrl;
})
}
async function shortcutWithSize(img, type, imgType, quality?, bounds?:Bounds, scale = 1) {
if (!shortcutCanvas) {
shortcutCanvas = createCanvas();
}
const sx = bounds ? bounds.x || 0 : 0;
const sy = bounds ? bounds.y || 0 : 0;
const sw = bounds ? (bounds.width ? Math.min(bounds.width, width) : width) : width;
const sh = bounds ? (bounds.height ? Math.min(bounds.height, height) : height) : height;
const dw = sw * scale;
const dh = sh * scale;
shortcutCanvas.width = dw;
shortcutCanvas.height = dh;
const context = shortcutCanvas.getContext('2d');
context.drawImage(img, sx, sy, sw, sh, 0, 0, dw, dh);
const dataUrl = shortcutCanvas.toDataURL('image/' + imgType, quality);
switch (type) {
case 0:
return await dataUrlToImage(dataUrl);
case 1:
return dataUrl;
}
}
/**
* 更新缩放模式
*/
function updateScaleModeSelf() {
let parent = _canvas.parentElement;
let containerWidth = parent.clientWidth;
let containerHeight = parent.clientHeight;
const designWidth = _designWidth || containerWidth;
const designHeight = _designHeight || containerHeight;
scaleX = containerWidth / designWidth;
scaleY = containerHeight / designHeight;
switch (_scaleMode) {
case ScaleMode.SHOW_ALL:
width = designWidth;
height = designHeight;
break;
case ScaleMode.FIXED_WIDTH:
width = designWidth;
if(_modifyCanvasSize){
height = designHeight;
}else{
height = containerHeight / scaleX;
}
scaleY = scaleX;
break;
case ScaleMode.FIXED_HEIGHT:
if(_modifyCanvasSize){
width = designWidth;
}else{
width = containerWidth / scaleY;
}
height = designHeight;
scaleX = scaleY;
break;
}
updateScaleMode(scaleX, scaleY, rotation);
let styleWidth = _modifyCanvasSize ? designWidth * scaleX : containerWidth;
let styleHeight = _modifyCanvasSize ? designHeight * scaleY : containerHeight;
_canvas.width = width;
_canvas.height = height;
_canvas.style.display = 'block';
_canvas.style.width = styleWidth + 'px';
_canvas.style.height = styleHeight + 'px';
}
/**
* Created by rockyl on 2018/11/5.
*/
export {ScillaComponent} from "./ScillaComponent";
export {Entity} from './Entity'
export {Scene} from './Scene'
export {ScillaEvent} from './ScillaEvent'
export {getContext, createCanvas, getStageSize, getStageScale, getStageCenter, shortcut, ScaleMode} from './context/RenderContext';
export * from './manager'
export {default as Texture, createTexture} from './Texture'
export * from './Sheet'
export * from './FrameAnimation'
\ No newline at end of file
/**
* Created by rockyl on 2018/11/23.
*/
import {Entity, traverse, traversePostorder} from "./Entity";
import {injectProp} from "../tools/utils";
import {setupContext as setupInteractContext} from "./context/InteractContext";
import {clear, ScaleMode, setupContext as setupRenderContext} from "./context/RenderContext";
import './requestAnimationFrame';
/**
* 默认配置
*/
let options: any = {
fps: 60,
designWidth: 750,
designHeight: 1334,
scaleMode: ScaleMode.FIXED_WIDTH,
};
let root: Entity;
let _flush = 0, _currentFlush = 0;
let tsStart, tsLast;
let lastFPS = 0;
/**
* 装配引擎
* @param _options
*/
export function setup(_options?) {
injectProp(options, _options);
const {canvas, designWidth, designHeight, scaleMode, modifyCanvasSize} = options;
let canvasElement = typeof canvas == 'object' ? canvas : document.getElementById(canvas);
setupInteractContext({
canvas: canvasElement,
touchHandler: {
onTouchBegin,
onTouchMove,
onTouchEnd,
}
});
setupRenderContext({
canvas: canvasElement,
designWidth,
designHeight,
scaleMode,
modifyCanvasSize,
});
root = new Entity('root');
root._restrict();
}
/**
* 开始引擎
*/
export function start() {
root.enabled = true;
tsStart = Date.now();
startTick();
}
/**
* 暂停引擎
*/
export function pause() {
root.enabled = false;
stopTick();
}
/**
* 获取根Entity
*/
export function getRoot(): Entity {
return root;
}
/**
* 获取当前帧率
*/
export function getFPS(){
return lastFPS;
}
/**
* 开始时钟
*/
function startTick() {
_flush = 60 / options.fps - 1 >> 0;
if (_flush < 0) {
_flush = 0;
}
requestAnimationFrame(flush);
}
/**
* 停止时钟
*/
function stopTick() {
}
let tsLast2;
/**
* 时钟触发
*/
function flush(tsNow): void {
if (_flush == 0) {
onFrameTick(tsNow);
} else {
if (_currentFlush == 0) {
onFrameTick(tsNow);
_currentFlush = _flush;
} else {
_currentFlush--;
}
}
requestAnimationFrame(flush);
}
function onFrameTick(tsNow){
clear();
const tsNow2 = Date.now();
lastFPS = Math.floor(1000 / (tsNow - tsLast));
tsLast = tsNow;
tsLast2 = tsNow2;
const ts = tsNow - tsStart;
traverse(root, function (child) {
if(!child.isFree && child.enabled){
child.onUpdate(ts);
}else{
return true;
}
}, -1, true, function(current){
current.afterUpdate();
});
//const tsPass = Date.now() - tsNow;
}
/**
* 代理出来的onTouchBegin方法
* @param event
*/
function onTouchBegin(event) {
traversePostorder(root, function (child) {
return child.onInteract(0, event);
})
}
/**
* 代理出来的onTouchMove方法
* @param event
*/
function onTouchMove(event) {
traversePostorder(root, function (child) {
return child.onInteract(1, event);
})
}
/**
* 代理出来的onTouchEnd方法
* @param event
*/
function onTouchEnd(event) {
traversePostorder(root, function (child) {
return child.onInteract(2, event);
})
}
\ No newline at end of file
/**
* Created by Administrator on 2017/7/12.
*/
var lastTime = 0;
var vendors = ['webkit', 'moz'];
for(var x = 0; x < vendors.length && !window.requestAnimationFrame; ++x) {
window.requestAnimationFrame = window[vendors[x] + 'RequestAnimationFrame'];
window.cancelAnimationFrame = window[vendors[x] + 'CancelAnimationFrame'] || // name has changed in Webkit
window[vendors[x] + 'CancelRequestAnimationFrame'];
}
if (!window.requestAnimationFrame) {
window.requestAnimationFrame = function(callback) {
var currTime = new Date().getTime();
var timeToCall = Math.max(0, 16.7 - (currTime - lastTime));
var id = window.setTimeout(function() {
callback(currTime + timeToCall);
}, timeToCall);
lastTime = currTime + timeToCall;
return id;
};
}
if (!window.cancelAnimationFrame) {
window.cancelAnimationFrame = function(id) {
clearTimeout(id);
};
}
/**
* Created by rockyl on 2018-12-04.
*/
import {destroyScene, setupScene, } from "./interpreter";
import {addLoader, cacheRes, destroyRes, getAllResUuids, loadJson5} from "../assets-manager";
import {getRoot, pause, Scene, start} from "../core";
export * from './interpreter'
let currentScene: Scene;
let resUUIDs;
/**
* 启动场景
* @param name
* @param progress
*/
export async function launchScene(name, progress?) {
const scene = await loadScene(`scenes/${name}.scene`, 'scene_' + name);
resUUIDs = getAllResUuids();
await scene.loadResGroup('preload', progress);
if(currentScene){
unmountScene(currentScene);
}
currentScene = scene;
mountScene(scene);
scene.loadResGroup('delay', progress);
}
/**
* 装载场景
* @param scene
*/
export function mountScene(scene){
pause();
setupScene(scene, getRoot());
start();
}
/**
* 卸载场景
* @param scene
*/
export function unmountScene(scene){
pause();
destroyScene(scene);
destroyRes(resUUIDs);
}
/**
* 加载场景资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
async function loadScene(url, uuid?, cache = false, config?) {
const sceneConfig = await loadJson5(url);
const scene = new Scene();
scene.initByConfig(sceneConfig);
return scene;
}
/**
* 加载预制资源
* @param url url
* @param uuid 唯一名
* @param cache 是否缓存
* @param config
* @return Promise<any> 资源
*/
export async function loadPrefab(url, uuid?, cache = true, config?) {
let data = await loadJson5(url, uuid, false);
cacheRes(data, url, uuid);
return data;
}
addLoader('.pfb', loadPrefab);
/**
* Created by rockyl on 2018-12-03.
*
* 配置文件解释器
*/
import {Entity, Scene, ScillaEvent} from "../core";
import {getRes} from "../assets-manager";
let entityCache = {};
let entityCacheConfig;
const defMap = {};
let prefabID: number = 0;
export function registerDef(name, def) {
defMap[name] = def;
def.__class__ = name;
}
function getEntityCacheConfig(config) {
return config['entity-cache'] ? config['entity-cache'].concat() : [];
}
/**
* 装配场景
* @param scene
* @param root
*/
export function setupScene(scene: Scene, root: Entity): Scene {
scene.root = root;
const config = scene.config;
entityCacheConfig = getEntityCacheConfig(config);
instantiateConfig(config.root, root);
entityCache = {};
return scene;
}
/**
* 销毁场景
* @param scene
*/
export function destroyScene(scene: Scene) {
const root = scene.root;
root.removeAllComponents();
root.removeChildren();
}
/**
* 装配预制体
* @param config
*/
export function instantiate(config: any): Entity {
let pid = ++prefabID;
entityCacheConfig = getEntityCacheConfig(config);
for (let i = 0, li = entityCacheConfig.length; i < li; i++) {
entityCacheConfig[i] = pid + '_' + entityCacheConfig[i];
}
let rootConfig = config.root;
const entity = setupEntity(rootConfig, null, pid);
setupComponent(rootConfig, entity, true);
injectComponent(rootConfig, entity, true, pid);
entityCache = {};
return entity.children[0];
}
/**
* 装配树节点
* @param config
* @param root
*/
function instantiateConfig(config, root?: Entity): Entity {
const entity = setupEntity(config, root);
setupComponent(config, entity, true);
injectComponent(config, entity, true);
return entity;
}
/**
* 装配实体
* @param config
* @param root
* @param pid
*/
function setupEntity(config, root?: Entity, pid?): Entity {
let entity: Entity = null;
if (config) {
let {name, uuid, children} = config;
if (pid !== undefined && uuid !== undefined) {
uuid = pid + '_' + uuid;
}
entity = root || new Entity(name, uuid);
if (entityCacheConfig.indexOf(uuid) >= 0) {
entityCache[uuid] = entity;
}
if (children) {
for (let i = 0, li = children.length; i < li; i++) {
let child = children[i];
const childEntity = setupEntity(child, null, pid);
entity.addChild(childEntity);
}
}
if (!root) {
entity.enabled = !config.disabled;
}
}
return entity;
}
/**
* 装配组件
* @param config
* @param root
* @param includeSelf
*/
function setupComponent(config, root: Entity, includeSelf = false) {
if (includeSelf) {
instantiateComponents(root, config);
}
if (config && config.children) {
for (let i = 0, li = root.children.length; i < li; i++) {
const child = config.children[i];
const entity = root.children[i];
instantiateComponents(entity, child);
setupComponent(child, entity);
}
}
}
/**
* 注入组件参数
* @param config
* @param root
* @param includeSelf
* @param pid
*/
function injectComponent(config, root: Entity, includeSelf = false, pid?) {
if (includeSelf) {
injectComponents(root, config, pid);
}
if (config && config.children) {
for (let i = 0, li = root.children.length; i < li; i++) {
const child = config.children[i];
const entity = root.children[i];
injectComponents(entity, child, pid);
injectComponent(child, entity, false, pid);
}
}
}
/**
* 实例化组件列表
* @param entity
* @param config
*/
function instantiateComponents(entity: Entity, config: any) {
if (config.components) {
for (const component of config.components) {
instantiateComponent(entity, component);
}
}
}
/**
* 注入组件列表参数
* @param entity
* @param config
* @param pid
*/
function injectComponents(entity: Entity, config: any, pid?) {
if (config.components) {
const components = entity.components;
for (let i = 0, li = config.components.length; i < li; i++) {
const component = config.components[i];
const {properties} = component;
if (properties) {
injectProperties(components[i], properties, pid);
}
}
}
}
/**
* 实例化组件
* @param entity
* @param config
*/
function instantiateComponent(entity: Entity, config: any) {
const {script, properties} = config;
let def = getDefByName(script);
if (!def) {
return;
}
const instance: any = new def();
instance.enabled = !config.disabled;
entity.addComponent(instance);
}
/**
* 根据名称获取定义
* @param name
*/
function getDefByName(name): any {
let def;
/*if (name.indexOf('/') >= 0) {//addition
name = name.substr(name.lastIndexOf('/') + 1);
}*/
def = defMap[name];
if (!def) {
console.warn('missing def:', name);
return;
}
return def;
}
const skipKeys = ['_type_', '_constructor_'];
/**
* 属性注入
* @param node
* @param propertiesConfig
* @param pid
*/
function injectProperties(node, propertiesConfig, pid?) {
if (!node) {
console.warn('node is null.');
return;
}
for (const key in propertiesConfig) {
if (skipKeys.indexOf(key) >= 0) {
continue;
}
const propertyOfConfig: any = propertiesConfig[key];
let propertyOfInstance = node[key];
if (typeof propertyOfConfig === 'object') {
if (propertyOfInstance instanceof ScillaEvent) {
injectEvent(propertyOfInstance, propertyOfConfig, pid);
} else if (propertyOfConfig._type_ === 'raw') {
node[key] = propertyOfInstance = propertyOfConfig.data;
} else {
if (Array.isArray(propertyOfConfig) && !propertyOfInstance) {
node[key] = propertyOfInstance = []
}
node[key] = injectObject(propertyOfInstance, propertyOfConfig, pid);
}
} else {
injectBaseType(node, key, propertyOfConfig, pid);
}
}
}
function injectObject(propertyOfInstance, propertyOfConfig, pid?) {
if (propertyOfInstance === undefined) {
if (propertyOfConfig._type_) {
let def = getDefByName(propertyOfConfig._type_);
if (def) {
let constructorArgs = propertyOfConfig._constructor_;
if (constructorArgs && constructorArgs.length > 0) {
propertyOfInstance = def.constructor.apply(null, constructorArgs);
} else {
propertyOfInstance = new def();
}
}
}
}
if (propertyOfInstance) {
injectProperties(propertyOfInstance, propertyOfConfig, pid);
}
return propertyOfInstance;
}
function injectBaseType(node, key, propertyOfConfig, pid?) {
let propertyValue;
if (typeof propertyOfConfig === 'string') {
propertyValue = getLink(propertyOfConfig, pid);
} else {
propertyValue = propertyOfConfig;
}
node[key] = propertyValue;
}
function injectEvent(event: ScillaEvent, config, pid?) {
for (const {entity: entityName, component: componentIndex, method: methodName, param} of config) {
if (entityName && componentIndex >= 0 && methodName) {
const entity = getLink(entityName, pid);
const component = entity.components[componentIndex];
const method = component[methodName];
if (method) {
if (param == undefined) {
event.addListener(method, component, 0);
} else {
event.addListener(method, component, 0, param);
}
}
}
}
}
function getLink(str: string, pid?) {
let result;
if (str.indexOf('res|') == 0) { //res uuid
const uuid = str.substr(4);
result = getRes(uuid);
} else if (str.indexOf('entity|') == 0) { //entity uuid
const uuid = transPrefabUUID(str.substr(7), pid);
result = entityCache[uuid];
} else {
result = str;
}
return result;
}
function transPrefabUUID(uuid, pid) {
return pid ? pid + '_' + uuid : uuid;
}
/**
* Created by rockyl on 2018-12-05.
*/
import {injectProp} from "./tools/utils";
export const EngineConfig = {
lineHeightRatio: 1.2,
entityEnabled: true,
componentEnabled: true,
awakeComponentWhenAdded: true,
sleepComponentWhenRemoved: true,
drawRenderRect: false,
imgCrossOrigin: true,
};
export function modifyEngineConfig(_options) {
injectProp(EngineConfig, _options);
}
/**
* 投影或者发光滤镜
* @class ShadowFilter
* @public
* @since 1.0.0
*/
export class ShadowFilter {
/**
* 颜色值
* @property color
* @public
* @readonly
* @since 1.0.0
* @default black
* @type {string}
*/
public color: string = "black";
/**
* x方向投影距离
* @property offsetX
* @public
* @readonly
* @since 1.0.0
* @default 2
* @type {number}
*/
public offsetX: number = 2;
/**
* y方向投影距离
* @property offsetY
* @public
* @readonly
* @since 1.0.0
* @default 2
* @type {number}
*/
public offsetY: number = 2;
/**
* 模糊值
* @property blur
* @public
* @readonly
* @since 1.0.0
* @default 2
* @type {number}
*/
public blur: number = 2;
/**
* 滤镜类型 只读
* @property color
* @public
* @readonly
* @since 1.0.0
* @default Shadow
* @type {string}
*/
public type: string = "Shadow";
/**
* @method ShadowFilter
* @param {string} color
* @param {number} offsetX
* @param {number} offsetY
* @param {number} blur
*/
public constructor(color: string = "black", offsetX: number = 2, offsetY: number = 2, blur: number = 2) {
let s = this;
s.offsetX = offsetX;
s.offsetY = offsetY;
s.blur = blur;
s.color = color;
}
/**
*获取滤镜的字符串表现形式以方便比较两个滤镜是否效果一样
* @method toString
* @public
* @since 1.0.0
* @return {string}
*/
public toString(): string {
let s = this;
return s.type + s.offsetX + s.offsetY + s.blur + s.color;
}
/**
* 绘画滤镜效果
* @method drawFilter
* @public
* @since 1.0.0
* @param {ImageData} imageData
*/
public drawFilter(imageData: ImageData = null) {
//什么也不要做
}
public destroy(): void {
}
}
/**
* 普通变色滤镜
* @class ColorFilter
* @public
* @since 1.0.0
*/
export class ColorFilter {
/**
* @property redMultiplier
* @public
* @since 1.0.0
* @readonly
* @type {number}
*/
public redMultiplier: number = 0;
/**
* @property redOffset
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public redOffset: number = 0;
/**
* @property greenMultiplier
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public greenMultiplier: number = 0;
/**
* @property greenOffset
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public greenOffset: number = 0;
/**
* @property blueMultiplier
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public blueMultiplier: number = 0;
/**
* @property blueOffset
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public blueOffset: number = 0;
/**
* @property alphaMultiplier
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public alphaMultiplier: number = 0;
/**
* @property alphaOffset
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public alphaOffset: number = 0;
/**
* @property type
* @public
* @readonly
* @since 1.0.0
* @type {string}
*/
public type: string = "Color";
/**
* @method ColorFilter
* @param {number} colorArrays 颜色值数据
*/
public constructor(colorArrays: number[]) {
let s = this;
s.redMultiplier = colorArrays[0];
s.greenMultiplier = colorArrays[1];
s.blueMultiplier = colorArrays[2];
s.alphaMultiplier = colorArrays[3];
s.redOffset = colorArrays[4];
s.greenOffset = colorArrays[5];
s.blueOffset = colorArrays[6];
s.alphaOffset = colorArrays[7];
}
/**
* 绘画滤镜效果
* @method drawFilter
* @param {ImageData} imageData
* @since 1.0.0
* @public
*/
public drawFilter(imageData: ImageData = null) {
if (!imageData) return;
let s = this;
let data = imageData.data;
let l = data.length;
for (let i = 0; i < l; i += 4) {
data[i] = data[i] * s.redMultiplier + s.redOffset;
data[i + 1] = data[i + 1] * s.greenMultiplier + s.greenOffset;
data[i + 2] = data[i + 2] * s.blueMultiplier + s.blueOffset;
data[i + 3] = data[i + 3] * s.alphaMultiplier + s.alphaOffset;
}
}
/**
*获取滤镜的字符串表现形式以方便比较两个滤镜是否效果一样
* @method toString
* @public
* @since 1.0.0
* @return {string}
*/
public toString(): string {
let s = this;
return s.type + s.redMultiplier + s.greenMultiplier + s.blueMultiplier + s.alphaMultiplier + s.redOffset + s.greenOffset + s.blueOffset + s.alphaOffset;
}
public destroy(): void {
}
}
/**
* 矩阵变色滤镜
* @class ColorMatrixFilter
* @public
* @since 1.0.0
*/
export class ColorMatrixFilter {
/**
* @property brightness
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public brightness: number = 0;
/**
* @property contrast
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public contrast: number = 0;
/**
* @property saturation
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public saturation: number = 0;
/**
* @property hue
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public hue: number = 0;
/**
* 滤镜类型 只读
* @property type
* @public
* @readonly
* @since 1.0.0
* @type {string}
*/
public type: string = "ColorMatrix";
private colorMatrix: any;
/**
* @method ColorMatrixFilter
* @param {number} brightness
* @param {number} contrast
* @param {number} saturation
* @param {number} hue
* @public
* @since 1.0.0
*/
public constructor(brightness: number, contrast: number, saturation: number, hue: number) {
let s = this;
s.brightness = brightness;
s.contrast = contrast;
s.saturation = saturation;
s.hue = hue;
s.colorMatrix = [
1, 0, 0, 0, 0,
0, 1, 0, 0, 0,
0, 0, 1, 0, 0,
0, 0, 0, 1, 0,
0, 0, 0, 0, 1
];
//brightness
brightness = s._cleanValue(brightness, 255);
if (brightness != 0) {
s._multiplyMatrix([
1, 0, 0, 0, brightness,
0, 1, 0, 0, brightness,
0, 0, 1, 0, brightness,
0, 0, 0, 1, 0,
0, 0, 0, 0, 1
]);
}
//contrast
contrast = this._cleanValue(contrast, 100);
let x: number;
if (contrast != 0) {
if (contrast < 0) {
x = 127 + contrast / 100 * 127;
} else {
x = contrast % 1;
if (x == 0) {
x = ColorMatrixFilter.DELTA_INDEX[contrast];
} else {
x = ColorMatrixFilter.DELTA_INDEX[(contrast << 0)] * (1 - x) + ColorMatrixFilter.DELTA_INDEX[(contrast << 0) + 1] * x; // use linear interpolation for more granularity.
}
x = x * 127 + 127;
}
s._multiplyMatrix([
x / 127, 0, 0, 0, 0.5 * (127 - x),
0, x / 127, 0, 0, 0.5 * (127 - x),
0, 0, x / 127, 0, 0.5 * (127 - x),
0, 0, 0, 1, 0,
0, 0, 0, 0, 1
]);
}
//saturation
saturation = this._cleanValue(saturation, 100);
if (saturation != 0) {
x = 1 + ((saturation > 0) ? 3 * saturation / 100 : saturation / 100);
let lumR = 0.3086;
let lumG = 0.6094;
let lumB = 0.0820;
s._multiplyMatrix([
lumR * (1 - x) + x, lumG * (1 - x), lumB * (1 - x), 0, 0,
lumR * (1 - x), lumG * (1 - x) + x, lumB * (1 - x), 0, 0,
lumR * (1 - x), lumG * (1 - x), lumB * (1 - x) + x, 0, 0,
0, 0, 0, 1, 0,
0, 0, 0, 0, 1
]);
}
//hue
hue = this._cleanValue(hue, 180) / 180 * Math.PI;
if (hue != 0) {
let cosVal = Math.cos(hue);
let sinVal = Math.sin(hue);
let lumR = 0.213;
let lumG = 0.715;
let lumB = 0.072;
s._multiplyMatrix([
lumR + cosVal * (1 - lumR) + sinVal * (-lumR), lumG + cosVal * (-lumG) + sinVal * (-lumG), lumB + cosVal * (-lumB) + sinVal * (1 - lumB), 0, 0,
lumR + cosVal * (-lumR) + sinVal * (0.143), lumG + cosVal * (1 - lumG) + sinVal * (0.140), lumB + cosVal * (-lumB) + sinVal * (-0.283), 0, 0,
lumR + cosVal * (-lumR) + sinVal * (-(1 - lumR)), lumG + cosVal * (-lumG) + sinVal * (lumG), lumB + cosVal * (1 - lumB) + sinVal * (lumB), 0, 0,
0, 0, 0, 1, 0,
0, 0, 0, 0, 1
]);
}
}
/**
* 绘画滤镜效果
* @method drawFilter
* @param {ImageData} imageData
* @since 1.0.0
* @public
*/
public drawFilter(imageData: ImageData = null): void {
if (!imageData) return;
let data: any = imageData.data;
let l = data.length;
let r: number, g: number, b: number, a: number;
let mtx = this.colorMatrix;
let m0 = mtx[0], m1 = mtx[1], m2 = mtx[2], m3 = mtx[3], m4 = mtx[4];
let m5 = mtx[5], m6 = mtx[6], m7 = mtx[7], m8 = mtx[8], m9 = mtx[9];
let m10 = mtx[10], m11 = mtx[11], m12 = mtx[12], m13 = mtx[13], m14 = mtx[14];
let m15 = mtx[15], m16 = mtx[16], m17 = mtx[17], m18 = mtx[18], m19 = mtx[19];
for (let i = 0; i < l; i += 4) {
r = data[i];
g = data[i + 1];
b = data[i + 2];
a = data[i + 3];
data[i] = r * m0 + g * m1 + b * m2 + a * m3 + m4; //red
data[i + 1] = r * m5 + g * m6 + b * m7 + a * m8 + m9; //green
data[i + 2] = r * m10 + g * m11 + b * m12 + a * m13 + m14; //blue
data[i + 3] = r * m15 + g * m16 + b * m17 + a * m18 + m19; //alpha
}
}
public static DELTA_INDEX = [
0, 0.01, 0.02, 0.04, 0.05, 0.06, 0.07, 0.08, 0.1, 0.11,
0.12, 0.14, 0.15, 0.16, 0.17, 0.18, 0.20, 0.21, 0.22, 0.24,
0.25, 0.27, 0.28, 0.30, 0.32, 0.34, 0.36, 0.38, 0.40, 0.42,
0.44, 0.46, 0.48, 0.5, 0.53, 0.56, 0.59, 0.62, 0.65, 0.68,
0.71, 0.74, 0.77, 0.80, 0.83, 0.86, 0.89, 0.92, 0.95, 0.98,
1.0, 1.06, 1.12, 1.18, 1.24, 1.30, 1.36, 1.42, 1.48, 1.54,
1.60, 1.66, 1.72, 1.78, 1.84, 1.90, 1.96, 2.0, 2.12, 2.25,
2.37, 2.50, 2.62, 2.75, 2.87, 3.0, 3.2, 3.4, 3.6, 3.8,
4.0, 4.3, 4.7, 4.9, 5.0, 5.5, 6.0, 6.5, 6.8, 7.0,
7.3, 7.5, 7.8, 8.0, 8.4, 8.7, 9.0, 9.4, 9.6, 9.8,
10.0
];
private _multiplyMatrix(colorMat: any) {
let i: number, j: number, k: number, col: any = [];
for (i = 0; i < 5; i++) {
for (j = 0; j < 5; j++) {
col[j] = this.colorMatrix[j + i * 5];
}
for (j = 0; j < 5; j++) {
let val = 0;
for (k = 0; k < 5; k++) {
val += colorMat[j + k * 5] * col[k];
}
this.colorMatrix[j + i * 5] = val;
}
}
}
private _cleanValue(value: number, limit: number): number {
return Math.min(limit, Math.max(-limit, value));
}
/**
*获取滤镜的字符串表现形式以方便比较两个滤镜是否效果一样
* @method toString
* @public
* @since 1.0.0
* @return {string}
*/
public toString(): string {
let s = this;
return s.type + s.brightness + s.hue + s.saturation + s.contrast;
}
public destroy(): void {
this.colorMatrix = null;
}
}
/**
* 模糊滤镜
* @class BlurFilter
* @public
* @since 1.0.0
*/
export class BlurFilter {
/**
* 滤镜类型 只读
* @property type
* @public
* @readonly
* @since 1.0.0
* @type {string}
*/
public type: string = "blur";
/**
* 水平模糊量
* @property blurX
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public blurX: number = 0;
/**
* 垂直模糊量
* @property blurY
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public blurY: number = 0;
/**
* 模糊品质
* @property quality
* @public
* @readonly
* @since 1.0.0
* @type {number}
*/
public quality: number = 1;
/**
* @method BlurFilter
* @public
* @since 1.0.0
* @param {number} blurX
* @param {number} blurY
* @param {number} quality
*/
public constructor(blurX: number = 2, blurY: number = 2, quality: number = 1) {
let s = this;
s.blurX = blurX;
s.blurY = blurY;
s.quality = quality;
}
/**
*获取滤镜的字符串表现形式以方便比较两个滤镜是否效果一样
* @method toString
* @public
* @since 1.0.0
* @return {string}
*/
public toString(): string {
let s = this;
return s.type + s.blurX + s.blurY + s.quality;
}
private static SHG_TABLE: any = [0, 9, 10, 11, 9, 12, 10, 11, 12, 9, 13, 13, 10, 9, 13, 13, 14, 14, 14, 14, 10, 13, 14, 14, 14, 13, 13, 13, 9, 14, 14, 14, 15, 14, 15, 14, 15, 15, 14, 15, 15, 15, 14, 15, 15, 15, 15, 15, 14, 15, 15, 15, 15, 15, 15, 12, 14, 15, 15, 13, 15, 15, 15, 15, 16, 16, 16, 15, 16, 14, 16, 16, 14, 16, 13, 16, 16, 16, 15, 16, 13, 16, 15, 16, 14, 9, 16, 16, 16, 16, 16, 16, 16, 16, 16, 13, 14, 16, 16, 15, 16, 16, 10, 16, 15, 16, 14, 16, 16, 14, 16, 16, 14, 16, 16, 14, 15, 16, 16, 16, 14, 15, 14, 15, 13, 16, 16, 15, 17, 17, 17, 17, 17, 17, 14, 15, 17, 17, 16, 16, 17, 16, 15, 17, 16, 17, 11, 17, 16, 17, 16, 17, 16, 17, 17, 16, 17, 17, 16, 17, 17, 16, 16, 17, 17, 17, 16, 14, 17, 17, 17, 17, 15, 16, 14, 16, 15, 16, 13, 16, 15, 16, 14, 16, 15, 16, 12, 16, 15, 16, 17, 17, 17, 17, 17, 13, 16, 15, 17, 17, 17, 16, 15, 17, 17, 17, 16, 15, 17, 17, 14, 16, 17, 17, 16, 17, 17, 16, 15, 17, 16, 14, 17, 16, 15, 17, 16, 17, 17, 16, 17, 15, 16, 17, 14, 17, 16, 15, 17, 16, 17, 13, 17, 16, 17, 17, 16, 17, 14, 17, 16, 17, 16, 17, 16, 17, 9];
private static MUL_TABLE: any = [1, 171, 205, 293, 57, 373, 79, 137, 241, 27, 391, 357, 41, 19, 283, 265, 497, 469, 443, 421, 25, 191, 365, 349, 335, 161, 155, 149, 9, 278, 269, 261, 505, 245, 475, 231, 449, 437, 213, 415, 405, 395, 193, 377, 369, 361, 353, 345, 169, 331, 325, 319, 313, 307, 301, 37, 145, 285, 281, 69, 271, 267, 263, 259, 509, 501, 493, 243, 479, 118, 465, 459, 113, 446, 55, 435, 429, 423, 209, 413, 51, 403, 199, 393, 97, 3, 379, 375, 371, 367, 363, 359, 355, 351, 347, 43, 85, 337, 333, 165, 327, 323, 5, 317, 157, 311, 77, 305, 303, 75, 297, 294, 73, 289, 287, 71, 141, 279, 277, 275, 68, 135, 67, 133, 33, 262, 260, 129, 511, 507, 503, 499, 495, 491, 61, 121, 481, 477, 237, 235, 467, 232, 115, 457, 227, 451, 7, 445, 221, 439, 218, 433, 215, 427, 425, 211, 419, 417, 207, 411, 409, 203, 202, 401, 399, 396, 197, 49, 389, 387, 385, 383, 95, 189, 47, 187, 93, 185, 23, 183, 91, 181, 45, 179, 89, 177, 11, 175, 87, 173, 345, 343, 341, 339, 337, 21, 167, 83, 331, 329, 327, 163, 81, 323, 321, 319, 159, 79, 315, 313, 39, 155, 309, 307, 153, 305, 303, 151, 75, 299, 149, 37, 295, 147, 73, 291, 145, 289, 287, 143, 285, 71, 141, 281, 35, 279, 139, 69, 275, 137, 273, 17, 271, 135, 269, 267, 133, 265, 33, 263, 131, 261, 130, 259, 129, 257, 1];
/**
* 绘画滤镜效果
* @method drawFilter
* @param {ImageData} imageData
* @since 1.0.0
* @public
*/
public drawFilter(imageData: ImageData = null) {
let s = this;
let radiusX = s.blurX >> 1;
if (isNaN(radiusX) || radiusX < 0) return false;
let radiusY = s.blurY >> 1;
if (isNaN(radiusY) || radiusY < 0) return false;
if (radiusX == 0 && radiusY == 0) return false;
let iterations = s.quality;
if (isNaN(iterations) || iterations < 1) iterations = 1;
iterations |= 0;
if (iterations > 3) iterations = 3;
if (iterations < 1) iterations = 1;
let px: any = imageData.data;
let x = 0, y = 0, i = 0, p = 0, yp = 0, yi = 0, yw = 0, r = 0, g = 0, b = 0, a = 0, pr = 0, pg = 0, pb = 0, pa = 0;
let divx = (radiusX + radiusX + 1) | 0;
let divy = (radiusY + radiusY + 1) | 0;
let w = imageData.width | 0;
let h = imageData.height | 0;
let w1 = (w - 1) | 0;
let h1 = (h - 1) | 0;
let rxp1 = (radiusX + 1) | 0;
let ryp1 = (radiusY + 1) | 0;
let ssx = { r: 0, b: 0, g: 0, a: 0 };
let sx: any = ssx;
for (i = 1; i < divx; i++) {
sx = sx.n = { r: 0, b: 0, g: 0, a: 0 };
}
sx.n = ssx;
let ssy = { r: 0, b: 0, g: 0, a: 0 };
let sy: any = ssy;
for (i = 1; i < divy; i++) {
sy = sy.n = { r: 0, b: 0, g: 0, a: 0 };
}
sy.n = ssy;
let si: any = null;
let mtx = BlurFilter.MUL_TABLE[radiusX] | 0;
let stx = BlurFilter.SHG_TABLE[radiusX] | 0;
let mty = BlurFilter.MUL_TABLE[radiusY] | 0;
let sty = BlurFilter.SHG_TABLE[radiusY] | 0;
while (iterations-- > 0) {
yw = yi = 0;
let ms = mtx;
let ss = stx;
for (y = h; --y > -1;) {
r = rxp1 * (pr = px[(yi) | 0]);
g = rxp1 * (pg = px[(yi + 1) | 0]);
b = rxp1 * (pb = px[(yi + 2) | 0]);
a = rxp1 * (pa = px[(yi + 3) | 0]);
sx = ssx;
for (i = rxp1; --i > -1;) {
sx.r = pr;
sx.g = pg;
sx.b = pb;
sx.a = pa;
sx = sx.n;
}
for (i = 1; i < rxp1; i++) {
p = (yi + ((w1 < i ? w1 : i) << 2)) | 0;
r += (sx.r = px[p]);
g += (sx.g = px[p + 1]);
b += (sx.b = px[p + 2]);
a += (sx.a = px[p + 3]);
sx = sx.n;
}
si = ssx;
for (x = 0; x < w; x++) {
px[yi++] = (r * ms) >>> ss;
px[yi++] = (g * ms) >>> ss;
px[yi++] = (b * ms) >>> ss;
px[yi++] = (a * ms) >>> ss;
p = ((yw + ((p = x + radiusX + 1) < w1 ? p : w1)) << 2);
r -= si.r - (si.r = px[p]);
g -= si.g - (si.g = px[p + 1]);
b -= si.b - (si.b = px[p + 2]);
a -= si.a - (si.a = px[p + 3]);
si = si.n;
}
yw += w;
}
ms = mty;
ss = sty;
for (x = 0; x < w; x++) {
yi = (x << 2) | 0;
r = (ryp1 * (pr = px[yi])) | 0;
g = (ryp1 * (pg = px[(yi + 1) | 0])) | 0;
b = (ryp1 * (pb = px[(yi + 2) | 0])) | 0;
a = (ryp1 * (pa = px[(yi + 3) | 0])) | 0;
sy = ssy;
for (i = 0; i < ryp1; i++) {
sy.r = pr;
sy.g = pg;
sy.b = pb;
sy.a = pa;
sy = sy.n;
}
yp = w;
for (i = 1; i <= radiusY; i++) {
yi = (yp + x) << 2;
r += (sy.r = px[yi]);
g += (sy.g = px[yi + 1]);
b += (sy.b = px[yi + 2]);
a += (sy.a = px[yi + 3]);
sy = sy.n;
if (i < h1) {
yp += w;
}
}
yi = x;
si = ssy;
if (iterations > 0) {
for (y = 0; y < h; y++) {
p = yi << 2;
px[p + 3] = pa = (a * ms) >>> ss;
if (pa > 0) {
px[p] = ((r * ms) >>> ss);
px[p + 1] = ((g * ms) >>> ss);
px[p + 2] = ((b * ms) >>> ss);
} else {
px[p] = px[p + 1] = px[p + 2] = 0
}
p = (x + (((p = y + ryp1) < h1 ? p : h1) * w)) << 2;
r -= si.r - (si.r = px[p]);
g -= si.g - (si.g = px[p + 1]);
b -= si.b - (si.b = px[p + 2]);
a -= si.a - (si.a = px[p + 3]);
si = si.n;
yi += w;
}
} else {
for (y = 0; y < h; y++) {
p = yi << 2;
px[p + 3] = pa = (a * ms) >>> ss;
if (pa > 0) {
pa = 255 / pa;
px[p] = ((r * ms) >>> ss) * pa;
px[p + 1] = ((g * ms) >>> ss) * pa;
px[p + 2] = ((b * ms) >>> ss) * pa;
} else {
px[p] = px[p + 1] = px[p + 2] = 0
}
p = (x + (((p = y + ryp1) < h1 ? p : h1) * w)) << 2;
r -= si.r - (si.r = px[p]);
g -= si.g - (si.g = px[p + 1]);
b -= si.b - (si.b = px[p + 2]);
a -= si.a - (si.a = px[p + 3]);
si = si.n;
yi += w;
}
}
}
}
}
public destroy(): void {
}
}
\ No newline at end of file
export { ShadowFilter } from './Filters';
export { ColorFilter } from './Filters';
export { ColorMatrixFilter } from './Filters';
export { BlurFilter } from './Filters';
\ No newline at end of file
/**
* Created by rockyl on 2018/11/15.
*/
export * from './core'
export * from './editor'
export * from './assets-manager'
export * from './support'
export * from './tools'
export * from './filter'
export * from './engine-config'
export * from './ReType'
\ No newline at end of file
/**
* Created by rockyl on 2018/11/7.
*
*/
/**
* 边界类
*/
export default class Bounds {
x;
y;
width;
height;
constructor(x = 0, y = 0, width = 0, height = 0) {
this.x = x;
this.y = y;
this.width = width;
this.height = height;
}
get left() {
return this.x;
}
set left(v) {
this.x = v;
}
get top() {
return this.y;
}
set top(v) {
this.y = v;
}
get right() {
return this.x + this.width;
}
set right(v) {
this.width = v - this.x;
}
get bottom() {
return this.y + this.height;
}
set bottom(v) {
this.height = v - this.y;
}
contains(x, y) {
return this.x <= x &&
this.x + this.width >= x &&
this.y <= y &&
this.y + this.height >= y;
}
setTo(x, y, width, height) {
this.x = x;
this.y = y;
this.width = width;
this.height = height;
}
copyFrom(target) {
this.x = target.x;
this.y = target.y;
this.width = target.width;
this.height = target.height;
}
clone() {
return new Bounds(this.x, this.y, this.width, this.height)
}
inflate(dx, dy) {
this.x -= dx;
this.width += 2 * dx;
this.y -= dy;
this.height += 2 * dy;
}
isEmpty() {
return this.width <= 0 || this.height <= 0;
}
setEmpty() {
this.x = 0;
this.y = 0;
this.width = 0;
this.height = 0;
}
intersects(toIntersect) {
return Math.max(this.x, toIntersect.x) <= Math.min(this.right, toIntersect.right)
&& Math.max(this.y, toIntersect.y) <= Math.min(this.bottom, toIntersect.bottom);
}
containsBounds(bounds) {
let r1 = bounds.x + bounds.width;
let b1 = bounds.y + bounds.height;
let r2 = this.x + this.width;
let b2 = this.y + this.height;
return (bounds.x >= this.x) && (bounds.x < r2) && (bounds.y >= this.y) && (bounds.y < b2) && (r1 > this.x) && (r1 <= r2) && (b1 > this.y) && (b1 <= b2);
}
equals(toCompare) {
if (this === toCompare) {
return true;
}
return this.x === toCompare.x && this.y === toCompare.y
&& this.width === toCompare.width && this.height === toCompare.height;
}
toString() {
const {x, y, width, height} = this;
return "(x=" + x + ", y=" + y + ", width=" + width + ", height=" + height + ")";
}
}
/**
* Created by rockyl on 2018-12-07.
*/
import {dirtyFieldTrigger} from "../tools/decorators";
const hsv2hsl = function(hue, sat, val) {
return [
hue,
(sat * val / ((hue = (2 - sat) * val) < 1 ? hue : 2 - hue)) || 0,
hue / 2
];
};
// Need to handle 1.0 as 100%, since once it is a number, there is no difference between it and 1
// <http://stackoverflow.com/questions/7422072/javascript-how-to-detect-number-as-a-decimal-including-1-0>
const isOnePointZero = function(n) {
return typeof n === 'string' && n.indexOf('.') !== -1 && parseFloat(n) === 1;
};
const isPercentage = function(n) {
return typeof n === 'string' && n.indexOf('%') !== -1;
};
// Take input from [0, n] and return it as [0, 1]
const bound01 = function(value, max) {
if (isOnePointZero(value)) value = '100%';
const processPercent = isPercentage(value);
value = Math.min(max, Math.max(0, parseFloat(value)));
// Automatically convert percentage into number
if (processPercent) {
value = Math.floor(value * max) / 100;
}
// Handle floating point rounding errors
if ((Math.abs(value - max) < 0.000001)) {
return 1;
}
// Convert into [0, 1] range if it isn't already
return (value % max) / parseFloat(max);
};
const INT_HEX_MAP = { 10: 'A', 11: 'B', 12: 'C', 13: 'D', 14: 'E', 15: 'F' };
const toHex = function({ r, g, b }) {
const hexOne = function(value) {
value = Math.min(Math.round(value), 255);
const high = Math.floor(value / 16);
const low = value % 16;
return '' + (INT_HEX_MAP[high] || high) + (INT_HEX_MAP[low] || low);
};
if (isNaN(r) || isNaN(g) || isNaN(b)) return '';
return '#' + hexOne(r) + hexOne(g) + hexOne(b);
};
const HEX_INT_MAP = { A: 10, B: 11, C: 12, D: 13, E: 14, F: 15 };
const parseHexChannel = function(hex) {
if (hex.length === 2) {
return (HEX_INT_MAP[hex[0].toUpperCase()] || +hex[0]) * 16 + (HEX_INT_MAP[hex[1].toUpperCase()] || +hex[1]);
}
return HEX_INT_MAP[hex[1].toUpperCase()] || +hex[1];
};
const hsl2hsv = function(hue, sat, light) {
sat = sat / 100;
light = light / 100;
let smin = sat;
const lmin = Math.max(light, 0.01);
let sv;
let v;
light *= 2;
sat *= (light <= 1) ? light : 2 - light;
smin *= lmin <= 1 ? lmin : 2 - lmin;
v = (light + sat) / 2;
sv = light === 0 ? (2 * smin) / (lmin + smin) : (2 * sat) / (light + sat);
return {
h: hue,
s: sv * 100,
v: v * 100
};
};
// `rgbToHsv`
// Converts an RGB color value to HSV
// *Assumes:* r, g, and b are contained in the set [0, 255] or [0, 1]
// *Returns:* { h, s, v } in [0,1]
const rgb2hsv = function(r, g, b) {
r = bound01(r, 255);
g = bound01(g, 255);
b = bound01(b, 255);
const max = Math.max(r, g, b);
const min = Math.min(r, g, b);
let h, s;
let v = max;
const d = max - min;
s = max === 0 ? 0 : d / max;
if (max === min) {
h = 0; // achromatic
} else {
switch (max) {
case r:
h = (g - b) / d + (g < b ? 6 : 0);
break;
case g:
h = (b - r) / d + 2;
break;
case b:
h = (r - g) / d + 4;
break;
}
h /= 6;
}
return { h: h * 360, s: s * 100, v: v * 100 };
};
// `hsvToRgb`
// Converts an HSV color value to RGB.
// *Assumes:* h is contained in [0, 1] or [0, 360] and s and v are contained in [0, 1] or [0, 100]
// *Returns:* { r, g, b } in the set [0, 255]
const hsv2rgb = function(h, s, v) {
h = bound01(h, 360) * 6;
s = bound01(s, 100);
v = bound01(v, 100);
const i = Math.floor(h);
const f = h - i;
const p = v * (1 - s);
const q = v * (1 - f * s);
const t = v * (1 - (1 - f) * s);
const mod = i % 6;
const r = [v, q, p, p, t, v][mod];
const g = [t, v, v, q, p, p][mod];
const b = [p, p, t, v, v, q][mod];
return {
r: Math.round(r * 255),
g: Math.round(g * 255),
b: Math.round(b * 255)
};
};
/**
* 颜色
*/
export default class Color {
enableAlpha;
format;
private _hue;
private _saturation;
private _value;
private _valueStr;
private _alpha;
constructor(value?) {
this._hue = 0;
this._saturation = 100;
this._value = 100;
this._alpha = 100;
this.enableAlpha = true;
this.format = 'hex';
if(value){
this.value = value;
}else{
this.value = '';
}
this.doOnChange();
}
get value(){
return this._valueStr;
}
set value(v){
this.fromString(v);
}
set(prop, value) {
if (arguments.length === 1 && typeof prop === 'object') {
for (let p in prop) {
if (prop.hasOwnProperty(p)) {
this.set(p, prop[p]);
}
}
return;
}
this['_' + prop] = value;
this.doOnChange();
}
get(prop) {
return this['_' + prop];
}
toRgb() {
return hsv2rgb(this._hue, this._saturation, this._value);
}
fromString(value) {
if (!value) {
this._hue = 0;
this._saturation = 100;
this._value = 100;
this.doOnChange();
return;
}
const fromHSV = (h, s, v) => {
this._hue = Math.max(0, Math.min(360, h));
this._saturation = Math.max(0, Math.min(100, s));
this._value = Math.max(0, Math.min(100, v));
this.doOnChange();
};
if (value.indexOf('hsl') !== -1) {
const parts = value.replace(/hsla|hsl|\(|\)/gm, '')
.split(/\s|,/g).filter((val) => val !== '').map((val, index) => index > 2 ? parseFloat(val) : parseInt(val, 10));
if (parts.length === 4) {
this._alpha = Math.floor(parseFloat(parts[3]) * 100);
} else if (parts.length === 3) {
this._alpha = 100;
}
if (parts.length >= 3) {
const { h, s, v } = hsl2hsv(parts[0], parts[1], parts[2]);
fromHSV(h, s, v);
}
} else if (value.indexOf('hsv') !== -1) {
const parts = value.replace(/hsva|hsv|\(|\)/gm, '')
.split(/\s|,/g).filter((val) => val !== '').map((val, index) => index > 2 ? parseFloat(val) : parseInt(val, 10));
if (parts.length === 4) {
this._alpha = Math.floor(parseFloat(parts[3]) * 100);
} else if (parts.length === 3) {
this._alpha = 100;
}
if (parts.length >= 3) {
fromHSV(parts[0], parts[1], parts[2]);
}
} else if (value.indexOf('rgb') !== -1) {
const parts = value.replace(/rgba|rgb|\(|\)/gm, '')
.split(/\s|,/g).filter((val) => val !== '').map((val, index) => index > 2 ? parseFloat(val) : parseInt(val, 10));
if (parts.length === 4) {
this._alpha = Math.floor(parseFloat(parts[3]) * 100);
} else if (parts.length === 3) {
this._alpha = 100;
}
if (parts.length >= 3) {
const { h, s, v } = rgb2hsv(parts[0], parts[1], parts[2]);
fromHSV(h, s, v);
}
} else if (value.indexOf('#') !== -1) {
const hex = value.replace('#', '').trim();
let r, g, b;
if (hex.length === 3) {
r = parseHexChannel(hex[0] + hex[0]);
g = parseHexChannel(hex[1] + hex[1]);
b = parseHexChannel(hex[2] + hex[2]);
} else if (hex.length === 6 || hex.length === 8) {
r = parseHexChannel(hex.substring(0, 2));
g = parseHexChannel(hex.substring(2, 4));
b = parseHexChannel(hex.substring(4, 6));
}
if (hex.length === 8) {
this._alpha = Math.floor(parseHexChannel(hex.substring(6)) / 255 * 100);
} else if (hex.length === 3 || hex.length === 6) {
this._alpha = 100;
}
const { h, s, v } = rgb2hsv(r, g, b);
fromHSV(h, s, v);
}
}
compare(color) {
return Math.abs(color._hue - this._hue) < 2 &&
Math.abs(color._saturation - this._saturation) < 1 &&
Math.abs(color._value - this._value) < 1 &&
Math.abs(color._alpha - this._alpha) < 1;
}
doOnChange() {
const { _hue, _saturation, _value, _alpha, format } = this;
if (this.enableAlpha) {
switch (format) {
case 'hsl':
const hsl = hsv2hsl(_hue, _saturation / 100, _value / 100);
this._valueStr = `hsla(${ _hue }, ${ Math.round(hsl[1] * 100) }%, ${ Math.round(hsl[2] * 100) }%, ${ _alpha / 100})`;
break;
case 'hsv':
this._valueStr = `hsva(${ _hue }, ${ Math.round(_saturation) }%, ${ Math.round(_value) }%, ${ _alpha / 100})`;
break;
default:
const { r, g, b } = hsv2rgb(_hue, _saturation, _value);
this._valueStr = `rgba(${r}, ${g}, ${b}, ${ _alpha / 100 })`;
}
} else {
switch (format) {
case 'hsl':
const hsl = hsv2hsl(_hue, _saturation / 100, _value / 100);
this._valueStr = `hsl(${ _hue }, ${ Math.round(hsl[1] * 100) }%, ${ Math.round(hsl[2] * 100) }%)`;
break;
case 'hsv':
this._valueStr = `hsv(${ _hue }, ${ Math.round(_saturation) }%, ${ Math.round(_value) }%)`;
break;
case 'rgb':
const { r, g, b } = hsv2rgb(_hue, _saturation, _value);
this._valueStr = `rgb(${r}, ${g}, ${b})`;
break;
default:
this._valueStr = toHex(hsv2rgb(_hue, _saturation, _value));
}
}
}
};
\ No newline at end of file
/**
* Created by rockyl on 2018-11-25.
*/
'use strict';
var has = Object.prototype.hasOwnProperty
, prefix = '~';
/**
* Constructor to create a storage for our `EE` objects.
* An `Events` instance is a plain object whose properties are event names.
*
* @constructor
* @private
*/
function Events() {}
//
// We try to not inherit from `Object.prototype`. In some engines creating an
// instance in this way is faster than calling `Object.create(null)` directly.
// If `Object.create(null)` is not supported we prefix the event names with a
// character to make sure that the built-in object properties are not
// overridden or used as an attack vector.
//
if (Object.create) {
Events.prototype = Object.create(null);
//
// This hack is needed because the `__proto__` property is still inherited in
// some old browsers like Android 4, iPhone 5.1, Opera 11 and Safari 5.
//
if (!new Events().__proto__) prefix = '';
}
/**
* Representation of a single event listener.
*
* @param {Function} fn The listener function.
* @param {*} context The context to invoke the listener with.
* @param {Boolean} [once=false] Specify if the listener is a one-time listener.
* @constructor
* @private
*/
function EE(fn, context, once) {
this.fn = fn;
this.context = context;
this.once = once || false;
}
/**
* Add a listener for a given event.
*
* @param {EventEmitter} emitter Reference to the `EventEmitter` instance.
* @param {(String|Symbol)} event The event name.
* @param {Function} fn The listener function.
* @param {*} context The context to invoke the listener with.
* @param {Boolean} once Specify if the listener is a one-time listener.
* @returns {EventEmitter}
* @private
*/
function addListener(emitter, event, fn, context, once) {
if (typeof fn !== 'function') {
throw new TypeError('The listener must be a function');
}
var listener = new EE(fn, context || emitter, once)
, evt = prefix ? prefix + event : event;
if (!emitter._events[evt]) emitter._events[evt] = listener, emitter._eventsCount++;
else if (!emitter._events[evt].fn) emitter._events[evt].push(listener);
else emitter._events[evt] = [emitter._events[evt], listener];
return emitter;
}
/**
* Clear event by name.
*
* @param {EventEmitter} emitter Reference to the `EventEmitter` instance.
* @param {(String|Symbol)} evt The Event name.
* @private
*/
function clearEvent(emitter, evt) {
if (--emitter._eventsCount === 0) emitter._events = new Events();
else delete emitter._events[evt];
}
/**
* Minimal `EventEmitter` interface that is molded against the Node.js
* `EventEmitter` interface.
*
* @constructor
* @public
*/
export default class EventEmitter{
_events;
_eventsCount;
off;
addListener;
static get prefixed(){
return prefix;
}
constructor() {
this._events = new Events();
this._eventsCount = 0;
this.off = this.removeListener;
this.addListener = this.on;
}
/**
* Return an array listing the events for which the emitter has registered
* listeners.
*
* @returns {Array}
* @public
*/
eventNames() {
var names = []
, events
, name;
if (this._eventsCount === 0) return names;
for (name in (events = this._events)) {
if (has.call(events, name)) names.push(prefix ? name.slice(1) : name);
}
//if (Object.getOwnPropertySymbols) {
// return names.concat(Object.getOwnPropertySymbols(events));
//}
return names;
}
/**
* Return the listeners registered for a given event.
*
* @param {(String|Symbol)} event The event name.
* @returns {Array} The registered listeners.
* @public
*/
listeners(event) {
var evt = prefix ? prefix + event : event
, handlers = this._events[evt];
if (!handlers) return [];
if (handlers.fn) return [handlers.fn];
for (var i = 0, l = handlers.length, ee = new Array(l); i < l; i++) {
ee[i] = handlers[i].fn;
}
return ee;
}
/**
* Return the number of listeners listening to a given event.
*
* @param {(String|Symbol)} event The event name.
* @returns {Number} The number of listeners.
* @public
*/
listenerCount(event) {
var evt = prefix ? prefix + event : event
, listeners = this._events[evt];
if (!listeners) return 0;
if (listeners.fn) return 1;
return listeners.length;
}
/**
* Calls each of the listeners registered for a given event.
*
* @param {(String|Symbol)} event The event name.
* @returns {Boolean} `true` if the event had listeners, else `false`.
* @public
*/
emit(event, a1?, a2?, a3?, a4?, a5?) {
var evt = prefix ? prefix + event : event;
if (!this._events[evt]) return false;
var listeners = this._events[evt]
, len = arguments.length
, args
, i;
if (listeners.fn) {
if (listeners.once) this.removeListener(event, listeners.fn, undefined, true);
switch (len) {
case 1: return listeners.fn.call(listeners.context), true;
case 2: return listeners.fn.call(listeners.context, a1), true;
case 3: return listeners.fn.call(listeners.context, a1, a2), true;
case 4: return listeners.fn.call(listeners.context, a1, a2, a3), true;
case 5: return listeners.fn.call(listeners.context, a1, a2, a3, a4), true;
case 6: return listeners.fn.call(listeners.context, a1, a2, a3, a4, a5), true;
}
for (i = 1, args = new Array(len -1); i < len; i++) {
args[i - 1] = arguments[i];
}
listeners.fn.apply(listeners.context, args);
} else {
var length = listeners.length
, j;
for (i = 0; i < length; i++) {
if (listeners[i].once) this.removeListener(event, listeners[i].fn, undefined, true);
switch (len) {
case 1: listeners[i].fn.call(listeners[i].context); break;
case 2: listeners[i].fn.call(listeners[i].context, a1); break;
case 3: listeners[i].fn.call(listeners[i].context, a1, a2); break;
case 4: listeners[i].fn.call(listeners[i].context, a1, a2, a3); break;
default:
if (!args) for (j = 1, args = new Array(len -1); j < len; j++) {
args[j - 1] = arguments[j];
}
listeners[i].fn.apply(listeners[i].context, args);
}
}
}
return true;
}
/**
* Add a listener for a given event.
*
* @param {(String|Symbol)} event The event name.
* @param {Function} fn The listener function.
* @param {*} [context=this] The context to invoke the listener with.
* @returns {EventEmitter} `this`.
* @public
*/
on(event, fn, context) {
return addListener(this, event, fn, context, false);
};
/**
* Add a one-time listener for a given event.
*
* @param {(String|Symbol)} event The event name.
* @param {Function} fn The listener function.
* @param {*} [context=this] The context to invoke the listener with.
* @returns {EventEmitter} `this`.
* @public
*/
once(event, fn, context) {
return addListener(this, event, fn, context, true);
}
/**
* Remove the listeners of a given event.
*
* @param {(String|Symbol)} event The event name.
* @param {Function} fn Only remove the listeners that match this function.
* @param {*} context Only remove the listeners that have this context.
* @param {Boolean} once Only remove one-time listeners.
* @returns {EventEmitter} `this`.
* @public
*/
removeListener(event, fn, context, once) {
var evt = prefix ? prefix + event : event;
if (!this._events[evt]) return this;
if (!fn) {
clearEvent(this, evt);
return this;
}
var listeners = this._events[evt];
if (listeners.fn) {
if (
listeners.fn === fn &&
(!once || listeners.once) &&
(!context || listeners.context === context)
) {
clearEvent(this, evt);
}
} else {
for (var i = 0, events = [], length = listeners.length; i < length; i++) {
if (
listeners[i].fn !== fn ||
(once && !listeners[i].once) ||
(context && listeners[i].context !== context)
) {
events.push(listeners[i]);
}
}
//
// Reset the array, or remove it completely if we have no more listeners.
//
if (events.length) this._events[evt] = events.length === 1 ? events[0] : events;
else clearEvent(this, evt);
}
return this;
}
/**
* Remove all listeners, or those of the specified event.
*
* @param {(String|Symbol)} [event] The event name.
* @returns {EventEmitter} `this`.
* @public
*/
removeAllListeners(event) {
var evt;
if (event) {
evt = prefix ? prefix + event : event;
if (this._events[evt]) clearEvent(this, evt);
} else {
this._events = new Events();
this._eventsCount = 0;
}
return this;
}
}
\ No newline at end of file
/**
* Created by rockyl on 2019-01-04.
*/
export default class LocalStorage {
ID: string;
constructor(ID: string) {
this.ID = ID;
}
getName(key: string, prefix: string = null): string {
return (prefix || !this.ID || this.ID == '' ? prefix : this.ID) + '_' + key;
}
getItem(key: string, prefix: string = null): string {
return localStorage.getItem(this.getName(key, prefix));
}
setItem(key: string, value: string, prefix: string = null) {
localStorage.setItem(this.getName(key, prefix), value);
}
getItemObj(key: string, defaultObj: any = null, prefix: string = null): any {
let result: any;
try {
result = JSON.parse(this.getItem(key, prefix));
} catch (e) {
}
if (!result) {
result = defaultObj;
}
return result;
}
setItemObj(key: string, itemObj: any, prefix: string = null) {
this.setItem(key, JSON.stringify(itemObj), prefix);
}
}
\ No newline at end of file
/**
* Created by rockyl on 2018/11/6.
*
* 矩阵 3x3
*/
let PI = Math.PI;
let TwoPI = PI * 2;
let DEG_TO_RAD = PI / 180;
let matrixPool = [];
/**
* Matrix 类表示一个转换矩阵,它确定如何将点从一个坐标空间映射到另一个坐标空间。
* 您可以对一个显示对象执行不同的图形转换,方法是设置 Matrix 对象的属性,将该 Matrix
* 对象应用于显示对象的 matrix 属性。这些转换函数包括平移(x 和 y 重新定位)、旋转、缩放和倾斜。
*/
export default class Matrix {
a;
b;
c;
d;
tx;
ty;
/**
* 释放一个Matrix实例到对象池
* @param matrix 需要回收的 matrix
*/
static release(matrix) {
if (!matrix) {
return;
}
matrixPool.push(matrix);
}
/**
* 从对象池中取出或创建一个新的Matrix对象。
*/
static create() {
let matrix = matrixPool.pop();
if (!matrix) {
matrix = new Matrix();
}
return matrix;
}
/**
* 使用指定参数创建一个 Matrix 对象
* @param a 缩放或旋转图像时影响像素沿 x 轴定位的值。
* @param b 旋转或倾斜图像时影响像素沿 y 轴定位的值。
* @param c 旋转或倾斜图像时影响像素沿 x 轴定位的值。
* @param d 缩放或旋转图像时影响像素沿 y 轴定位的值。
* @param tx 沿 x 轴平移每个点的距离。
* @param ty 沿 y 轴平移每个点的距离。
*/
constructor(a = 1, b = 0, c = 0, d = 1, tx = 0, ty = 0) {
this.a = a;
this.b = b;
this.c = c;
this.d = d;
this.tx = tx;
this.ty = ty;
}
/**
* 返回一个新的 Matrix 对象,它是此矩阵的克隆,带有与所含对象完全相同的副本。
*/
clone() {
const m = Matrix.create();
m.setTo(this.a, this.b, this.c, this.d, this.tx, this.ty)
return m
}
/**
* 将某个矩阵与当前矩阵连接,从而将这两个矩阵的几何效果有效地结合在一起。在数学术语中,将两个矩阵连接起来与使用矩阵乘法将它们结合起来是相同的。
* @param other 要连接到源矩阵的矩阵。
*/
concat(other) {
let a = this.a * other.a;
let b = 0.0;
let c = 0.0;
let d = this.d * other.d;
let tx = this.tx * other.a + other.tx;
let ty = this.ty * other.d + other.ty;
if (this.b !== 0.0 || this.c !== 0.0 || other.b !== 0.0 || other.c !== 0.0) {
a += this.b * other.c;
d += this.c * other.b;
b += this.a * other.b + this.b * other.d;
c += this.c * other.a + this.d * other.c;
tx += this.ty * other.c;
ty += this.tx * other.b;
}
this.a = a;
this.b = b;
this.c = c;
this.d = d;
this.tx = tx;
this.ty = ty;
}
/**
* 将源 Matrix 对象中的所有矩阵数据复制到调用方 Matrix 对象中。
* @param other 要拷贝的目标矩阵
*/
copyFrom(other) {
this.a = other.a;
this.b = other.b;
this.c = other.c;
this.d = other.d;
this.tx = other.tx;
this.ty = other.ty;
return this;
}
/**
* 为每个矩阵属性设置一个值,该值将导致矩阵无转换。通过应用恒等矩阵转换的对象将与原始对象完全相同。
* 调用 identity() 方法后,生成的矩阵具有以下属性:a=1、b=0、c=0、d=1、tx=0 和 ty=0。
*/
identity() {
this.a = this.d = 1;
this.b = this.c = this.tx = this.ty = 0;
}
/**
* 执行原始矩阵的逆转换。
* 您可以将一个逆矩阵应用于对象来撤消在应用原始矩阵时执行的转换。
*/
invert() {
this.$invertInto(this);
}
/**
* @private
*/
$invertInto(target) {
let a = this.a;
let b = this.b;
let c = this.c;
let d = this.d;
let tx = this.tx;
let ty = this.ty;
if (b == 0 && c == 0) {
target.b = target.c = 0;
if (a == 0 || d == 0) {
target.a = target.d = target.tx = target.ty = 0;
}
else {
a = target.a = 1 / a;
d = target.d = 1 / d;
target.tx = -a * tx;
target.ty = -d * ty;
}
return;
}
let determinant = a * d - b * c;
if (determinant == 0) {
target.identity();
return;
}
determinant = 1 / determinant;
let k = target.a = d * determinant;
b = target.b = -b * determinant;
c = target.c = -c * determinant;
d = target.d = a * determinant;
target.tx = -(k * tx + c * ty);
target.ty = -(b * tx + d * ty);
}
/**
* 对 Matrix 对象应用旋转转换。
* rotate() 方法将更改 Matrix 对象的 a、b、c 和 d 属性。
* @param radian 以弧度为单位的旋转角度。
*/
rotate(radian) {
radian = +radian;
if (radian !== 0) {
//angle = angle / DEG_TO_RAD;
let u = Math.cos(radian);
let v = Math.sin(radian);
const {a, b, c, d, tx, ty} = this;
this.a = a * u - b * v;
this.b = a * v + b * u;
this.c = c * u - d * v;
this.d = c * v + d * u;
this.tx = tx * u - ty * v;
this.ty = tx * v + ty * u;
}
}
/**
* 对矩阵应用缩放转换。x 轴乘以 sx,y 轴乘以 sy。
* scale() 方法将更改 Matrix 对象的 a 和 d 属性。
* @param sx 用于沿 x 轴缩放对象的乘数。
* @param sy 用于沿 y 轴缩放对象的乘数。
*/
scale(sx, sy) {
if (sx !== 1) {
this.a *= sx;
this.c *= sx;
this.tx *= sx;
}
if (sy !== 1) {
this.b *= sy;
this.d *= sy;
this.ty *= sy;
}
}
/**
* 将 Matrix 的成员设置为指定值
* @param a 缩放或旋转图像时影响像素沿 x 轴定位的值。
* @param b 旋转或倾斜图像时影响像素沿 y 轴定位的值。
* @param c 旋转或倾斜图像时影响像素沿 x 轴定位的值。
* @param d 缩放或旋转图像时影响像素沿 y 轴定位的值。
* @param tx 沿 x 轴平移每个点的距离。
* @param ty 沿 y 轴平移每个点的距离。
*/
setTo(a, b, c, d, tx, ty) {
this.a = a;
this.b = b;
this.c = c;
this.d = d;
this.tx = tx;
this.ty = ty;
return this;
}
/**
* 返回将 Matrix 对象表示的几何转换应用于指定点所产生的结果。
* @param pointX 想要获得其矩阵转换结果的点的x坐标。
* @param pointY 想要获得其矩阵转换结果的点的y坐标。
* @param resultPoint 框架建议尽可能减少创建对象次数来优化性能,可以从外部传入一个复用的Point对象来存储结果,若不传入将创建一个新的Point对象返回。
* @returns Object 由应用矩阵转换所产生的点。
*/
transformPoint(pointX, pointY, resultPoint) {
const {a, b, c, d, tx, ty} = this;
let x = a * pointX + c * pointY + tx;
let y = b * pointX + d * pointY + ty;
if (resultPoint) {
resultPoint.x = x;
resultPoint.y = y;
return resultPoint;
}
return {x, y};
}
/**
* 如果给定预转换坐标空间中的点,则此方法返回发生转换后该点的坐标。
* 与使用 transformPoint() 方法应用的标准转换不同,deltaTransformPoint() 方法的转换不考虑转换参数 tx 和 ty。
* @param pointX 想要获得其矩阵转换结果的点的x坐标。
* @param pointY 想要获得其矩阵转换结果的点的y坐标。
* @param resultPoint 框架建议尽可能减少创建对象次数来优化性能,可以从外部传入一个复用的Point对象来存储结果,若不传入将创建一个新的Point对象返回。
*/
deltaTransformPoint(pointX, pointY, resultPoint) {
const {a, b, c, d} = this;
let x = a * pointX + c * pointY;
let y = b * pointX + d * pointY;
if (resultPoint) {
resultPoint.x = x;
resultPoint.y = y;
return resultPoint;
}
return {x, y};
}
/**
* 沿 x 和 y 轴平移矩阵,由 dx 和 dy 参数指定。
* @param dx 沿 x 轴向右移动的量(以像素为单位)。
* @param dy 沿 y 轴向下移动的量(以像素为单位)。
*/
translate(dx, dy) {
this.tx += dx;
this.ty += dy;
}
/**
* 是否与另一个矩阵数据相等
* @param other 要比较的另一个矩阵对象。
* @returns 是否相等,ture表示相等。
*/
equals(other) {
return this.a == other.a && this.b == other.b &&
this.c == other.c && this.d == other.d &&
this.tx == other.tx && this.ty == other.ty;
}
/**
* 前置矩阵
* @param a 缩放或旋转图像时影响像素沿 x 轴定位的值
* @param b 缩放或旋转图像时影响像素沿 y 轴定位的值
* @param c 缩放或旋转图像时影响像素沿 x 轴定位的值
* @param d 缩放或旋转图像时影响像素沿 y 轴定位的值
* @param tx 沿 x 轴平移每个点的距离
* @param ty 沿 y 轴平移每个点的距离
* @returns 矩阵自身
*/
prepend(a, b, c, d, tx, ty) {
let tx1 = this.tx;
if (a != 1 || b != 0 || c != 0 || d != 1) {
let a1 = this.a;
let c1 = this.c;
this.a = a1 * a + this.b * c;
this.b = a1 * b + this.b * d;
this.c = c1 * a + this.d * c;
this.d = c1 * b + this.d * d;
}
this.tx = tx1 * a + this.ty * c + tx;
this.ty = tx1 * b + this.ty * d + ty;
return this;
}
/**
* 后置矩阵
* @param a 缩放或旋转图像时影响像素沿 x 轴定位的值
* @param b 缩放或旋转图像时影响像素沿 y 轴定位的值
* @param c 缩放或旋转图像时影响像素沿 x 轴定位的值
* @param d 缩放或旋转图像时影响像素沿 y 轴定位的值
* @param tx 沿 x 轴平移每个点的距离
* @param ty 沿 y 轴平移每个点的距离
* @returns 矩阵自身
*/
append(a, b, c, d, tx, ty) {
let a1 = this.a;
let b1 = this.b;
let c1 = this.c;
let d1 = this.d;
if (a != 1 || b != 0 || c != 0 || d != 1) {
this.a = a * a1 + b * c1;
this.b = a * b1 + b * d1;
this.c = c * a1 + d * c1;
this.d = c * b1 + d * d1;
}
this.tx = tx * a1 + ty * c1 + this.tx;
this.ty = tx * b1 + ty * d1 + this.ty;
return this;
}
/**
* 返回将 Matrix 对象表示的几何转换应用于指定点所产生的结果。
* @returns 一个字符串,它包含 Matrix 对象的属性值:a、b、c、d、tx 和 ty。
*/
toString() {
return "(a=" + this.a + ", b=" + this.b + ", c=" + this.c + ", d=" + this.d + ", tx=" + this.tx + ", ty=" + this.ty + ")";
}
/**
* 包括用于缩放、旋转和转换的参数。当应用于矩阵时,该方法会基于这些参数设置矩阵的值。
* @param scaleX 水平缩放所用的系数
* @param scaleY 垂直缩放所用的系数
* @param rotation 旋转量(以弧度为单位)
* @param tx 沿 x 轴向右平移(移动)的像素数
* @param ty 沿 y 轴向下平移(移动)的像素数
*/
createBox(scaleX, scaleY, rotation = 0, tx = 0, ty = 0) {
let self = this;
if (rotation !== 0) {
rotation = rotation / DEG_TO_RAD;
let u = Math.cos(rotation);
let v = Math.sin(rotation);
self.a = u * scaleX;
self.b = v * scaleY;
self.c = -v * scaleX;
self.d = u * scaleY;
} else {
self.a = scaleX;
self.b = 0;
self.c = 0;
self.d = scaleY;
}
self.tx = tx;
self.ty = ty;
}
/**
* 创建 Graphics 类的 beginGradientFill() 和 lineGradientStyle() 方法所需的矩阵的特定样式。
* 宽度和高度被缩放为 scaleX/scaleY 对,而 tx/ty 值偏移了宽度和高度的一半。
* @param width 渐变框的宽度
* @param height 渐变框的高度
* @param rotation 旋转量(以弧度为单位)
* @param tx 沿 x 轴向右平移的距离(以像素为单位)。此值将偏移 width 参数的一半
* @param ty 沿 y 轴向下平移的距离(以像素为单位)。此值将偏移 height 参数的一半
*/
createGradientBox(width, height, rotation = 0, tx = 0, ty = 0) {
this.createBox(width / 1638.4, height / 1638.4, rotation, tx + width / 2, ty + height / 2);
}
/**
* @private
*/
$transformBounds(bounds) {
let a = this.a;
let b = this.b;
let c = this.c;
let d = this.d;
let tx = this.tx;
let ty = this.ty;
let x = bounds.x;
let y = bounds.y;
let xMax = x + bounds.width;
let yMax = y + bounds.height;
let x0 = a * x + c * y + tx;
let y0 = b * x + d * y + ty;
let x1 = a * xMax + c * y + tx;
let y1 = b * xMax + d * y + ty;
let x2 = a * xMax + c * yMax + tx;
let y2 = b * xMax + d * yMax + ty;
let x3 = a * x + c * yMax + tx;
let y3 = b * x + d * yMax + ty;
let tmp = 0;
if (x0 > x1) {
tmp = x0;
x0 = x1;
x1 = tmp;
}
if (x2 > x3) {
tmp = x2;
x2 = x3;
x3 = tmp;
}
bounds.x = Math.floor(x0 < x2 ? x0 : x2);
bounds.width = Math.ceil((x1 > x3 ? x1 : x3) - bounds.x);
if (y0 > y1) {
tmp = y0;
y0 = y1;
y1 = tmp;
}
if (y2 > y3) {
tmp = y2;
y2 = y3;
y3 = tmp;
}
bounds.y = Math.floor(y0 < y2 ? y0 : y2);
bounds.height = Math.ceil((y1 > y3 ? y1 : y3) - bounds.y);
}
/**
* @private
*/
getDeterminant() {
return this.a * this.d - this.b * this.c;
}
/**
* @private
*/
$getScaleX() {
let m = this;
if (m.b == 0) {
return m.a;
}
let result = Math.sqrt(m.a * m.a + m.b * m.b);
return this.getDeterminant() < 0 ? -result : result;
}
/**
* @private
*/
$getScaleY() {
let m = this;
if (m.c == 0) {
return m.d;
}
let result = Math.sqrt(m.c * m.c + m.d * m.d);
return this.getDeterminant() < 0 ? -result : result;
}
/**
* @private
*/
$getSkewX() {
if (this.d < 0) {
return Math.atan2(this.d, this.c) + (PI / 2);
}
else {
return Math.atan2(this.d, this.c) - (PI / 2);
}
}
/**
* @private
*/
$getSkewY() {
if (this.a < 0) {
return Math.atan2(this.b, this.a) - PI;
}
else {
return Math.atan2(this.b, this.a);
}
}
/**
* @private
*/
$updateScaleAndRotation(scaleX, scaleY, skewX, skewY) {
if ((skewX == 0 || skewX == TwoPI) && (skewY == 0 || skewY == TwoPI)) {
this.a = scaleX;
this.b = this.c = 0;
this.d = scaleY;
return;
}
skewX = skewX / DEG_TO_RAD;
skewY = skewY / DEG_TO_RAD;
let u = Math.cos(skewX);
let v = Math.sin(skewX);
if (skewX == skewY) {
this.a = u * scaleX;
this.b = v * scaleX;
} else {
this.a = Math.cos(skewY) * scaleX;
this.b = Math.sin(skewY) * scaleX;
}
this.c = -v * scaleY;
this.d = u * scaleY;
}
/**
* @private
* target = other * this
*/
$preMultiplyInto(other, target) {
let a = other.a * this.a;
let b = 0.0;
let c = 0.0;
let d = other.d * this.d;
let tx = other.tx * this.a + this.tx;
let ty = other.ty * this.d + this.ty;
if (other.b !== 0.0 || other.c !== 0.0 || this.b !== 0.0 || this.c !== 0.0) {
a += other.b * this.c;
d += other.c * this.b;
b += other.a * this.b + other.b * this.d;
c += other.c * this.a + other.d * this.c;
tx += other.ty * this.c;
ty += other.tx * this.b;
}
target.a = a;
target.b = b;
target.c = c;
target.d = d;
target.tx = tx;
target.ty = ty;
}
}
\ No newline at end of file
/**
* Created by rockyl on 2018/8/1.
*
* 对象池
*/
let all = {};
function getGroup(name){
let group = all[name];
if(!group){
throw new Error('group ' + name + ' not registered.');
}
return group;
}
export function register(name, newFunc, initFunc){
all[name] = {name, newFunc, initFunc, pool: []};
}
export function get(name, ...params){
let group = getGroup(name);
let {newFunc, initFunc, pool} = group;
let instance;
if(pool.length == 0){
instance = newFunc();
}else{
instance = pool.pop();
}
initFunc(instance, ...params);
return instance;
}
export function recycle(name, instance){
let group = getGroup(name);
group.pool.push(instance);
}
\ No newline at end of file
/**
* Created by rockyl on 2018-12-07.
*/
import {dirtyFieldTrigger} from "../tools/decorators";
/**
* 尺寸
*/
export default class Size {
@dirtyFieldTrigger
width: number;
@dirtyFieldTrigger
height: number;
onChange;
constructor(width = NaN, height = NaN) {
this.width = width;
this.height = height;
}
setNaN(){
this.width = NaN;
this.height = NaN;
}
isEmpty(){
}
set(width?, height?) {
if (width !== undefined) {
this.width = width;
}
if (height !== undefined) {
this.height = height;
}
}
clone() {
return new Size(this.width, this.height);
}
copyFrom(target) {
this.width = target.width;
this.height = target.height;
}
onModify(value, key, oldValue) {
this.onChange && this.onChange(value, key, oldValue);
}
}
/**
* Created by rockyl on 2018-11-29.
*/
import {dirtyFieldTrigger} from "../tools/decorators";
export enum FontStyle{
/**
* 正常
*/
NORMAL = 'normal',
/**
* 斜体
*/
ITALIC = 'italic',
/**
* 倾斜
*/
OBLIQUE = 'oblique',
}
export enum FontVariant{
/**
* 正常
*/
NORMAL = 'normal',
/**
* 小型大写
*/
SMALL_CAPS = 'small-caps',
}
export enum FontWeight{
/**
* 正常
*/
NORMAL = 'normal',
/**
* 粗体
*/
BOLD = 'bold',
/**
* 更粗
*/
BOLDER = 'bolder',
/**
* 更细
*/
LIGHTER = 'lighter',
}
/**
* 文本样式
*/
export class TextStyle {
private readonly _callback;
onChange;
/**
* 字体样式
*/
@dirtyFieldTrigger
fontStyle: FontStyle = FontStyle.NORMAL;
/**
* 字体倾斜
*/
@dirtyFieldTrigger
fontVariant: FontVariant = FontVariant.NORMAL;
/**
* 字体宽度
*/
@dirtyFieldTrigger
fontWeight: FontWeight = FontWeight.NORMAL;
/**
* 字体尺寸
*/
@dirtyFieldTrigger
fontSize: number = 25;
/**
* 字体名称
*/
@dirtyFieldTrigger
fontFamily: string = 'Arial';
onModify(value, key, oldValue) {
this.onChange && this.onChange(value, key, oldValue, 'textStyle');
}
}
/**
* Created by rockyl on 2018/11/8.
*
*/
import {ScillaComponent} from "../core";
import {lerp, lerpObj} from "../tools/math";
import {injectProp} from "../tools/utils";
import HashObject from "../core/HashObject";
enum STATUS {
IDLE,
PENDING,
DO_SET,
DO_TO,
DO_WAIT,
DO_CALL,
}
export interface ITweenPlugin {
//resolveLerp(fromValue, toValue, ratio, allowOutOfBounds):any;
}
export interface TweenOptions {
loop?: number;
autoPlay?: boolean;
initFields?: string[];
clazz?: any;
fields?: string[];
}
/**
* 补间动画
* @param target
* @param override
* @param options
* @param plugins
*/
export function createTween(target: ScillaComponent, override = false, options?: TweenOptions, plugins = []) {
if (override) {
killTweens(target);
}
const tween = new Tween(target, options);
addTween(target, tween);
return tween;
}
/**
* 移除对象上所有的Tween实例
* @param target
*/
export function killTweens(target: ScillaComponent) {
let tweens: Tween[] = target['tweens'];
if (tweens) {
for (let tween of tweens) {
tween.stop();
}
tweens.splice(0);
}
}
function addTween(target, tween: Tween) {
let tweens: Tween[] = target['tweens'];
if (!tweens) {
tweens = target['tweens'] = [];
}
tweens.push(tween);
}
export class Tween extends HashObject {
target: ScillaComponent;
loop: number;
queue = [];
loopCounting: number = 0;
step: number;
status: STATUS = STATUS.IDLE;
t;
startTime;
plugins: ITweenPlugin[];
clazz;
fields;
autoPlay: boolean;
initProps: any;
fromProps: any;
toProps: any;
ease: Function;
duration: number;
constructor(target: ScillaComponent, options?: TweenOptions, plugins = []) {
super();
this.target = target;
this.loop = options ? options.loop : 0;
this.autoPlay = options ? (options.hasOwnProperty('autoPlay') ? options.autoPlay : true) : true;
this.clazz = options ? options.clazz : null;
this.fields = options ? options.fields : null;
this.plugins = plugins;
if (options && options.initFields && options.initFields.length > 0) {
this.initProps = this.getInitProps(options.initFields);
}
}
onUpdate = (t) => {
this.t = t;
switch (this.status) {
case STATUS.DO_TO:
var {target, startTime, fromProps, toProps, duration, ease, clazz, fields} = this;
var passTime = t - startTime;
let timeRatio = Math.min(1, passTime / duration);
let ratio = timeRatio;
if (ease) {
ratio = ease(ratio);
}
for (let key in fromProps) {
const toValue = toProps[key];
const fromValue = fromProps[key];
let currentValue;
if (timeRatio < 1) {
if (typeof toValue == 'object') {
currentValue = lerpObj(fromValue, toValue, ratio, clazz, fields || Object.keys(toValue), true);
} else {
currentValue = lerp(fromValue, toValue, ratio, true);
}
} else {
currentValue = toValue;
}
target[key] = currentValue;
if (timeRatio >= 1) {
this._doNextAction();
}
}
break;
case STATUS.DO_WAIT:
var {startTime, duration} = this;
var passTime = t - startTime;
if (passTime > duration) {
this._doNextAction();
}
break;
}
};
private getInitProps(fields) {
const props = {};
for (let field of fields) {
if (field in this.target) {
props[field] = this.target[field];
}
}
return props;
}
set(props) {
this.queue.push({action: 'set', props});
if (this.autoPlay) {
this._start();
}
return this;
}
to(props, duration?, ease?) {
this.queue.push({action: 'to', props, duration, ease});
if (this.autoPlay) {
this._start();
}
return this;
}
wait(duration) {
this.queue.push({action: 'wait', duration});
if (this.autoPlay) {
this._start();
}
return this;
}
call(func, thisObj?, params?) {
this.queue.push({action: 'call', func, thisObj, params});
if (this.autoPlay) {
this._start();
}
return this;
}
play(override = false, delay: number = 0, resetLoopCounting: boolean = true) {
if (override) {
killTweens(this.target);
}
if(delay > 0){
setTimeout(this._doPlay, delay, resetLoopCounting)
}else{
this._doPlay(resetLoopCounting);
}
}
private _doPlay=(resetLoopCounting)=>{
addTween(this.target, this);
this._start(resetLoopCounting);
};
stop() {
this.status = STATUS.IDLE;
this.target.cancelOnNextTick(this.onUpdate);
}
_set(props) {
this.status = STATUS.DO_SET;
injectProp(this.target, props);
this._doNextAction();
}
_to(props, duration, ease) {
this.status = STATUS.DO_TO;
this.startTime = this.t;
this.fromProps = {};
for (let key in props) {
this.fromProps[key] = this.target[key];
}
this.toProps = {};
injectProp(this.toProps, props);
this.ease = ease;
this.duration = duration;
//this.tween = annie.Tween.to(this.target, (duration / 1000) || 0, _props)
}
_wait(duration) {
this.status = STATUS.DO_WAIT;
this.startTime = this.t;
this.duration = duration;
/*setTimeout(() => {
this._doNextAction();
}, duration)*/
}
_call(func, thisObj, params) {
this.status = STATUS.DO_CALL;
func.apply(thisObj, params);
this._doNextAction();
}
_start(resetLoopCounting: boolean = true) {
this.status = STATUS.PENDING;
if(resetLoopCounting){
this.loopCounting = 0;
}
this.target.callOnNextTick(this._readyStart);
this.target.callOnNextTick(this.onUpdate, false);
}
_readyStart = (t) => {
this.t = t;
this._doStart();
};
_doStart() {
if (this.status == STATUS.IDLE) {
return;
}
this.step = 0;
this.loopCounting++;
if (this.loopCounting > 1 && this.initProps) {
injectProp(this.target, this.initProps);
}
this._doNextAction();
};
_doNextAction = () => {
if (this.step < this.queue.length) {
let action = this.queue[this.step++];
switch (action.action) {
case 'set':
this._set(action.props);
break;
case 'to':
if (action.duration > 0) {
this._to(action.props, action.duration, action.ease);
} else {
this._set(action.props);
}
break;
case 'wait':
this._wait(action.duration);
break;
case 'call':
this._call(action.func, action.thisObj, action.params);
break;
}
} else {
if (this.loop < 0) {
this._doStart();
} else if (this.loopCounting < this.loop) {
this._doStart();
} else {
this.status = STATUS.IDLE;
}
}
}
}
\ No newline at end of file
/**
* Created by rockyl on 2018/11/6.
*
*/
import {get, recycle, register} from "./ObjectPool";
const name = 'Vector2D';
register(name, function(){
return new Vector2D();
}, function(instance: Vector2D, x, y){
instance.setXY(x, y);
});
/**
* 创建2D矢量
* @param x
* @param y
*/
export function createVector2D(x = 0, y = 0){
return get(name, x, y);
}
/**
* 回收2D矢量
* @param target
*/
export function releaseVector2D(target){
recycle(name, target);
}
/**
* 2D矢量
*/
export default class Vector2D {
_x;
_y;
onChange;
public static get zero(): Vector2D{
return zero;
}
constructor(x = 0, y = 0, onChange?) {
this.onChange = onChange;
this._x = 0;
this._y = 0;
this.setXY(x, y);
}
get x(){
return this._x;
}
set x(v){
if(this._x !== v){
const old = this._x;
this._x = v;
this.onChange && this.onChange(v, 'x', old);
}
}
get y(){
return this._y;
}
set y(v){
if(this._y !== v){
const old = this._y;
this._y = v;
this.onChange && this.onChange(v, 'y', old);
}
}
setXY(x = 0, y = 0) {
this.x = x;
this.y = y;
return this;
}
copyFrom(v2) {
this.x = v2.x;
this.y = v2.y;
return this;
}
clone() {
return new Vector2D(this.x, this.y);
}
zero() {
this.x = 0;
this.y = 0;
return this;
}
get isZero() {
return this.x == 0 && this.y == 0;
}
normalize() {
let len = this.length;
if (len == 0) {
this.x = 1;
return this;
}
this.x /= len;
this.y /= len;
return this;
}
get isNormalized() {
return this.length == 1.0;
}
truncate(max) {
this.length = Math.min(max, this.length);
return this;
}
reverse() {
this.x = -this.x;
this.y = -this.y;
return this;
}
dotProd(v2) {
return this.x * v2.x + this.y * v2.y;
}
crossProd(v2) {
return this.x * v2.y - this.y * v2.x;
}
distSQ(v2) {
let dx = v2.x - this.x;
let dy = v2.y - this.y;
return dx * dx + dy * dy;
}
distance(v2) {
return Math.sqrt(this.distSQ(v2));
}
add(v2) {
this.x += v2.x;
this.y += v2.y;
return this;
}
subtract(v2) {
this.x -= v2.x;
this.y -= v2.y;
return this;
}
multiply(value) {
this.x *= value;
this.y *= value;
return this;
}
divide(value) {
this.x /= value;
this.y /= value;
return this;
}
set angle(value) {
this.radian = value * Math.PI / 180;
}
get angle() {
return this.radian * 180 / Math.PI;
}
set radian(value) {
let len = this.length;
this.setXY(Math.cos(value) * len, Math.sin(value) * len);
}
get radian() {
return Math.atan2(this.y, this.x);
}
equals(v2) {
return this.x == v2.x && this.y == v2.y;
}
set length(value) {
let a = this.radian;
this.setXY(Math.cos(a) * value, Math.sin(a) * value);
}
get length() {
return Math.sqrt(this.lengthSQ);
}
get lengthSQ() {
return this.x * this.x + this.y * this.y;
}
get slope() {
return this.y / this.x;
}
toString() {
return "[Vector2D (x:" + this.x + ", y:" + this.y + ")]";
}
static corner(v1, v2) {
return Math.acos(v1.dotProd(v2) / (v1.length * v2.length));
}
}
const zero = new Vector2D();
/**
* Created by rockyl on 2018/11/15.
*
* 支撑类库
*/
export {default as Bounds} from './Bounds'
export {default as Vector2D, createVector2D, releaseVector2D} from './Vector2D'
export {createTween, Tween} from './Tween'
export {default as Matrix} from './Matrix'
export {default as Size} from './Size'
//export {default as Color} from './Color'
export {default as LocalStorage} from './LocalStorage'
export {TextStyle} from './TextStyle'
export {default as EventEmitter} from './EventEmitter';
\ No newline at end of file
/**
* Created by rockyl on 2018/11/9.
*
* 装饰器
*/
/**
* 属性修改时触发
* @param onChange
*/
export function fieldChanged(onChange) {
return function (target: any, key: string) {
const privateKey = '_' + key;
Object.defineProperty(target, key, {
enumerable: true,
get: function () {
return this[privateKey];
},
set: function (v) {
const oldValue = this[privateKey];
if (oldValue !== v) {
this[privateKey] = v;
onChange.apply(this, [v, key, oldValue]);
}
}
})
}
}
/**
* 属性变脏时设置宿主的dirty属性为true
*/
export const dirtyFieldDetector = fieldChanged(
function (value, key, oldValue) {
this['dirty'] = true;
}
);
/**
* 属性变脏时触发onModify方法
*/
export const dirtyFieldTrigger = fieldChanged(
function (value, key, oldValue) {
this['onModify'] && this['onModify'](value, key, oldValue);
}
);
/**
* Created by rockyl on 2018/11/8.
*
* 缓动函数集合,使用不同的缓动函数使得动画按照对应的方程进行
*/
export enum Ease {
quadIn = 'quadIn',
quadOut = 'quadOut',
quadInOut = 'quadInOut',
cubicIn = 'cubicIn',
cubicOut = 'cubicOut',
cubicInOut = 'cubicInOut',
quartIn = 'quartIn',
quartOut = 'quartOut',
quartInOut = 'quartInOut',
quintIn = 'quintIn',
quintOut = 'quintOut',
quintInOut = 'quintInOut',
sineIn = 'sineIn',
sineOut = 'sineOut',
sineInOut = 'sineInOut',
backIn = 'backIn',
backOut = 'backOut',
backInOut = 'backInOut',
circIn = 'circIn',
circOut = 'circOut',
circInOut = 'circInOut',
bounceIn = 'bounceIn',
bounceOut = 'bounceOut',
bounceInOut = 'bounceInOut',
elasticIn = 'elasticIn',
elasticOut = 'elasticOut',
elasticInOut = 'elasticInOut',
}
export function get(amount) {
if (amount < -1) {
amount = -1;
}
if (amount > 1) {
amount = 1;
}
return function (t) {
if (amount == 0) {
return t;
}
if (amount < 0) {
return t * (t * -amount + 1 + amount);
}
return t * ((2 - t) * amount + (1 - amount));
}
}
export function getPowIn(pow) {
return function (t) {
return Math.pow(t, pow);
}
}
export function getPowOut(pow) {
return function (t) {
return 1 - Math.pow(1 - t, pow);
}
}
export function getPowInOut(pow) {
return function (t) {
if ((t *= 2) < 1) return 0.5 * Math.pow(t, pow);
return 1 - 0.5 * Math.abs(Math.pow(2 - t, pow));
}
}
export const quadIn = getPowIn(2);
export const quadOut = getPowOut(2);
export const quadInOut = getPowInOut(2);
export const cubicIn = getPowIn(3);
export const cubicOut = getPowOut(3);
export const cubicInOut = getPowInOut(3);
export const quartIn = getPowIn(4);
export const quartOut = getPowOut(4);
export const quartInOut = getPowInOut(4);
export const quintIn = getPowIn(5);
export const quintOut = getPowOut(5);
export const quintInOut = getPowInOut(5);
export function sineIn(t) {
return 1 - Math.cos(t * Math.PI / 2);
}
export function sineOut(t) {
return Math.sin(t * Math.PI / 2);
}
export function sineInOut(t) {
return -0.5 * (Math.cos(Math.PI * t) - 1)
}
export function getBackIn(amount) {
return function (t) {
return t * t * ((amount + 1) * t - amount);
}
}
export const backIn = getBackIn(1.7);
export function getBackOut(amount) {
return function (t) {
return (--t * t * ((amount + 1) * t + amount) + 1);
}
}
export const backOut = getBackOut(1.7);
export function getBackInOut(amount) {
amount *= 1.525;
return function (t) {
if ((t *= 2) < 1) return 0.5 * (t * t * ((amount + 1) * t - amount));
return 0.5 * ((t -= 2) * t * ((amount + 1) * t + amount) + 2);
}
}
export const backInOut = getBackInOut(1.7);
export function circIn(t) {
return -(Math.sqrt(1 - t * t) - 1);
}
export function circOut(t) {
return Math.sqrt(1 - (--t) * t);
}
export function circInOut(t) {
if ((t *= 2) < 1) {
return -0.5 * (Math.sqrt(1 - t * t) - 1);
}
return 0.5 * (Math.sqrt(1 - (t -= 2) * t) + 1);
}
export function bounceIn(t) {
return 1 - bounceOut(1 - t);
}
export function bounceOut(t) {
if (t < 1 / 2.75) {
return (7.5625 * t * t);
} else if (t < 2 / 2.75) {
return (7.5625 * (t -= 1.5 / 2.75) * t + 0.75);
} else if (t < 2.5 / 2.75) {
return (7.5625 * (t -= 2.25 / 2.75) * t + 0.9375);
} else {
return (7.5625 * (t -= 2.625 / 2.75) * t + 0.984375);
}
}
export function bounceInOut(t) {
if (t < 0.5) return bounceIn(t * 2) * .5;
return bounceOut(t * 2 - 1) * 0.5 + 0.5;
}
export function getElasticIn(amplitude, period) {
let pi2 = Math.PI * 2;
return function (t) {
if (t == 0 || t == 1) return t;
let s = period / pi2 * Math.asin(1 / amplitude);
return -(amplitude * Math.pow(2, 10 * (t -= 1)) * Math.sin((t - s) * pi2 / period));
}
}
export const elasticIn = getElasticIn(1, 0.3);
export function getElasticOut(amplitude, period) {
let pi2 = Math.PI * 2;
return function (t) {
if (t == 0 || t == 1) return t;
let s = period / pi2 * Math.asin(1 / amplitude);
return (amplitude * Math.pow(2, -10 * t) * Math.sin((t - s) * pi2 / period) + 1);
}
}
export const elasticOut = getElasticOut(1, 0.3);
export function getElasticInOut(amplitude, period) {
let pi2 = Math.PI * 2;
return function (t) {
let s = period / pi2 * Math.asin(1 / amplitude);
if ((t *= 2) < 1) return -0.5 * (amplitude * Math.pow(2, 10 * (t -= 1)) * Math.sin((t - s) * pi2 / period));
return amplitude * Math.pow(2, -10 * (t -= 1)) * Math.sin((t - s) * pi2 / period) * 0.5 + 1;
}
}
export const elasticInOut = getElasticInOut(1, 0.3 * 1.5);
/**
* Created by rockyl on 2018/11/16.
*/
import * as decorators from './decorators'
import * as ease from './ease'
import * as math from './math'
import * as utils from './utils'
import * as timeUtils from './time'
import {Ease} from "./ease";
export {
decorators,
ease,
Ease,
math,
utils,
timeUtils,
}
/**
* Created by rockyl on 2018/11/8.
*
* 数学工具
*/
/**
* 线性插值
* @param begin number
* @param end number
* @param t number
* @param allowOutOfBounds
* @return number
*/
export function lerp(begin, end, t, allowOutOfBounds = false) {
const type = typeof begin;
if (type !== typeof end) {
console.error('begin and end need same type')
}
if (!allowOutOfBounds) {
t = Math.max(0, Math.min(1, t));
}
let sign = end - begin;
sign = sign > 0 ? 1 : (sign < 0 ? -1 : 0);
const distance = Math.abs(end - begin);
return begin + distance * t * sign;
}
/**
* 线性插值对象
* @param begin
* @param end
* @param t
* @param clazz
* @param fields
* @param allowOutOfBounds
* @return
*/
export function lerpObj(begin, end, t, clazz, fields, allowOutOfBounds = false) {
const type = typeof begin;
if (type !== typeof end) {
console.error('begin and end need same type')
}
const temp = new clazz();
for (let field of fields) {
temp[field] = lerp(begin[field], end[field], t, allowOutOfBounds);
}
return temp;
}
/**
* 随机生成一个整数
* @param max
* @param min
*/
export function makeRandomInt(max: number, min: number = 0): number {
return Math.floor(Math.random() * (max - min)) + min;
}
/**
* 打乱一个数组
* @param arr
* @returns {any}
*/
export function mixArray(arr: any): Array<any> {
for (let i: number = 0, len: number = Math.round(arr.length / 2); i < len; i++) {
let a: number = makeRandomInt(arr.length);
let b: number = makeRandomInt(arr.length);
let temp = arr[a];
arr[a] = arr[b];
arr[b] = temp;
}
return arr;
}
/**
* Created by rockyl on 2019-01-01.
*/
import {format as stringFormat, supplement} from './utils'
/**
* 时间戳转日期
* @param ts
*/
export function ts2Date(ts) {
let newDate:Date = new Date();
newDate.setTime(ts);
return newDate;
}
export function dateToDateString(date:Date, format:string = '{0}/{1}/{2}'):string{
return stringFormat(format, date.getFullYear(), supplement(date.getMonth() + 1, 2), supplement(date.getDate(), 2))
}
export function dateToTimeString(date:Date, format:string = '{0}:{1}:{2}'):string{
return stringFormat(format, supplement(date.getHours(), 2), supplement(date.getMinutes(), 2), supplement(date.getSeconds(), 2))
}
export function dateToString(date: Date, dayFormat, timeFormat){
return dateToDateString(date, dayFormat) + dateToTimeString(date, timeFormat);
}
export function tsToTimeString(ts, format:string = '{0}:{1}:{2}'):string{
let date = ts2Date(ts);
return stringFormat(format, supplement(date.getHours(), 2), supplement(date.getMinutes(), 2), supplement(date.getSeconds(), 2))
}
export function secondFormat(second:number, format:string = '{2}:{1}:{0}', placeZero:boolean = true):string {
let ss:any = second % 60;
let mm:any = Math.floor(second / 60) % 60;
let hh:any = Math.floor(second / 3600) % 24;
let dd:any = Math.floor(second / 3600 / 24);
if (placeZero) {
ss = supplement(ss, 2);
mm = supplement(mm, 2);
hh = supplement(hh, 2);
dd = supplement(dd, 2);
}
return stringFormat(format, ss, mm, hh, dd);
}
/**
* Created by rockyl on 2018/11/9.
*
* 常用工具
*/
export function injectProp(target: any, data?: any, callback?: Function, ignoreMethod: boolean = true, ignoreNull: boolean = true): boolean {
if (!target || !data) {
return false;
}
let result = true;
for (let key in data) {
let value: any = data[key];
if ((!ignoreMethod || typeof value != 'function') && (!ignoreNull || value != null)) {
if (callback) {
callback(target, key, value);
} else {
target[key] = value;
}
}
}
return result;
}
export function objectStringify(obj) {
if (!obj) {
return '';
}
let arr = [];
for (let key in obj) {
arr.push(key + '=' + obj[key]);
}
return arr.join('&');
}
export function waitPromise(duration): Promise<void> {
return new Promise(resolve => {
setTimeout(resolve, duration);
});
}
export function format(formatStr: string, ...params): string {
return formatApply(formatStr, params);
}
export function formatApply(formatStr: string, params: any[]): string {
let result: string = formatStr;
for (let i = 0, len = params.length; i < len; i++) {
let reg = new RegExp("\\{" + i + "\\}", 'g');
result = result.replace(reg, params[i]);
}
return result;
}
const zeros: Array<string> = [
"0",
"00",
"000",
"0000",
"00000",
"000000",
"0000000",
"00000000",
"000000000",
"0000000000"
];
export function supplement(value: number, count: number): string {
let index = count - value.toString().length - 1;
if (index < 0) {
return value.toString();
}
return zeros[index] + value;
}
{
"compilerOptions": {
"target": "es5",
"experimentalDecorators": true,
"sourceMap": true,
"declarationDir": "./types",
"declaration": true,
"lib": [
"es5",
"es6",
"dom",
"es2015.promise"
]
},
"include": [
"src",
"libs"
]
}
\ No newline at end of file
# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.
# yarn lockfile v1
"@babel/code-frame@^7.0.0":
version "7.0.0"
resolved "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.0.0.tgz#06e2ab19bdb535385559aabb5ba59729482800f8"
integrity sha512-OfC2uemaknXr87bdLUkWog7nYuliM9Ij5HUcajsVcMCpQrcLmtxRbVFTIqmcSkSeYRBFBRxs2FiUqFJDLdiebA==
dependencies:
"@babel/highlight" "^7.0.0"
"@babel/highlight@^7.0.0":
version "7.0.0"
resolved "https://registry.npmjs.org/@babel/highlight/-/highlight-7.0.0.tgz#f710c38c8d458e6dd9a201afb637fcb781ce99e4"
integrity sha512-UFMC4ZeFC48Tpvj7C8UgLvtkaUuovQX+5xNWrsIoMG8o2z+XFKjKaN9iVmS84dPwVN00W4wPmqvYoZF3EGAsfw==
dependencies:
chalk "^2.0.0"
esutils "^2.0.2"
js-tokens "^4.0.0"
"@types/estree@0.0.39":
version "0.0.39"
resolved "https://registry.npmjs.org/@types/estree/-/estree-0.0.39.tgz#e177e699ee1b8c22d23174caaa7422644389509f"
integrity sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw==
"@types/node@*":
version "10.12.18"
resolved "https://registry.npmjs.org/@types/node/-/node-10.12.18.tgz#1d3ca764718915584fcd9f6344621b7672665c67"
integrity sha512-fh+pAqt4xRzPfqA6eh3Z2y6fyZavRIumvjhaCL753+TVkGKGhpPeyrJG2JftD0T9q4GF00KjefsQ+PQNDdWQaQ==
ansi-styles@^3.2.1:
version "3.2.1"
resolved "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d"
integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==
dependencies:
color-convert "^1.9.0"
arr-diff@^2.0.0:
version "2.0.0"
resolved "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz#8f3b827f955a8bd669697e4a4256ac3ceae356cf"
integrity sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=
dependencies:
arr-flatten "^1.0.1"
arr-flatten@^1.0.1:
version "1.1.0"
resolved "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz#36048bbff4e7b47e136644316c99669ea5ae91f1"
integrity sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==
array-unique@^0.2.1:
version "0.2.1"
resolved "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz#a1d97ccafcbc2625cc70fadceb36a50c58b01a53"
integrity sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=
braces@^1.8.2:
version "1.8.5"
resolved "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz#ba77962e12dff969d6b76711e914b737857bf6a7"
integrity sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=
dependencies:
expand-range "^1.8.1"
preserve "^0.2.0"
repeat-element "^1.1.2"
builtin-modules@^2.0.0:
version "2.0.0"
resolved "https://registry.npmjs.org/builtin-modules/-/builtin-modules-2.0.0.tgz#60b7ef5ae6546bd7deefa74b08b62a43a232648e"
integrity sha512-3U5kUA5VPsRUA3nofm/BXX7GVHKfxz0hOBAPxXrIvHzlDRkQVqEn6yi8QJegxl4LzOHLdvb7XF5dVawa/VVYBg==
chalk@^2.0.0:
version "2.4.2"
resolved "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz#cd42541677a54333cf541a49108c1432b44c9424"
integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==
dependencies:
ansi-styles "^3.2.1"
escape-string-regexp "^1.0.5"
supports-color "^5.3.0"
color-convert@^1.9.0:
version "1.9.3"
resolved "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8"
integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==
dependencies:
color-name "1.1.3"
color-name@1.1.3:
version "1.1.3"
resolved "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25"
integrity sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=
commander@~2.17.1:
version "2.17.1"
resolved "https://registry.npmjs.org/commander/-/commander-2.17.1.tgz#bd77ab7de6de94205ceacc72f1716d29f20a77bf"
integrity sha512-wPMUt6FnH2yzG95SA6mzjQOEKUU3aLaDEmzs1ti+1E9h+CsrZghRlqEM/EJ4KscsQVG8uNN4uVreUeT8+drlgg==
core-util-is@~1.0.0:
version "1.0.2"
resolved "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz#b5fd54220aa2bc5ab57aab7140c940754503c1a7"
integrity sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=
escape-string-regexp@^1.0.5:
version "1.0.5"
resolved "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4"
integrity sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=
estree-walker@^0.5.2:
version "0.5.2"
resolved "https://registry.npmjs.org/estree-walker/-/estree-walker-0.5.2.tgz#d3850be7529c9580d815600b53126515e146dd39"
integrity sha512-XpCnW/AE10ws/kDAs37cngSkvgIR8aN3G0MS85m7dUpuK2EREo9VJ00uvw6Dg/hXEpfsE1I1TvJOJr+Z+TL+ig==
esutils@^2.0.2:
version "2.0.2"
resolved "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz#0abf4f1caa5bcb1f7a9d8acc6dea4faaa04bac9b"
integrity sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=
expand-brackets@^0.1.4:
version "0.1.5"
resolved "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz#df07284e342a807cd733ac5af72411e581d1177b"
integrity sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=
dependencies:
is-posix-bracket "^0.1.0"
expand-range@^1.8.1:
version "1.8.2"
resolved "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz#a299effd335fe2721ebae8e257ec79644fc85337"
integrity sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=
dependencies:
fill-range "^2.1.0"
extglob@^0.3.1:
version "0.3.2"
resolved "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz#2e18ff3d2f49ab2765cec9023f011daa8d8349a1"
integrity sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=
dependencies:
is-extglob "^1.0.0"
filename-regex@^2.0.0:
version "2.0.1"
resolved "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz#c1c4b9bee3e09725ddb106b75c1e301fe2f18b26"
integrity sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=
fill-range@^2.1.0:
version "2.2.4"
resolved "https://registry.npmjs.org/fill-range/-/fill-range-2.2.4.tgz#eb1e773abb056dcd8df2bfdf6af59b8b3a936565"
integrity sha512-cnrcCbj01+j2gTG921VZPnHbjmdAf8oQV/iGeV2kZxGSyfYjjTyY79ErsK1WJWMpw6DaApEX72binqJE+/d+5Q==
dependencies:
is-number "^2.1.0"
isobject "^2.0.0"
randomatic "^3.0.0"
repeat-element "^1.1.2"
repeat-string "^1.5.2"
for-in@^1.0.1:
version "1.0.2"
resolved "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz#81068d295a8142ec0ac726c6e2200c30fb6d5e80"
integrity sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=
for-own@^0.1.4:
version "0.1.5"
resolved "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz#5265c681a4f294dabbf17c9509b6763aa84510ce"
integrity sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=
dependencies:
for-in "^1.0.1"
fs-extra@7.0.0:
version "7.0.0"
resolved "https://registry.npmjs.org/fs-extra/-/fs-extra-7.0.0.tgz#8cc3f47ce07ef7b3593a11b9fb245f7e34c041d6"
integrity sha512-EglNDLRpmaTWiD/qraZn6HREAEAHJcJOmxNEYwq6xeMKnVMAy3GUcFB+wXt2C6k4CNvB/mP1y/U3dzvKKj5OtQ==
dependencies:
graceful-fs "^4.1.2"
jsonfile "^4.0.0"
universalify "^0.1.0"
glob-base@^0.3.0:
version "0.3.0"
resolved "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz#dbb164f6221b1c0b1ccf82aea328b497df0ea3c4"
integrity sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=
dependencies:
glob-parent "^2.0.0"
is-glob "^2.0.0"
glob-parent@^2.0.0:
version "2.0.0"
resolved "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz#81383d72db054fcccf5336daa902f182f6edbb28"
integrity sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=
dependencies:
is-glob "^2.0.0"
graceful-fs@^4.1.2, graceful-fs@^4.1.6:
version "4.1.15"
resolved "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.15.tgz#ffb703e1066e8a0eeaa4c8b80ba9253eeefbfb00"
integrity sha512-6uHUhOPEBgQ24HM+r6b/QwWfZq+yiFcipKFrOFiBEnWdy5sdzYoi+pJeQaPI5qOLRFqWmAXUPQNsielzdLoecA==
has-flag@^3.0.0:
version "3.0.0"
resolved "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd"
integrity sha1-tdRU3CGZriJWmfNGfloH87lVuv0=
inherits@~2.0.3:
version "2.0.3"
resolved "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz#633c2c83e3da42a502f52466022480f4208261de"
integrity sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=
is-buffer@^1.1.5:
version "1.1.6"
resolved "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz#efaa2ea9daa0d7ab2ea13a97b2b8ad51fefbe8be"
integrity sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==
is-dotfile@^1.0.0:
version "1.0.3"
resolved "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz#a6a2f32ffd2dfb04f5ca25ecd0f6b83cf798a1e1"
integrity sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=
is-equal-shallow@^0.1.3:
version "0.1.3"
resolved "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz#2238098fc221de0bcfa5d9eac4c45d638aa1c534"
integrity sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=
dependencies:
is-primitive "^2.0.0"
is-extendable@^0.1.1:
version "0.1.1"
resolved "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz#62b110e289a471418e3ec36a617d472e301dfc89"
integrity sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=
is-extglob@^1.0.0:
version "1.0.0"
resolved "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz#ac468177c4943405a092fc8f29760c6ffc6206c0"
integrity sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=
is-glob@^2.0.0, is-glob@^2.0.1:
version "2.0.1"
resolved "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz#d096f926a3ded5600f3fdfd91198cb0888c2d863"
integrity sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=
dependencies:
is-extglob "^1.0.0"
is-module@^1.0.0:
version "1.0.0"
resolved "https://registry.npmjs.org/is-module/-/is-module-1.0.0.tgz#3258fb69f78c14d5b815d664336b4cffb6441591"
integrity sha1-Mlj7afeMFNW4FdZkM2tM/7ZEFZE=
is-number@^2.1.0:
version "2.1.0"
resolved "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz#01fcbbb393463a548f2f466cce16dece49db908f"
integrity sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=
dependencies:
kind-of "^3.0.2"
is-number@^4.0.0:
version "4.0.0"
resolved "https://registry.npmjs.org/is-number/-/is-number-4.0.0.tgz#0026e37f5454d73e356dfe6564699867c6a7f0ff"
integrity sha512-rSklcAIlf1OmFdyAqbnWTLVelsQ58uvZ66S/ZyawjWqIviTWCjg2PzVGw8WUA+nNuPTqb4wgA+NszrJ+08LlgQ==
is-posix-bracket@^0.1.0:
version "0.1.1"
resolved "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz#3334dc79774368e92f016e6fbc0a88f5cd6e6bc4"
integrity sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=
is-primitive@^2.0.0:
version "2.0.0"
resolved "https://registry.npmjs.org/is-primitive/-/is-primitive-2.0.0.tgz#207bab91638499c07b2adf240a41a87210034575"
integrity sha1-IHurkWOEmcB7Kt8kCkGochADRXU=
isarray@1.0.0, isarray@~1.0.0:
version "1.0.0"
resolved "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11"
integrity sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=
isobject@^2.0.0:
version "2.1.0"
resolved "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz#f065561096a3f1da2ef46272f815c840d87e0c89"
integrity sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=
dependencies:
isarray "1.0.0"
jest-worker@^23.2.0:
version "23.2.0"
resolved "https://registry.npmjs.org/jest-worker/-/jest-worker-23.2.0.tgz#faf706a8da36fae60eb26957257fa7b5d8ea02b9"
integrity sha1-+vcGqNo2+uYOsmlXJX+ntdjqArk=
dependencies:
merge-stream "^1.0.1"
js-tokens@^4.0.0:
version "4.0.0"
resolved "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz#19203fb59991df98e3a287050d4647cdeaf32499"
integrity sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==
jsonfile@^4.0.0:
version "4.0.0"
resolved "https://registry.npmjs.org/jsonfile/-/jsonfile-4.0.0.tgz#8771aae0799b64076b76640fca058f9c10e33ecb"
integrity sha1-h3Gq4HmbZAdrdmQPygWPnBDjPss=
optionalDependencies:
graceful-fs "^4.1.6"
kind-of@^3.0.2:
version "3.2.2"
resolved "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz#31ea21a734bab9bbb0f32466d893aea51e4a3c64"
integrity sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=
dependencies:
is-buffer "^1.1.5"
kind-of@^6.0.0:
version "6.0.2"
resolved "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz#01146b36a6218e64e58f3a8d66de5d7fc6f6d051"
integrity sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==
magic-string@^0.25.1:
version "0.25.1"
resolved "https://registry.npmjs.org/magic-string/-/magic-string-0.25.1.tgz#b1c248b399cd7485da0fe7385c2fc7011843266e"
integrity sha512-sCuTz6pYom8Rlt4ISPFn6wuFodbKMIHUMv4Qko9P17dpxb7s52KJTmRuZZqHdGmLCK9AOcDare039nRIcfdkEg==
dependencies:
sourcemap-codec "^1.4.1"
math-random@^1.0.1:
version "1.0.1"
resolved "https://registry.npmjs.org/math-random/-/math-random-1.0.1.tgz#8b3aac588b8a66e4975e3cdea67f7bb329601fac"
integrity sha1-izqsWIuKZuSXXjzepn97sylgH6w=
merge-stream@^1.0.1:
version "1.0.1"
resolved "https://registry.npmjs.org/merge-stream/-/merge-stream-1.0.1.tgz#4041202d508a342ba00174008df0c251b8c135e1"
integrity sha1-QEEgLVCKNCugAXQAjfDCUbjBNeE=
dependencies:
readable-stream "^2.0.1"
micromatch@^2.3.11:
version "2.3.11"
resolved "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz#86677c97d1720b363431d04d0d15293bd38c1565"
integrity sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=
dependencies:
arr-diff "^2.0.0"
array-unique "^0.2.1"
braces "^1.8.2"
expand-brackets "^0.1.4"
extglob "^0.3.1"
filename-regex "^2.0.0"
is-extglob "^1.0.0"
is-glob "^2.0.1"
kind-of "^3.0.2"
normalize-path "^2.0.1"
object.omit "^2.0.0"
parse-glob "^3.0.4"
regex-cache "^0.4.2"
normalize-path@^2.0.1:
version "2.1.1"
resolved "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz#1ab28b556e198363a8c1a6f7e6fa20137fe6aed9"
integrity sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=
dependencies:
remove-trailing-separator "^1.0.1"
object.omit@^2.0.0:
version "2.0.1"
resolved "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz#1a9c744829f39dbb858c76ca3579ae2a54ebd1fa"
integrity sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=
dependencies:
for-own "^0.1.4"
is-extendable "^0.1.1"
parse-glob@^3.0.4:
version "3.0.4"
resolved "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz#b2c376cfb11f35513badd173ef0bb6e3a388391c"
integrity sha1-ssN2z7EfNVE7rdFz7wu246OIORw=
dependencies:
glob-base "^0.3.0"
is-dotfile "^1.0.0"
is-extglob "^1.0.0"
is-glob "^2.0.0"
path-parse@^1.0.5, path-parse@^1.0.6:
version "1.0.6"
resolved "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz#d62dbb5679405d72c4737ec58600e9ddcf06d24c"
integrity sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==
preserve@^0.2.0:
version "0.2.0"
resolved "https://registry.npmjs.org/preserve/-/preserve-0.2.0.tgz#815ed1f6ebc65926f865b310c0713bcb3315ce4b"
integrity sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=
process-nextick-args@~2.0.0:
version "2.0.0"
resolved "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz#a37d732f4271b4ab1ad070d35508e8290788ffaa"
integrity sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==
randomatic@^3.0.0:
version "3.1.1"
resolved "https://registry.npmjs.org/randomatic/-/randomatic-3.1.1.tgz#b776efc59375984e36c537b2f51a1f0aff0da1ed"
integrity sha512-TuDE5KxZ0J461RVjrJZCJc+J+zCkTb1MbH9AQUq68sMhOMcy9jLcb3BrZKgp9q9Ncltdg4QVqWrH02W2EFFVYw==
dependencies:
is-number "^4.0.0"
kind-of "^6.0.0"
math-random "^1.0.1"
readable-stream@^2.0.1:
version "2.3.6"
resolved "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz#b11c27d88b8ff1fbe070643cf94b0c79ae1b0aaf"
integrity sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==
dependencies:
core-util-is "~1.0.0"
inherits "~2.0.3"
isarray "~1.0.0"
process-nextick-args "~2.0.0"
safe-buffer "~5.1.1"
string_decoder "~1.1.1"
util-deprecate "~1.0.1"
regex-cache@^0.4.2:
version "0.4.4"
resolved "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz#75bdc58a2a1496cec48a12835bc54c8d562336dd"
integrity sha512-nVIZwtCjkC9YgvWkpM55B5rBhBYRZhAaJbgcFYXXsHnbZ9UZI9nnVWYZpBlCqv9ho2eZryPnWrZGsOdPwVWXWQ==
dependencies:
is-equal-shallow "^0.1.3"
remove-trailing-separator@^1.0.1:
version "1.1.0"
resolved "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz#c24bce2a283adad5bc3f58e0d48249b92379d8ef"
integrity sha1-wkvOKig62tW8P1jg1IJJuSN52O8=
repeat-element@^1.1.2:
version "1.1.3"
resolved "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.3.tgz#782e0d825c0c5a3bb39731f84efee6b742e6b1ce"
integrity sha512-ahGq0ZnV5m5XtZLMb+vP76kcAM5nkLqk0lpqAuojSKGgQtn4eRi4ZZGm2olo2zKFH+sMsWaqOCW1dqAnOru72g==
repeat-string@^1.5.2:
version "1.6.1"
resolved "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz#8dcae470e1c88abc2d600fff4a776286da75e637"
integrity sha1-jcrkcOHIirwtYA//Sndihtp15jc=
resolve@1.8.1:
version "1.8.1"
resolved "https://registry.npmjs.org/resolve/-/resolve-1.8.1.tgz#82f1ec19a423ac1fbd080b0bab06ba36e84a7a26"
integrity sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==
dependencies:
path-parse "^1.0.5"
resolve@^1.1.6, resolve@^1.8.1:
version "1.9.0"
resolved "https://registry.npmjs.org/resolve/-/resolve-1.9.0.tgz#a14c6fdfa8f92a7df1d996cb7105fa744658ea06"
integrity sha512-TZNye00tI67lwYvzxCxHGjwTNlUV70io54/Ed4j6PscB8xVfuBJpRenI/o6dVk0cY0PYTY27AgCoGGxRnYuItQ==
dependencies:
path-parse "^1.0.6"
rollup-plugin-commonjs@^9.2.0:
version "9.2.0"
resolved "https://registry.npmjs.org/rollup-plugin-commonjs/-/rollup-plugin-commonjs-9.2.0.tgz#4604e25069e0c78a09e08faa95dc32dec27f7c89"
integrity sha512-0RM5U4Vd6iHjL6rLvr3lKBwnPsaVml+qxOGaaNUWN1lSq6S33KhITOfHmvxV3z2vy9Mk4t0g4rNlVaJJsNQPWA==
dependencies:
estree-walker "^0.5.2"
magic-string "^0.25.1"
resolve "^1.8.1"
rollup-pluginutils "^2.3.3"
rollup-plugin-node-resolve@^3.4.0:
version "3.4.0"
resolved "https://registry.npmjs.org/rollup-plugin-node-resolve/-/rollup-plugin-node-resolve-3.4.0.tgz#908585eda12e393caac7498715a01e08606abc89"
integrity sha512-PJcd85dxfSBWih84ozRtBkB731OjXk0KnzN0oGp7WOWcarAFkVa71cV5hTJg2qpVsV2U8EUwrzHP3tvy9vS3qg==
dependencies:
builtin-modules "^2.0.0"
is-module "^1.0.0"
resolve "^1.1.6"
rollup-plugin-typescript2@^0.18.0:
version "0.18.1"
resolved "https://registry.npmjs.org/rollup-plugin-typescript2/-/rollup-plugin-typescript2-0.18.1.tgz#921865828080a254c088c6bc181ca654e5ef73c6"
integrity sha512-aR2m5NCCAUV/KpcKgCWX6Giy8rTko9z92b5t0NX9eZyjOftCvcdDFa1C9Ze/9yp590hnRymr5hG0O9SAXi1oUg==
dependencies:
fs-extra "7.0.0"
resolve "1.8.1"
rollup-pluginutils "2.3.3"
tslib "1.9.3"
rollup-plugin-uglify@^6.0.0:
version "6.0.0"
resolved "https://registry.npmjs.org/rollup-plugin-uglify/-/rollup-plugin-uglify-6.0.0.tgz#15aa8919e5cdc63b7cfc9319c781788b40084ce4"
integrity sha512-XtzZd159QuOaXNvcxyBcbUCSoBsv5YYWK+7ZwUyujSmISst8avRfjWlp7cGu8T2O52OJnpEBvl+D4WLV1k1iQQ==
dependencies:
"@babel/code-frame" "^7.0.0"
jest-worker "^23.2.0"
serialize-javascript "^1.5.0"
uglify-js "^3.4.9"
rollup-pluginutils@2.3.3, rollup-pluginutils@^2.3.3:
version "2.3.3"
resolved "https://registry.npmjs.org/rollup-pluginutils/-/rollup-pluginutils-2.3.3.tgz#3aad9b1eb3e7fe8262820818840bf091e5ae6794"
integrity sha512-2XZwja7b6P5q4RZ5FhyX1+f46xi1Z3qBKigLRZ6VTZjwbN0K1IFGMlwm06Uu0Emcre2Z63l77nq/pzn+KxIEoA==
dependencies:
estree-walker "^0.5.2"
micromatch "^2.3.11"
rollup@^0.66.6:
version "0.66.6"
resolved "https://registry.npmjs.org/rollup/-/rollup-0.66.6.tgz#ce7d6185beb7acea644ce220c25e71ae03275482"
integrity sha512-J7/SWanrcb83vfIHqa8+aVVGzy457GcjA6GVZEnD0x2u4OnOd0Q1pCrEoNe8yLwM6z6LZP02zBT2uW0yh5TqOw==
dependencies:
"@types/estree" "0.0.39"
"@types/node" "*"
safe-buffer@~5.1.0, safe-buffer@~5.1.1:
version "5.1.2"
resolved "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d"
integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==
serialize-javascript@^1.5.0:
version "1.6.1"
resolved "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-1.6.1.tgz#4d1f697ec49429a847ca6f442a2a755126c4d879"
integrity sha512-A5MOagrPFga4YaKQSWHryl7AXvbQkEqpw4NNYMTNYUNV51bA8ABHgYFpqKx+YFFrw59xMV1qGH1R4AgoNIVgCw==
source-map@~0.6.1:
version "0.6.1"
resolved "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263"
integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==
sourcemap-codec@^1.4.1:
version "1.4.4"
resolved "https://registry.npmjs.org/sourcemap-codec/-/sourcemap-codec-1.4.4.tgz#c63ea927c029dd6bd9a2b7fa03b3fec02ad56e9f"
integrity sha512-CYAPYdBu34781kLHkaW3m6b/uUSyMOC2R61gcYMWooeuaGtjof86ZA/8T+qVPPt7np1085CR9hmMGrySwEc8Xg==
string_decoder@~1.1.1:
version "1.1.1"
resolved "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8"
integrity sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==
dependencies:
safe-buffer "~5.1.0"
supports-color@^5.3.0:
version "5.5.0"
resolved "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f"
integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==
dependencies:
has-flag "^3.0.0"
tslib@1.9.3, tslib@^1.9.3:
version "1.9.3"
resolved "https://registry.npmjs.org/tslib/-/tslib-1.9.3.tgz#d7e4dd79245d85428c4d7e4822a79917954ca286"
integrity sha512-4krF8scpejhaOgqzBEcGM7yDIEfi0/8+8zDRZhNZZ2kjmHJ4hv3zCbQWxoJGz1iw5U0Jl0nma13xzHXcncMavQ==
typescript@^3.1.6:
version "3.2.2"
resolved "https://registry.npmjs.org/typescript/-/typescript-3.2.2.tgz#fe8101c46aa123f8353523ebdcf5730c2ae493e5"
integrity sha512-VCj5UiSyHBjwfYacmDuc/NOk4QQixbE+Wn7MFJuS0nRuPQbof132Pw4u53dm264O8LPc2MVsc7RJNml5szurkg==
uglify-js@^3.4.9:
version "3.4.9"
resolved "https://registry.npmjs.org/uglify-js/-/uglify-js-3.4.9.tgz#af02f180c1207d76432e473ed24a28f4a782bae3"
integrity sha512-8CJsbKOtEbnJsTyv6LE6m6ZKniqMiFWmm9sRbopbkGs3gMPPfd3Fh8iIA4Ykv5MgaTbqHr4BaoGLJLZNhsrW1Q==
dependencies:
commander "~2.17.1"
source-map "~0.6.1"
universalify@^0.1.0:
version "0.1.2"
resolved "https://registry.npmjs.org/universalify/-/universalify-0.1.2.tgz#b646f69be3942dabcecc9d6639c80dc105efaa66"
integrity sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg==
util-deprecate@~1.0.1:
version "1.0.2"
resolved "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf"
integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment