UNPKG

flamingo-ui

Version:

火烈鸟UI组件库

1,136 lines 485 kB
(function(global2, factory) { typeof exports === "object" && typeof module !== "undefined" ? factory(exports, require("vue")) : typeof define === "function" && define.amd ? define(["exports", "vue"], factory) : (global2 = typeof globalThis !== "undefined" ? globalThis : global2 || self, factory(global2["flamingo-ui"] = {}, global2.Vue)); })(this, function(exports2, vue) { "use strict"; var commonjsGlobal = typeof globalThis !== "undefined" ? globalThis : typeof window !== "undefined" ? window : typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : {}; function getDefaultExportFromCjs(x) { return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, "default") ? x["default"] : x; } var matterExports = {}; var matter = { get exports() { return matterExports; }, set exports(v) { matterExports = v; } }; /*! * matter-js 0.19.0 by @liabru * http://brm.io/matter-js/ * License MIT * * The MIT License (MIT) * * Copyright (c) Liam Brummitt and contributors. * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * THE SOFTWARE. */ (function(module2, exports3) { (function webpackUniversalModuleDefinition(root, factory) { module2.exports = factory(); })(commonjsGlobal, function() { return ( /******/ function(modules) { var installedModules = {}; function __webpack_require__(moduleId) { if (installedModules[moduleId]) { return installedModules[moduleId].exports; } var module3 = installedModules[moduleId] = { /******/ i: moduleId, /******/ l: false, /******/ exports: {} /******/ }; modules[moduleId].call(module3.exports, module3, module3.exports, __webpack_require__); module3.l = true; return module3.exports; } __webpack_require__.m = modules; __webpack_require__.c = installedModules; __webpack_require__.d = function(exports4, name2, getter) { if (!__webpack_require__.o(exports4, name2)) { Object.defineProperty(exports4, name2, { enumerable: true, get: getter }); } }; __webpack_require__.r = function(exports4) { if (typeof Symbol !== "undefined" && Symbol.toStringTag) { Object.defineProperty(exports4, Symbol.toStringTag, { value: "Module" }); } Object.defineProperty(exports4, "__esModule", { value: true }); }; __webpack_require__.t = function(value, mode) { if (mode & 1) value = __webpack_require__(value); if (mode & 8) return value; if (mode & 4 && typeof value === "object" && value && value.__esModule) return value; var ns = /* @__PURE__ */ Object.create(null); __webpack_require__.r(ns); Object.defineProperty(ns, "default", { enumerable: true, value }); if (mode & 2 && typeof value != "string") for (var key in value) __webpack_require__.d(ns, key, function(key2) { return value[key2]; }.bind(null, key)); return ns; }; __webpack_require__.n = function(module3) { var getter = module3 && module3.__esModule ? ( /******/ function getDefault() { return module3["default"]; } ) : ( /******/ function getModuleExports() { return module3; } ); __webpack_require__.d(getter, "a", getter); return getter; }; __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); }; __webpack_require__.p = ""; return __webpack_require__(__webpack_require__.s = 20); }([ /* 0 */ /***/ function(module3, exports4) { var Common = {}; module3.exports = Common; (function() { Common._baseDelta = 1e3 / 60; Common._nextId = 0; Common._seed = 0; Common._nowStartTime = +new Date(); Common._warnedOnce = {}; Common._decomp = null; Common.extend = function(obj, deep) { var argsStart, deepClone; if (typeof deep === "boolean") { argsStart = 2; deepClone = deep; } else { argsStart = 1; deepClone = true; } for (var i = argsStart; i < arguments.length; i++) { var source = arguments[i]; if (source) { for (var prop in source) { if (deepClone && source[prop] && source[prop].constructor === Object) { if (!obj[prop] || obj[prop].constructor === Object) { obj[prop] = obj[prop] || {}; Common.extend(obj[prop], deepClone, source[prop]); } else { obj[prop] = source[prop]; } } else { obj[prop] = source[prop]; } } } } return obj; }; Common.clone = function(obj, deep) { return Common.extend({}, deep, obj); }; Common.keys = function(obj) { if (Object.keys) return Object.keys(obj); var keys = []; for (var key in obj) keys.push(key); return keys; }; Common.values = function(obj) { var values = []; if (Object.keys) { var keys = Object.keys(obj); for (var i = 0; i < keys.length; i++) { values.push(obj[keys[i]]); } return values; } for (var key in obj) values.push(obj[key]); return values; }; Common.get = function(obj, path, begin, end) { path = path.split(".").slice(begin, end); for (var i = 0; i < path.length; i += 1) { obj = obj[path[i]]; } return obj; }; Common.set = function(obj, path, val, begin, end) { var parts = path.split(".").slice(begin, end); Common.get(obj, path, 0, -1)[parts[parts.length - 1]] = val; return val; }; Common.shuffle = function(array) { for (var i = array.length - 1; i > 0; i--) { var j = Math.floor(Common.random() * (i + 1)); var temp = array[i]; array[i] = array[j]; array[j] = temp; } return array; }; Common.choose = function(choices) { return choices[Math.floor(Common.random() * choices.length)]; }; Common.isElement = function(obj) { if (typeof HTMLElement !== "undefined") { return obj instanceof HTMLElement; } return !!(obj && obj.nodeType && obj.nodeName); }; Common.isArray = function(obj) { return Object.prototype.toString.call(obj) === "[object Array]"; }; Common.isFunction = function(obj) { return typeof obj === "function"; }; Common.isPlainObject = function(obj) { return typeof obj === "object" && obj.constructor === Object; }; Common.isString = function(obj) { return toString.call(obj) === "[object String]"; }; Common.clamp = function(value, min, max) { if (value < min) return min; if (value > max) return max; return value; }; Common.sign = function(value) { return value < 0 ? -1 : 1; }; Common.now = function() { if (typeof window !== "undefined" && window.performance) { if (window.performance.now) { return window.performance.now(); } else if (window.performance.webkitNow) { return window.performance.webkitNow(); } } if (Date.now) { return Date.now(); } return new Date() - Common._nowStartTime; }; Common.random = function(min, max) { min = typeof min !== "undefined" ? min : 0; max = typeof max !== "undefined" ? max : 1; return min + _seededRandom() * (max - min); }; var _seededRandom = function() { Common._seed = (Common._seed * 9301 + 49297) % 233280; return Common._seed / 233280; }; Common.colorToNumber = function(colorString) { colorString = colorString.replace("#", ""); if (colorString.length == 3) { colorString = colorString.charAt(0) + colorString.charAt(0) + colorString.charAt(1) + colorString.charAt(1) + colorString.charAt(2) + colorString.charAt(2); } return parseInt(colorString, 16); }; Common.logLevel = 1; Common.log = function() { if (console && Common.logLevel > 0 && Common.logLevel <= 3) { console.log.apply(console, ["matter-js:"].concat(Array.prototype.slice.call(arguments))); } }; Common.info = function() { if (console && Common.logLevel > 0 && Common.logLevel <= 2) { console.info.apply(console, ["matter-js:"].concat(Array.prototype.slice.call(arguments))); } }; Common.warn = function() { if (console && Common.logLevel > 0 && Common.logLevel <= 3) { console.warn.apply(console, ["matter-js:"].concat(Array.prototype.slice.call(arguments))); } }; Common.warnOnce = function() { var message = Array.prototype.slice.call(arguments).join(" "); if (!Common._warnedOnce[message]) { Common.warn(message); Common._warnedOnce[message] = true; } }; Common.deprecated = function(obj, prop, warning) { obj[prop] = Common.chain(function() { Common.warnOnce("🔅 deprecated 🔅", warning); }, obj[prop]); }; Common.nextId = function() { return Common._nextId++; }; Common.indexOf = function(haystack, needle) { if (haystack.indexOf) return haystack.indexOf(needle); for (var i = 0; i < haystack.length; i++) { if (haystack[i] === needle) return i; } return -1; }; Common.map = function(list, func) { if (list.map) { return list.map(func); } var mapped = []; for (var i = 0; i < list.length; i += 1) { mapped.push(func(list[i])); } return mapped; }; Common.topologicalSort = function(graph) { var result = [], visited = [], temp = []; for (var node in graph) { if (!visited[node] && !temp[node]) { Common._topologicalSort(node, visited, temp, graph, result); } } return result; }; Common._topologicalSort = function(node, visited, temp, graph, result) { var neighbors = graph[node] || []; temp[node] = true; for (var i = 0; i < neighbors.length; i += 1) { var neighbor = neighbors[i]; if (temp[neighbor]) { continue; } if (!visited[neighbor]) { Common._topologicalSort(neighbor, visited, temp, graph, result); } } temp[node] = false; visited[node] = true; result.push(node); }; Common.chain = function() { var funcs = []; for (var i = 0; i < arguments.length; i += 1) { var func = arguments[i]; if (func._chained) { funcs.push.apply(funcs, func._chained); } else { funcs.push(func); } } var chain = function() { var lastResult, args = new Array(arguments.length); for (var i2 = 0, l = arguments.length; i2 < l; i2++) { args[i2] = arguments[i2]; } for (i2 = 0; i2 < funcs.length; i2 += 1) { var result = funcs[i2].apply(lastResult, args); if (typeof result !== "undefined") { lastResult = result; } } return lastResult; }; chain._chained = funcs; return chain; }; Common.chainPathBefore = function(base2, path, func) { return Common.set(base2, path, Common.chain( func, Common.get(base2, path) )); }; Common.chainPathAfter = function(base2, path, func) { return Common.set(base2, path, Common.chain( Common.get(base2, path), func )); }; Common.setDecomp = function(decomp) { Common._decomp = decomp; }; Common.getDecomp = function() { var decomp = Common._decomp; try { if (!decomp && typeof window !== "undefined") { decomp = window.decomp; } if (!decomp && typeof commonjsGlobal !== "undefined") { decomp = commonjsGlobal.decomp; } } catch (e) { decomp = null; } return decomp; }; })(); }, /* 1 */ /***/ function(module3, exports4) { var Bounds = {}; module3.exports = Bounds; (function() { Bounds.create = function(vertices) { var bounds = { min: { x: 0, y: 0 }, max: { x: 0, y: 0 } }; if (vertices) Bounds.update(bounds, vertices); return bounds; }; Bounds.update = function(bounds, vertices, velocity) { bounds.min.x = Infinity; bounds.max.x = -Infinity; bounds.min.y = Infinity; bounds.max.y = -Infinity; for (var i = 0; i < vertices.length; i++) { var vertex = vertices[i]; if (vertex.x > bounds.max.x) bounds.max.x = vertex.x; if (vertex.x < bounds.min.x) bounds.min.x = vertex.x; if (vertex.y > bounds.max.y) bounds.max.y = vertex.y; if (vertex.y < bounds.min.y) bounds.min.y = vertex.y; } if (velocity) { if (velocity.x > 0) { bounds.max.x += velocity.x; } else { bounds.min.x += velocity.x; } if (velocity.y > 0) { bounds.max.y += velocity.y; } else { bounds.min.y += velocity.y; } } }; Bounds.contains = function(bounds, point) { return point.x >= bounds.min.x && point.x <= bounds.max.x && point.y >= bounds.min.y && point.y <= bounds.max.y; }; Bounds.overlaps = function(boundsA, boundsB) { return boundsA.min.x <= boundsB.max.x && boundsA.max.x >= boundsB.min.x && boundsA.max.y >= boundsB.min.y && boundsA.min.y <= boundsB.max.y; }; Bounds.translate = function(bounds, vector) { bounds.min.x += vector.x; bounds.max.x += vector.x; bounds.min.y += vector.y; bounds.max.y += vector.y; }; Bounds.shift = function(bounds, position) { var deltaX = bounds.max.x - bounds.min.x, deltaY = bounds.max.y - bounds.min.y; bounds.min.x = position.x; bounds.max.x = position.x + deltaX; bounds.min.y = position.y; bounds.max.y = position.y + deltaY; }; })(); }, /* 2 */ /***/ function(module3, exports4) { var Vector = {}; module3.exports = Vector; (function() { Vector.create = function(x, y) { return { x: x || 0, y: y || 0 }; }; Vector.clone = function(vector) { return { x: vector.x, y: vector.y }; }; Vector.magnitude = function(vector) { return Math.sqrt(vector.x * vector.x + vector.y * vector.y); }; Vector.magnitudeSquared = function(vector) { return vector.x * vector.x + vector.y * vector.y; }; Vector.rotate = function(vector, angle, output) { var cos = Math.cos(angle), sin = Math.sin(angle); if (!output) output = {}; var x = vector.x * cos - vector.y * sin; output.y = vector.x * sin + vector.y * cos; output.x = x; return output; }; Vector.rotateAbout = function(vector, angle, point, output) { var cos = Math.cos(angle), sin = Math.sin(angle); if (!output) output = {}; var x = point.x + ((vector.x - point.x) * cos - (vector.y - point.y) * sin); output.y = point.y + ((vector.x - point.x) * sin + (vector.y - point.y) * cos); output.x = x; return output; }; Vector.normalise = function(vector) { var magnitude = Vector.magnitude(vector); if (magnitude === 0) return { x: 0, y: 0 }; return { x: vector.x / magnitude, y: vector.y / magnitude }; }; Vector.dot = function(vectorA, vectorB) { return vectorA.x * vectorB.x + vectorA.y * vectorB.y; }; Vector.cross = function(vectorA, vectorB) { return vectorA.x * vectorB.y - vectorA.y * vectorB.x; }; Vector.cross3 = function(vectorA, vectorB, vectorC) { return (vectorB.x - vectorA.x) * (vectorC.y - vectorA.y) - (vectorB.y - vectorA.y) * (vectorC.x - vectorA.x); }; Vector.add = function(vectorA, vectorB, output) { if (!output) output = {}; output.x = vectorA.x + vectorB.x; output.y = vectorA.y + vectorB.y; return output; }; Vector.sub = function(vectorA, vectorB, output) { if (!output) output = {}; output.x = vectorA.x - vectorB.x; output.y = vectorA.y - vectorB.y; return output; }; Vector.mult = function(vector, scalar) { return { x: vector.x * scalar, y: vector.y * scalar }; }; Vector.div = function(vector, scalar) { return { x: vector.x / scalar, y: vector.y / scalar }; }; Vector.perp = function(vector, negate) { negate = negate === true ? -1 : 1; return { x: negate * -vector.y, y: negate * vector.x }; }; Vector.neg = function(vector) { return { x: -vector.x, y: -vector.y }; }; Vector.angle = function(vectorA, vectorB) { return Math.atan2(vectorB.y - vectorA.y, vectorB.x - vectorA.x); }; Vector._temp = [ Vector.create(), Vector.create(), Vector.create(), Vector.create(), Vector.create(), Vector.create() ]; })(); }, /* 3 */ /***/ function(module3, exports4, __webpack_require__) { var Vertices = {}; module3.exports = Vertices; var Vector = __webpack_require__(2); var Common = __webpack_require__(0); (function() { Vertices.create = function(points, body) { var vertices = []; for (var i = 0; i < points.length; i++) { var point = points[i], vertex = { x: point.x, y: point.y, index: i, body, isInternal: false }; vertices.push(vertex); } return vertices; }; Vertices.fromPath = function(path, body) { var pathPattern = /L?\s*([-\d.e]+)[\s,]*([-\d.e]+)*/ig, points = []; path.replace(pathPattern, function(match, x, y) { points.push({ x: parseFloat(x), y: parseFloat(y) }); }); return Vertices.create(points, body); }; Vertices.centre = function(vertices) { var area = Vertices.area(vertices, true), centre = { x: 0, y: 0 }, cross, temp, j; for (var i = 0; i < vertices.length; i++) { j = (i + 1) % vertices.length; cross = Vector.cross(vertices[i], vertices[j]); temp = Vector.mult(Vector.add(vertices[i], vertices[j]), cross); centre = Vector.add(centre, temp); } return Vector.div(centre, 6 * area); }; Vertices.mean = function(vertices) { var average = { x: 0, y: 0 }; for (var i = 0; i < vertices.length; i++) { average.x += vertices[i].x; average.y += vertices[i].y; } return Vector.div(average, vertices.length); }; Vertices.area = function(vertices, signed) { var area = 0, j = vertices.length - 1; for (var i = 0; i < vertices.length; i++) { area += (vertices[j].x - vertices[i].x) * (vertices[j].y + vertices[i].y); j = i; } if (signed) return area / 2; return Math.abs(area) / 2; }; Vertices.inertia = function(vertices, mass) { var numerator = 0, denominator = 0, v = vertices, cross, j; for (var n = 0; n < v.length; n++) { j = (n + 1) % v.length; cross = Math.abs(Vector.cross(v[j], v[n])); numerator += cross * (Vector.dot(v[j], v[j]) + Vector.dot(v[j], v[n]) + Vector.dot(v[n], v[n])); denominator += cross; } return mass / 6 * (numerator / denominator); }; Vertices.translate = function(vertices, vector, scalar) { scalar = typeof scalar !== "undefined" ? scalar : 1; var verticesLength = vertices.length, translateX = vector.x * scalar, translateY = vector.y * scalar, i; for (i = 0; i < verticesLength; i++) { vertices[i].x += translateX; vertices[i].y += translateY; } return vertices; }; Vertices.rotate = function(vertices, angle, point) { if (angle === 0) return; var cos = Math.cos(angle), sin = Math.sin(angle), pointX = point.x, pointY = point.y, verticesLength = vertices.length, vertex, dx, dy, i; for (i = 0; i < verticesLength; i++) { vertex = vertices[i]; dx = vertex.x - pointX; dy = vertex.y - pointY; vertex.x = pointX + (dx * cos - dy * sin); vertex.y = pointY + (dx * sin + dy * cos); } return vertices; }; Vertices.contains = function(vertices, point) { var pointX = point.x, pointY = point.y, verticesLength = vertices.length, vertex = vertices[verticesLength - 1], nextVertex; for (var i = 0; i < verticesLength; i++) { nextVertex = vertices[i]; if ((pointX - vertex.x) * (nextVertex.y - vertex.y) + (pointY - vertex.y) * (vertex.x - nextVertex.x) > 0) { return false; } vertex = nextVertex; } return true; }; Vertices.scale = function(vertices, scaleX, scaleY, point) { if (scaleX === 1 && scaleY === 1) return vertices; point = point || Vertices.centre(vertices); var vertex, delta; for (var i = 0; i < vertices.length; i++) { vertex = vertices[i]; delta = Vector.sub(vertex, point); vertices[i].x = point.x + delta.x * scaleX; vertices[i].y = point.y + delta.y * scaleY; } return vertices; }; Vertices.chamfer = function(vertices, radius, quality, qualityMin, qualityMax) { if (typeof radius === "number") { radius = [radius]; } else { radius = radius || [8]; } quality = typeof quality !== "undefined" ? quality : -1; qualityMin = qualityMin || 2; qualityMax = qualityMax || 14; var newVertices = []; for (var i = 0; i < vertices.length; i++) { var prevVertex = vertices[i - 1 >= 0 ? i - 1 : vertices.length - 1], vertex = vertices[i], nextVertex = vertices[(i + 1) % vertices.length], currentRadius = radius[i < radius.length ? i : radius.length - 1]; if (currentRadius === 0) { newVertices.push(vertex); continue; } var prevNormal = Vector.normalise({ x: vertex.y - prevVertex.y, y: prevVertex.x - vertex.x }); var nextNormal = Vector.normalise({ x: nextVertex.y - vertex.y, y: vertex.x - nextVertex.x }); var diagonalRadius = Math.sqrt(2 * Math.pow(currentRadius, 2)), radiusVector = Vector.mult(Common.clone(prevNormal), currentRadius), midNormal = Vector.normalise(Vector.mult(Vector.add(prevNormal, nextNormal), 0.5)), scaledVertex = Vector.sub(vertex, Vector.mult(midNormal, diagonalRadius)); var precision = quality; if (quality === -1) { precision = Math.pow(currentRadius, 0.32) * 1.75; } precision = Common.clamp(precision, qualityMin, qualityMax); if (precision % 2 === 1) precision += 1; var alpha = Math.acos(Vector.dot(prevNormal, nextNormal)), theta = alpha / precision; for (var j = 0; j < precision; j++) { newVertices.push(Vector.add(Vector.rotate(radiusVector, theta * j), scaledVertex)); } } return newVertices; }; Vertices.clockwiseSort = function(vertices) { var centre = Vertices.mean(vertices); vertices.sort(function(vertexA, vertexB) { return Vector.angle(centre, vertexA) - Vector.angle(centre, vertexB); }); return vertices; }; Vertices.isConvex = function(vertices) { var flag = 0, n = vertices.length, i, j, k, z; if (n < 3) return null; for (i = 0; i < n; i++) { j = (i + 1) % n; k = (i + 2) % n; z = (vertices[j].x - vertices[i].x) * (vertices[k].y - vertices[j].y); z -= (vertices[j].y - vertices[i].y) * (vertices[k].x - vertices[j].x); if (z < 0) { flag |= 1; } else if (z > 0) { flag |= 2; } if (flag === 3) { return false; } } if (flag !== 0) { return true; } else { return null; } }; Vertices.hull = function(vertices) { var upper = [], lower = [], vertex, i; vertices = vertices.slice(0); vertices.sort(function(vertexA, vertexB) { var dx = vertexA.x - vertexB.x; return dx !== 0 ? dx : vertexA.y - vertexB.y; }); for (i = 0; i < vertices.length; i += 1) { vertex = vertices[i]; while (lower.length >= 2 && Vector.cross3(lower[lower.length - 2], lower[lower.length - 1], vertex) <= 0) { lower.pop(); } lower.push(vertex); } for (i = vertices.length - 1; i >= 0; i -= 1) { vertex = vertices[i]; while (upper.length >= 2 && Vector.cross3(upper[upper.length - 2], upper[upper.length - 1], vertex) <= 0) { upper.pop(); } upper.push(vertex); } upper.pop(); lower.pop(); return upper.concat(lower); }; })(); }, /* 4 */ /***/ function(module3, exports4, __webpack_require__) { var Body = {}; module3.exports = Body; var Vertices = __webpack_require__(3); var Vector = __webpack_require__(2); var Sleeping = __webpack_require__(7); var Common = __webpack_require__(0); var Bounds = __webpack_require__(1); var Axes = __webpack_require__(11); (function() { Body._timeCorrection = true; Body._inertiaScale = 4; Body._nextCollidingGroupId = 1; Body._nextNonCollidingGroupId = -1; Body._nextCategory = 1; Body._baseDelta = 1e3 / 60; Body.create = function(options) { var defaults = { id: Common.nextId(), type: "body", label: "Body", parts: [], plugin: {}, angle: 0, vertices: Vertices.fromPath("L 0 0 L 40 0 L 40 40 L 0 40"), position: { x: 0, y: 0 }, force: { x: 0, y: 0 }, torque: 0, positionImpulse: { x: 0, y: 0 }, constraintImpulse: { x: 0, y: 0, angle: 0 }, totalContacts: 0, speed: 0, angularSpeed: 0, velocity: { x: 0, y: 0 }, angularVelocity: 0, isSensor: false, isStatic: false, isSleeping: false, motion: 0, sleepThreshold: 60, density: 1e-3, restitution: 0, friction: 0.1, frictionStatic: 0.5, frictionAir: 0.01, collisionFilter: { category: 1, mask: 4294967295, group: 0 }, slop: 0.05, timeScale: 1, render: { visible: true, opacity: 1, strokeStyle: null, fillStyle: null, lineWidth: null, sprite: { xScale: 1, yScale: 1, xOffset: 0, yOffset: 0 } }, events: null, bounds: null, chamfer: null, circleRadius: 0, positionPrev: null, anglePrev: 0, parent: null, axes: null, area: 0, mass: 0, inertia: 0, deltaTime: 1e3 / 60, _original: null }; var body = Common.extend(defaults, options); _initProperties(body, options); return body; }; Body.nextGroup = function(isNonColliding) { if (isNonColliding) return Body._nextNonCollidingGroupId--; return Body._nextCollidingGroupId++; }; Body.nextCategory = function() { Body._nextCategory = Body._nextCategory << 1; return Body._nextCategory; }; var _initProperties = function(body, options) { options = options || {}; Body.set(body, { bounds: body.bounds || Bounds.create(body.vertices), positionPrev: body.positionPrev || Vector.clone(body.position), anglePrev: body.anglePrev || body.angle, vertices: body.vertices, parts: body.parts || [body], isStatic: body.isStatic, isSleeping: body.isSleeping, parent: body.parent || body }); Vertices.rotate(body.vertices, body.angle, body.position); Axes.rotate(body.axes, body.angle); Bounds.update(body.bounds, body.vertices, body.velocity); Body.set(body, { axes: options.axes || body.axes, area: options.area || body.area, mass: options.mass || body.mass, inertia: options.inertia || body.inertia }); var defaultFillStyle = body.isStatic ? "#14151f" : Common.choose(["#f19648", "#f5d259", "#f55a3c", "#063e7b", "#ececd1"]), defaultStrokeStyle = body.isStatic ? "#555" : "#ccc", defaultLineWidth = body.isStatic && body.render.fillStyle === null ? 1 : 0; body.render.fillStyle = body.render.fillStyle || defaultFillStyle; body.render.strokeStyle = body.render.strokeStyle || defaultStrokeStyle; body.render.lineWidth = body.render.lineWidth || defaultLineWidth; body.render.sprite.xOffset += -(body.bounds.min.x - body.position.x) / (body.bounds.max.x - body.bounds.min.x); body.render.sprite.yOffset += -(body.bounds.min.y - body.position.y) / (body.bounds.max.y - body.bounds.min.y); }; Body.set = function(body, settings, value) { var property; if (typeof settings === "string") { property = settings; settings = {}; settings[property] = value; } for (property in settings) { if (!Object.prototype.hasOwnProperty.call(settings, property)) continue; value = settings[property]; switch (property) { case "isStatic": Body.setStatic(body, value); break; case "isSleeping": Sleeping.set(body, value); break; case "mass": Body.setMass(body, value); break; case "density": Body.setDensity(body, value); break; case "inertia": Body.setInertia(body, value); break; case "vertices": Body.setVertices(body, value); break; case "position": Body.setPosition(body, value); break; case "angle": Body.setAngle(body, value); break; case "velocity": Body.setVelocity(body, value); break; case "angularVelocity": Body.setAngularVelocity(body, value); break; case "speed": Body.setSpeed(body, value); break; case "angularSpeed": Body.setAngularSpeed(body, value); break; case "parts": Body.setParts(body, value); break; case "centre": Body.setCentre(body, value); break; default: body[property] = value; } } }; Body.setStatic = function(body, isStatic) { for (var i = 0; i < body.parts.length; i++) { var part = body.parts[i]; part.isStatic = isStatic; if (isStatic) { part._original = { restitution: part.restitution, friction: part.friction, mass: part.mass, inertia: part.inertia, density: part.density, inverseMass: part.inverseMass, inverseInertia: part.inverseInertia }; part.restitution = 0; part.friction = 1; part.mass = part.inertia = part.density = Infinity; part.inverseMass = part.inverseInertia = 0; part.positionPrev.x = part.position.x; part.positionPrev.y = part.position.y; part.anglePrev = part.angle; part.angularVelocity = 0; part.speed = 0; part.angularSpeed = 0; part.motion = 0; } else if (part._original) { part.restitution = part._original.restitution; part.friction = part._original.friction; part.mass = part._original.mass; part.inertia = part._original.inertia; part.density = part._original.density; part.inverseMass = part._original.inverseMass; part.inverseInertia = part._original.inverseInertia; part._original = null; } } }; Body.setMass = function(body, mass) { var moment = body.inertia / (body.mass / 6); body.inertia = moment * (mass / 6); body.inverseInertia = 1 / body.inertia; body.mass = mass; body.inverseMass = 1 / body.mass; body.density = body.mass / body.area; }; Body.setDensity = function(body, density) { Body.setMass(body, density * body.area); body.density = density; }; Body.setInertia = function(body, inertia) { body.inertia = inertia; body.inverseInertia = 1 / body.inertia; }; Body.setVertices = function(body, vertices) { if (vertices[0].body === body) { body.vertices = vertices; } else { body.vertices = Vertices.create(vertices, body); } body.axes = Axes.fromVertices(body.vertices); body.area = Vertices.area(body.vertices); Body.setMass(body, body.density * body.area); var centre = Vertices.centre(body.vertices); Vertices.translate(body.vertices, centre, -1); Body.setInertia(body, Body._inertiaScale * Vertices.inertia(body.vertices, body.mass)); Vertices.translate(body.vertices, body.position); Bounds.update(body.bounds, body.vertices, body.velocity); }; Body.setParts = function(body, parts, autoHull) { var i; parts = parts.slice(0); body.parts.length = 0; body.parts.push(body); body.parent = body; for (i = 0; i < parts.length; i++) { var part = parts[i]; if (part !== body) { part.parent = body; body.parts.push(part); } } if (body.parts.length === 1) return; autoHull = typeof autoHull !== "undefined" ? autoHull : true; if (autoHull) { var vertices = []; for (i = 0; i < parts.length; i++) { vertices = vertices.concat(parts[i].vertices); } Vertices.clockwiseSort(vertices); var hull = Vertices.hull(vertices), hullCentre = Vertices.centre(hull); Body.setVertices(body, hull); Vertices.translate(body.vertices, hullCentre); } var total = Body._totalProperties(body); body.area = total.area; body.parent = body; body.position.x = total.centre.x; body.position.y = total.centre.y; body.positionPrev.x = total.centre.x; body.positionPrev.y = total.centre.y; Body.setMass(body, total.mass); Body.setInertia(body, total.inertia); Body.setPosition(body, total.centre); }; Body.setCentre = function(body, centre, relative) { if (!relative) { body.positionPrev.x = centre.x - (body.position.x - body.positionPrev.x); body.positionPrev.y = centre.y - (body.position.y - body.positionPrev.y); body.position.x = centre.x; body.position.y = centre.y; } else { body.positionPrev.x += centre.x; body.positionPrev.y += centre.y; body.position.x += centre.x; body.position.y += centre.y; } }; Body.setPosition = function(body, position, updateVelocity) { var delta = Vector.sub(position, body.position); if (updateVelocity) { body.positionPrev.x = body.position.x; body.positionPrev.y = body.position.y; body.velocity.x = delta.x; body.velocity.y = delta.y; body.speed = Vector.magnitude(delta); } else { body.positionPrev.x += delta.x; body.positionPrev.y += delta.y; } for (var i = 0; i < body.parts.length; i++) { var part = body.parts[i]; part.position.x += delta.x; part.position.y += delta.y; Vertices.translate(part.vertices, delta); Bounds.update(part.bounds, part.vertices, body.velocity); } }; Body.setAngle = function(body, angle, updateVelocity) { var delta = angle - body.angle; if (updateVelocity) { body.anglePrev = body.angle; body.angularVelocity = delta; body.angularSpeed = Math.abs(delta); } else { body.anglePrev += delta; } for (var i = 0; i < body.parts.length; i++) { var part = body.parts[i]; part.angle += delta; Vertices.rotate(part.vertices, delta, body.position); Axes.rotate(part.axes, delta); Bounds.update(part.bounds, part.vertices, body.velocity); if (i > 0) { Vector.rotateAbout(part.position, delta, body.position, part.position); } } }; Body.setVelocity = function(body, velocity) { var timeScale = body.deltaTime / Body._baseDelta; body.positionPrev.x = body.position.x - velocity.x * timeScale; body.positionPrev.y = body.position.y - velocity.y * timeScale; body.velocity.x = (body.position.x - body.positionPrev.x) / timeScale; body.velocity.y = (body.position.y - body.positionPrev.y) / timeScale; body.speed = Vector.magnitude(body.velocity); }; Body.getVelocity = function(body) { var timeScale = Body._baseDelta / body.deltaTime; return { x: (body.position.x - body.positionPrev.x) * timeScale, y: (body.position.y - body.positionPrev.y) * timeScale }; }; Body.getSpeed = function(body) { return Vector.magnitude(Body.getVelocity(body)); }; Body.setSpeed = function(body, speed) { Body.setVelocity(body, Vector.mult(Vector.normalise(Body.getVelocity(body)), speed)); }; Body.setAngularVelocity = function(body, velocity) { var timeScale = body.deltaTime / Body._baseDelta; body.anglePrev = body.angle - velocity * timeScale; body.angularVelocity = (body.angle - body.anglePrev) / timeScale; body.angularSpeed = Math.abs(body.angularVelocity); }; Body.getAngularVelocity = function(body) { return (body.angle - body.anglePrev) * Body._baseDelta / body.deltaTime; }; Body.getAngularSpeed = function(body) { return Math.abs(Body.getAngularVelocity(body)); }; Body.setAngula