diff options
author | Ulrich-Matthias Schäfer <ulima.ums@googlemail.com> | 2018-11-04 21:46:33 +0100 |
---|---|---|
committer | Ulrich-Matthias Schäfer <ulima.ums@googlemail.com> | 2018-11-04 21:46:33 +0100 |
commit | d654ab010adf42aab757529b6c09f27215740b27 (patch) | |
tree | 95baa420a8eb71f64220b27b822bcab403d4d535 /src | |
parent | d22dce113a4a61d76b3c0e7c7fb77231f575c6fd (diff) | |
download | svg.js-d654ab010adf42aab757529b6c09f27215740b27.tar.gz svg.js-d654ab010adf42aab757529b6c09f27215740b27.zip |
Revert back to classes, fix remaining tests
Diffstat (limited to 'src')
42 files changed, 520 insertions, 480 deletions
@@ -1,10 +1,10 @@ -import Base from './Base.js' +import Container from './Container.js' import {nodeOrNew} from './tools.js' import {xlink} from './namespaces.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class A extends Base{ +export default class A extends Container { constructor (node) { super(nodeOrNew('a', node), A) } diff --git a/src/ArrayPolyfill.js b/src/ArrayPolyfill.js index 9c3ee61..19c1ede 100644 --- a/src/ArrayPolyfill.js +++ b/src/ArrayPolyfill.js @@ -1,6 +1,5 @@ export const subClassArray = (function () { try { - //throw 'asdad' // try es6 subclassing return Function('name', 'baseClass', '_constructor', [ 'baseClass = baseClass || Array', diff --git a/src/Bare.js b/src/Bare.js index e0d8cdd..76aa3bf 100644 --- a/src/Bare.js +++ b/src/Bare.js @@ -1,14 +1,12 @@ import {nodeOrNew} from './tools.js' import {register} from './adopter.js' -import Base from './Base.js' +import Parent from './Parent.js' import {registerMethods} from './methods.js' import {extend} from './tools.js' - -export default class Bare extends Base { - constructor (node, inherit = {}) { +export default class Bare extends Parent { + constructor (node) { super(nodeOrNew(node, typeof node === 'string' ? null : node), Bare) - //extend(this, inherit) } words (text) { diff --git a/src/Base.js b/src/Base.js index 6b1242b..1e76bb4 100644 --- a/src/Base.js +++ b/src/Base.js @@ -1,11 +1,11 @@ export default class Base { - constructor (node, {extensions = []}) { - this.tags = [] - - for (let extension of extensions) { - extension.setup.call(this, node) - this.tags.push(extension.name) - } + constructor (node/*, {extensions = []}*/) { + // this.tags = [] + // + // for (let extension of extensions) { + // extension.setup.call(this, node) + // this.tags.push(extension.name) + // } } is (ability) { @@ -98,7 +98,6 @@ function getBox(cb) { box = cb(clone.node) clone.remove() } catch (e) { - throw (e) console.warn('Getting a bounding box of this element is not possible') } } diff --git a/src/Circle.js b/src/Circle.js index d19b759..9d0c4db 100644 --- a/src/Circle.js +++ b/src/Circle.js @@ -1,11 +1,11 @@ -import Base from './Base.js' +import Shape from './Shape.js' import {nodeOrNew, extend} from './tools.js' import {x, y, cx, cy, width, height, size} from './circled.js' import SVGNumber from './SVGNumber.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Circle extends Base { +export default class Circle extends Shape { constructor (node) { super(nodeOrNew('circle', node), Circle) } diff --git a/src/ClipPath.js b/src/ClipPath.js index 4989d6d..1801c67 100644 --- a/src/ClipPath.js +++ b/src/ClipPath.js @@ -1,11 +1,11 @@ -import Base from './Base.js' +import Container from './Container.js' import {nodeOrNew, extend} from './tools.js' import find from './selector.js' -import {remove} from './Element.js' +//import {remove} from './Element.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class ClipPath extends Base { +export default class ClipPath extends Container { constructor (node) { super(nodeOrNew('clipPath', node), ClipPath) } @@ -18,7 +18,8 @@ export default class ClipPath extends Base { }) // remove clipPath from parent - return remove.call(this) + return super.remove() + //return remove.call(this) } targets () { diff --git a/src/Container.js b/src/Container.js new file mode 100644 index 0000000..5d6dc43 --- /dev/null +++ b/src/Container.js @@ -0,0 +1,2 @@ +import Parent from './Parent.js' +export default class Container extends Parent {} diff --git a/src/Defs.js b/src/Defs.js index 68c5755..8cafb49 100644 --- a/src/Defs.js +++ b/src/Defs.js @@ -1,8 +1,8 @@ -import Base from './Base.js' +import Container from './Container.js' import {nodeOrNew} from './tools.js' import {register} from './adopter.js' -export default class Defs extends Base { +export default class Defs extends Container { constructor (node) { super(nodeOrNew('defs', node), Defs) } @@ -1,12 +1,12 @@ -import Base from './Base.js' +import Container from './Container.js' import Defs from './Defs.js' import { extend, nodeOrNew } from './tools.js' import { ns, xlink, xmlns, svgjs } from './namespaces.js' import {adopt, register} from './adopter.js' import {registerMethods} from './methods.js' -import {remove, parent, doc} from './Element.js' +//import {remove, parent, doc} from './Element.js' -export default class Doc extends Base { +export default class Doc extends Container { constructor(node) { super(nodeOrNew('svg', node), Doc) this.namespace() @@ -22,7 +22,8 @@ export default class Doc extends Base { // If not, call docs from this element doc() { if (this.isRoot()) return this - return doc.call(this) + return super.doc() + //return doc.call(this) } // Add namespaces @@ -50,21 +51,22 @@ export default class Doc extends Base { : adopt(this.node.parentNode) } - return parent.call(this, type) + return super.parent(type) + //return parent.call(this, type) } // Removes the doc from the DOM - remove() { - if (!this.isRoot()) { - return remove.call(this) - } - - if (this.parent()) { - this.parent().removeChild(this.node) - } - - return this - } + // remove() { + // if (!this.isRoot()) { + // return super.remove() + // } + // + // if (this.parent()) { + // this.parent().remove(this) + // } + // + // return this + // } clear() { // remove children diff --git a/src/Element.js b/src/Element.js index e8352a8..5e798ff 100644 --- a/src/Element.js +++ b/src/Element.js @@ -5,277 +5,283 @@ import {ns} from './namespaces.js' import SVGNumber from './SVGNumber.js' import {registerMethods} from './methods.js' import {registerConstructor} from './methods.js' +import EventTarget from './EventTarget.js' const Doc = getClass(root) -const HtmlNode = getClass('HtmlNode') -export const name = 'Element' +//export const name = 'Element' + +export default class Element extends EventTarget { + constructor (node) { + super() -export function setup (node) { // initialize data object - this.dom = {} + this.dom = {} // create circular reference - this.node = node + this.node = node - this.type = node.nodeName - this.node.instance = this + this.type = node.nodeName + this.node.instance = this - if (node.hasAttribute('svgjs:data')) { - // pull svgjs data from the dom (getAttributeNS doesn't work in html5) - this.setData(JSON.parse(node.getAttribute('svgjs:data')) || {}) + if (node.hasAttribute('svgjs:data')) { + // pull svgjs data from the dom (getAttributeNS doesn't work in html5) + this.setData(JSON.parse(node.getAttribute('svgjs:data')) || {}) + } } -} // Move over x-axis -export function x (x) { - return this.attr('x', x) -} + x (x) { + return this.attr('x', x) + } // Move over y-axis -export function y (y) { - return this.attr('y', y) -} + y (y) { + return this.attr('y', y) + } // Move by center over x-axis -export function cx (x) { - return x == null ? this.x() + this.width() / 2 : this.x(x - this.width() / 2) -} + cx (x) { + return x == null ? this.x() + this.width() / 2 : this.x(x - this.width() / 2) + } // Move by center over y-axis -export function cy (y) { - return y == null - ? this.y() + this.height() / 2 - : this.y(y - this.height() / 2) -} + cy (y) { + return y == null + ? this.y() + this.height() / 2 + : this.y(y - this.height() / 2) + } // Move element to given x and y values -export function move (x, y) { - return this.x(x).y(y) -} + move (x, y) { + return this.x(x).y(y) + } // Move element by its center -export function center (x, y) { - return this.cx(x).cy(y) -} + center (x, y) { + return this.cx(x).cy(y) + } // Set width of element -export function width (width) { - return this.attr('width', width) -} + width (width) { + return this.attr('width', width) + } // Set height of element -export function height (height) { - return this.attr('height', height) -} + height (height) { + return this.attr('height', height) + } // Set element size to given width and height -export function size (width, height) { - let p = proportionalSize(this, width, height) + size (width, height) { + let p = proportionalSize(this, width, height) - return this - .width(new SVGNumber(p.width)) - .height(new SVGNumber(p.height)) -} + return this + .width(new SVGNumber(p.width)) + .height(new SVGNumber(p.height)) + } // Clone element -export function clone (parent) { - // write dom data to the dom so the clone can pickup the data - this.writeDataToDom() + clone (parent) { + // write dom data to the dom so the clone can pickup the data + this.writeDataToDom() - // clone element and assign new id - let clone = assignNewId(this.node.cloneNode(true)) + // clone element and assign new id + let clone = assignNewId(this.node.cloneNode(true)) - // insert the clone in the given parent or after myself - if (parent) parent.add(clone) - else this.after(clone) + // insert the clone in the given parent or after myself + if (parent) parent.add(clone) + else this.after(clone) - return clone -} + return clone + } // Remove element -export function remove () { - if (this.parent()) { this.parent().removeElement(this) } + remove () { + if (this.parent()) { this.parent().removeElement(this) } - return this -} + return this + } // Replace element -export function replace (element) { - this.after(element).remove() + replace (element) { + this.after(element).remove() - return element -} + return element + } // Add element to given container and return self -export function addTo (parent) { - return makeInstance(parent).put(this) -} + addTo (parent) { + return makeInstance(parent).put(this) + } // Add element to given container and return container -export function putIn (parent) { - return makeInstance(parent).add(this) -} + putIn (parent) { + return makeInstance(parent).add(this) + } // Get / set id -export function id (id) { - // generate new id if no id set - if (typeof id === 'undefined' && !this.node.id) { - this.node.id = eid(this.type) + id (id) { + // generate new id if no id set + if (typeof id === 'undefined' && !this.node.id) { + this.node.id = eid(this.type) + } + + // dont't set directly width this.node.id to make `null` work correctly + return this.attr('id', id) } - // dont't set directly width this.node.id to make `null` work correctly - return this.attr('id', id) -} - // Checks whether the given point inside the bounding box of the element -export function inside (x, y) { - let box = this.bbox() + inside (x, y) { + let box = this.bbox() - return x > box.x && - y > box.y && - x < box.x + box.width && - y < box.y + box.height -} + return x > box.x && + y > box.y && + x < box.x + box.width && + y < box.y + box.height + } // Return id on string conversion -export function toString () { - return this.id() -} + toString () { + return this.id() + } // Return array of classes on the node -export function classes () { - var attr = this.attr('class') - return attr == null ? [] : attr.trim().split(delimiter) -} + classes () { + var attr = this.attr('class') + return attr == null ? [] : attr.trim().split(delimiter) + } // Return true if class exists on the node, false otherwise -export function hasClass (name) { - return this.classes().indexOf(name) !== -1 -} + hasClass (name) { + return this.classes().indexOf(name) !== -1 + } // Add class to the node -export function addClass (name) { - if (!this.hasClass(name)) { - var array = this.classes() - array.push(name) - this.attr('class', array.join(' ')) + addClass (name) { + if (!this.hasClass(name)) { + var array = this.classes() + array.push(name) + this.attr('class', array.join(' ')) + } + + return this } - return this -} - // Remove class from the node -export function removeClass (name) { - if (this.hasClass(name)) { - this.attr('class', this.classes().filter(function (c) { - return c !== name - }).join(' ')) + removeClass (name) { + if (this.hasClass(name)) { + this.attr('class', this.classes().filter(function (c) { + return c !== name + }).join(' ')) + } + + return this } - return this -} - // Toggle the presence of a class on the node -export function toggleClass (name) { - return this.hasClass(name) ? this.removeClass(name) : this.addClass(name) -} + toggleClass (name) { + return this.hasClass(name) ? this.removeClass(name) : this.addClass(name) + } -// Get referenced element form attribute value -export function reference (attr) { - let id = idFromReference(this.attr(attr)) - return id ? makeInstance(id) : null -} + // Get referenced element form attribute value + reference (attr) { + let id = idFromReference(this.attr(attr)) + return id ? makeInstance(id) : null + } // Returns the parent element instance -export function parent (type) { - var parent = this + parent (type) { + var parent = this - // check for parent - if (!parent.node.parentNode) return null + // check for parent + if (!parent.node.parentNode) return null - // get parent element - parent = adopt(parent.node.parentNode) + // get parent element + parent = adopt(parent.node.parentNode) - if (!type) return parent + if (!type) return parent - // loop trough ancestors if type is given - while (parent && parent.node instanceof window.SVGElement) { - if (typeof type === 'string' ? parent.matches(type) : parent instanceof type) return parent - parent = adopt(parent.node.parentNode) + // loop trough ancestors if type is given + while (parent && parent.node instanceof window.SVGElement) { + if (typeof type === 'string' ? parent.matches(type) : parent instanceof type) return parent + parent = adopt(parent.node.parentNode) + } } -} -// Get parent document -export function doc () { - let p = this.parent(Doc) - return p && p.doc() -} + // Get parent document + doc () { + let p = this.parent(Doc) + return p && p.doc() + } // Get defs -export function defs () { - return this.doc().defs() -} + defs () { + return this.doc().defs() + } // return array of all ancestors of given type up to the root svg -export function parents (type) { - let parents = [] - let parent = this + parents (type) { + let parents = [] + let parent = this - do { - parent = parent.parent(type) - if (!parent || parent instanceof HtmlNode) break + do { + parent = parent.parent(type) + if (!parent || parent instanceof getClass('HtmlNode')) break - parents.push(parent) - } while (parent.parent) + parents.push(parent) + } while (parent.parent) - return parents -} + return parents + } // matches the element vs a css selector -export function matches (selector) { - return matcher(this.node, selector) -} + matches (selector) { + return matcher(this.node, selector) + } // Returns the svg node to call native svg methods on it -export function native () { - return this.node -} + native () { + return this.node + } // Import raw svg -export function svg () { - // write svgjs data to the dom - this.writeDataToDom() + svg () { + // write svgjs data to the dom + this.writeDataToDom() - return this.node.outerHTML -} + return this.node.outerHTML + } // write svgjs data to the dom -export function writeDataToDom () { - // remove previously set data - this.node.removeAttribute('svgjs:data') - - if (Object.keys(this.dom).length) { - this.node.setAttribute('svgjs:data', JSON.stringify(this.dom)) // see #428 + writeDataToDom () { + // remove previously set data + this.node.removeAttribute('svgjs:data') + + if (Object.keys(this.dom).length) { + this.node.setAttribute('svgjs:data', JSON.stringify(this.dom)) // see #428 + } + return this } - return this -} // set given data to the elements data property -export function setData (o) { - this.dom = o - return this -} + setData (o) { + this.dom = o + return this + } -export function getEventTarget () { - return this.node + getEventTarget () { + return this.node + } } -registerMethods('Element', { - x, y, cx, cy, move, center, width, height, size, clone, remove, replace, - addTo, putIn, id, inside, toString, classes, hasClass, addClass, removeClass, - toggleClass, reference, doc, defs, parent, parents, matches, native, svg, - writeDataToDom, setData, getEventTarget -}) -registerConstructor('Element', setup) + +// registerMethods('Element', { +// x, y, cx, cy, move, center, width, height, size, clone, remove, replace, +// addTo, putIn, id, inside, toString, classes, hasClass, addClass, removeClass, +// toggleClass, reference, doc, defs, parent, parents, matches, native, svg, +// writeDataToDom, setData, getEventTarget +// }) +// +// registerConstructor('Element', setup) diff --git a/src/Ellipse.js b/src/Ellipse.js index b5bd436..21a1018 100644 --- a/src/Ellipse.js +++ b/src/Ellipse.js @@ -1,10 +1,10 @@ -import Base from './Base.js' +import Shape from './Shape.js' import * as circled from './circled.js' import {extend, nodeOrNew} from './tools.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Ellipse extends Base { +export default class Ellipse extends Shape { constructor (node) { super(nodeOrNew('ellipse', node), Ellipse) } diff --git a/src/EventTarget.js b/src/EventTarget.js index 8702894..a72cafd 100644 --- a/src/EventTarget.js +++ b/src/EventTarget.js @@ -1,37 +1,71 @@ -import {on as _on, off as _off, dispatch as _dispatch} from './event.js' -import {registerMethods} from './methods.js' -import {registerConstructor} from './methods.js' +import Base from './Base.js' +import {on, off, dispatch} from './event.js' +import {extend} from './tools.js' -export const name = 'EventTarget' - -export function setup (node = {}) { - this.events = node.events || {} -} +export default class EventTarget extends Base{ + constructor (node = {}) { + super() + this.events = node.events || {} + } // Bind given event to listener -export function on (event, listener, binding, options) { - _on(this, event, listener, binding, options) - return this -} + on (event, listener, binding, options) { + on(this, event, listener, binding, options) + return this + } // Unbind event from listener -export function off (event, listener) { - _off(this, event, listener) - return this -} + off (event, listener) { + off(this, event, listener) + return this + } -export function dispatch (event, data) { - return _dispatch(this, event, data) -} + dispatch (event, data) { + return dispatch(this, event, data) + } // Fire given event -export function fire (event, data) { - this.dispatch(event, data) - return this + fire (event, data) { + this.dispatch(event, data) + return this + } } -registerMethods('EventTarget', { - on, off, dispatch, fire -}) -registerConstructor('EventTarget', setup) +// Add events to elements +const methods = [ 'click', + 'dblclick', + 'mousedown', + 'mouseup', + 'mouseover', + 'mouseout', + 'mousemove', + 'mouseenter', + 'mouseleave', + 'touchstart', + 'touchmove', + 'touchleave', + 'touchend', + 'touchcancel' ].reduce(function (last, event) { + // add event to Element + const fn = function (f) { + if (f === null) { + off(this, event) + } else { + on(this, event, f) + } + return this + } + + last[event] = fn + return last + }, {}) + +extend(EventTarget, methods) + + +// registerMethods('EventTarget', { +// on, off, dispatch, fire +// }) +// +// registerConstructor('EventTarget', setup) @@ -1,9 +1,9 @@ -import Base from './Base.js' +import Container from './Container.js' import {nodeOrNew} from './tools.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class G extends Base { +export default class G extends Container { constructor (node) { super(nodeOrNew('g', node), G) } diff --git a/src/Gradient.js b/src/Gradient.js index e6aa362..0f20173 100644 --- a/src/Gradient.js +++ b/src/Gradient.js @@ -1,12 +1,13 @@ import Stop from './Stop.js' -import Base from './Base.js' +import Container from './Container.js' import * as gradiented from './gradiented.js' import {nodeOrNew, extend} from './tools.js' -import attr from './attr.js' +//import attr from './attr.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' +import Box from './Box.js' -export default class Gradient extends Base { +export default class Gradient extends Container { constructor (type) { super( nodeOrNew(type + 'Gradient', typeof type === 'string' ? null : type), @@ -45,12 +46,17 @@ export default class Gradient extends Base { // custom attr to handle transform attr (a, b, c) { if (a === 'transform') a = 'gradientTransform' - return attr.call(this, a, b, c) + return super.attr(a, b, c) + //return attr.call(this, a, b, c) } targets () { return find('svg [fill*="' + this.id() + '"]') } + + bbox () { + return new Box() + } } extend(Gradient, gradiented) diff --git a/src/HtmlNode.js b/src/HtmlNode.js index 8488edf..258c0ec 100644 --- a/src/HtmlNode.js +++ b/src/HtmlNode.js @@ -1,8 +1,8 @@ import {makeInstance} from './adopter.js' -import Base from './Base.js' +import Parent from './Parent.js' import {register} from './adopter.js' -export default class HtmlNode extends Base { +export default class HtmlNode extends Parent { constructor (element) { super(element, HtmlNode) this.node = element @@ -23,6 +23,11 @@ export default class HtmlNode extends Base { return element } + removeElement (element) { + this.node.removeChild(element.node) + return this + } + getEventTarget () { return this.node } diff --git a/src/Image.js b/src/Image.js index 69eede5..ea46a57 100644 --- a/src/Image.js +++ b/src/Image.js @@ -1,4 +1,4 @@ -import Base from './Base.js' +import Shape from './Shape.js' import Pattern from './Pattern.js' import {on, off} from './event.js' import {nodeOrNew} from './tools.js' @@ -6,7 +6,7 @@ import {xlink} from './namespaces.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Image extends Base { +export default class Image extends Shape { constructor (node) { super(nodeOrNew('image', node), Image) } diff --git a/src/Line.js b/src/Line.js index 550c0de..660b4f5 100644 --- a/src/Line.js +++ b/src/Line.js @@ -1,11 +1,12 @@ import {proportionalSize} from './helpers.js' -import {nodeOrNew} from './tools.js' +import {nodeOrNew, extend} from './tools.js' import PointArray from './PointArray.js' -import Base from './Base.js' +import Shape from './Shape.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' +import * as pointed from './pointed.js' -export default class Line extends Base { +export default class Line extends Shape { // Initialize node constructor (node) { super(nodeOrNew('line', node), Line) @@ -42,9 +43,10 @@ export default class Line extends Base { var p = proportionalSize(this, width, height) return this.attr(this.array().size(p.width, p.height).toLine()) } - } +extend(Line, pointed) + registerMethods({ Container: { // Create a line element diff --git a/src/Marker.js b/src/Marker.js index 403a387..df19f20 100644 --- a/src/Marker.js +++ b/src/Marker.js @@ -1,9 +1,9 @@ -import Base from './Base.js' +import Container from './Container.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' import {nodeOrNew} from './tools.js' -export default class Marker extends Base { +export default class Marker extends Container { // Initialize node constructor (node) { super(nodeOrNew('marker', node), Marker) diff --git a/src/Mask.js b/src/Mask.js index b61c336..40ebce7 100644 --- a/src/Mask.js +++ b/src/Mask.js @@ -1,11 +1,11 @@ -import Base from './Base.js' +import Container from './Container.js' import {nodeOrNew} from './tools.js' import find from './selector.js' -import {remove} from './Element.js' +//import {remove} from './Element.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Mask extends Base { +export default class Mask extends Container { // Initialize node constructor (node) { super(nodeOrNew('mask', node), Mask) @@ -19,7 +19,8 @@ export default class Mask extends Base { }) // remove mask from parent - return remove.call(this) + return super.remove() + //return remove.call(this) } targets () { diff --git a/src/Matrix.js b/src/Matrix.js index b0a6c48..e6d3da0 100644 --- a/src/Matrix.js +++ b/src/Matrix.js @@ -3,7 +3,7 @@ import Point from './Point.js' import {delimiter} from './regex.js' import {radians} from './utils.js' import parser from './parser.js' -import Base from './Base.js' +import Element from './Element.js' import {registerMethods} from './methods.js' export default class Matrix { @@ -16,7 +16,7 @@ export default class Matrix { var base = arrayToMatrix([1, 0, 0, 1, 0, 0]) // ensure source as object - source = source instanceof Base && source.is('Element') ? source.matrixify() + source = source instanceof Element ? source.matrixify() : typeof source === 'string' ? arrayToMatrix(source.split(delimiter).map(parseFloat)) : Array.isArray(source) ? arrayToMatrix(source) : (typeof source === 'object' && isMatrixLike(source)) ? source diff --git a/src/Morphable.js b/src/Morphable.js index d927733..18f5a3b 100644 --- a/src/Morphable.js +++ b/src/Morphable.js @@ -7,6 +7,7 @@ import PointArray from './PointArray.js' import PathArray from './PathArray.js' import Box from './Box.js' import Matrix from './Matrix.js' +import {delimiter, pathLetters, numberAndUnit} from './regex.js' export default class Morphable { constructor (stepper) { @@ -58,12 +59,12 @@ export default class Morphable { } else if (type === 'string') { if (Color.isColor(value)) { this.type(Color) - } else if (regex.delimiter.test(value)) { - this.type(regex.pathLetters.test(value) + } else if (delimiter.test(value)) { + this.type(pathLetters.test(value) ? PathArray : SVGArray ) - } else if (regex.numberAndUnit.test(value)) { + } else if (numberAndUnit.test(value)) { this.type(SVGNumber) } else { this.type(NonMorphable) diff --git a/src/Parent.js b/src/Parent.js index a52b000..6786329 100644 --- a/src/Parent.js +++ b/src/Parent.js @@ -1,166 +1,169 @@ import {makeInstance, adopt} from './adopter.js' import {map} from './utils.js' import {registerMethods} from './methods.js' -import Base from './Base.js' +import Element from './Element.js' import {ns} from './namespaces.js' -// Returns all child elements -export function children () { - return map(this.node.children, function (node) { - return adopt(node) - }) -} +export default class Parent extends Element { + // Returns all child elements + children () { + return map(this.node.children, function (node) { + return adopt(node) + }) + } -// Add given element at a position -export function add (element, i) { - element = makeInstance(element) + // Add given element at a position + add (element, i) { + element = makeInstance(element) - if (i == null) { - this.node.appendChild(element.node) - } else if (element.node !== this.node.childNodes[i]) { - this.node.insertBefore(element.node, this.node.childNodes[i]) + if (i == null) { + this.node.appendChild(element.node) + } else if (element.node !== this.node.childNodes[i]) { + this.node.insertBefore(element.node, this.node.childNodes[i]) + } + + return this } - return this -} + // Basically does the same as `add()` but returns the added element instead + put (element, i) { + this.add(element, i) + return element.instance || element + } -// Basically does the same as `add()` but returns the added element instead -export function put (element, i) { - this.add(element, i) - return element.instance || element -} + // Checks if the given element is a child + has (element) { + return this.index(element) >= 0 + } -// Checks if the given element is a child -export function has (element) { - return this.index(element) >= 0 -} + // Gets index of given element + index (element) { + return [].slice.call(this.node.childNodes).indexOf(element.node) + } -// Gets index of given element -export function index (element) { - return [].slice.call(this.node.childNodes).indexOf(element.node) -} + // Get a element at the given index + get (i) { + return adopt(this.node.childNodes[i]) + } -// Get a element at the given index -export function get (i) { - return adopt(this.node.childNodes[i]) -} + // Get first child + first () { + return adopt(this.node.firstChild) + } -// Get first child -export function first () { - return adopt(this.node.firstChild) -} + // Get the last child + last () { + return adopt(this.node.lastChild) + } -// Get the last child -export function last () { - return adopt(this.node.lastChild) -} + // Iterates over all children and invokes a given block + each (block, deep) { + var children = this.children() + var i, il -// Iterates over all children and invokes a given block -export function each (block, deep) { - var children = this.children() - var i, il + for (i = 0, il = children.length; i < il; i++) { + if (children[i] instanceof Element) { + block.apply(children[i], [i, children]) + } - for (i = 0, il = children.length; i < il; i++) { - if (children[i] instanceof Base) { - block.apply(children[i], [i, children]) + if (deep && (children[i] instanceof Parent)) { + children[i].each(block, deep) + } } - if (deep && (children[i] instanceof Base && children[i].is('Parent'))) { - children[i].each(block, deep) - } + return this } - return this -} + // Remove a given child + removeElement (element) { + this.node.removeChild(element.node) -// Remove a given child -export function removeElement (element) { - this.node.removeChild(element.node) + return this + } - return this -} + // Remove all elements in this container + clear () { + // remove children + while (this.node.hasChildNodes()) { + this.node.removeChild(this.node.lastChild) + } + + // remove defs reference + delete this._defs -// Remove all elements in this container -export function clear () { - // remove children - while (this.node.hasChildNodes()) { - this.node.removeChild(this.node.lastChild) + return this } - // remove defs reference - delete this._defs + // Import raw svg + svg (svg) { + var well, len - return this -} + // act as a setter if svg is given + if (svg) { + // create temporary holder + well = document.createElementNS(ns, 'svg') + // dump raw svg + well.innerHTML = svg -// Import raw svg -export function svg (svg) { - var well, len + // transplant nodes + for (len = well.children.length; len--;) { + this.node.appendChild(well.firstElementChild) + } - // act as a setter if svg is given - if (svg) { - // create temporary holder - well = document.createElementNS(ns, 'svg') - // dump raw svg - well.innerHTML = svg + // otherwise act as a getter + } else { + // write svgjs data to the dom + this.writeDataToDom() - // transplant nodes - for (len = well.children.length; len--;) { - this.node.appendChild(well.firstElementChild) + return this.node.outerHTML } - // otherwise act as a getter - } else { - // write svgjs data to the dom - this.writeDataToDom() - - return this.node.outerHTML + return this } - return this -} - -// write svgjs data to the dom -export function writeDataToDom () { - // dump variables recursively - this.each(function () { - this.writeDataToDom() - }) + // write svgjs data to the dom + writeDataToDom () { + // dump variables recursively + this.each(function () { + this.writeDataToDom() + }) - // remove previously set data - this.node.removeAttribute('svgjs:data') + // remove previously set data + this.node.removeAttribute('svgjs:data') - if (Object.keys(this.dom).length) { - this.node.setAttribute('svgjs:data', JSON.stringify(this.dom)) // see #428 + if (Object.keys(this.dom).length) { + this.node.setAttribute('svgjs:data', JSON.stringify(this.dom)) // see #428 + } + return this } - return this -} -export function flatten (parent) { - this.each(function () { - if (this.is('Parent')) return this.flatten(parent).ungroup(parent) - return this.toParent(parent) - }) + flatten (parent) { + this.each(function () { + if (this instanceof Parent) return this.flatten(parent).ungroup(parent) + return this.toParent(parent) + }) - // we need this so that Doc does not get removed - this.node.firstElementChild || this.remove() + // we need this so that Doc does not get removed + this.node.firstElementChild || this.remove() - return this -} + return this + } -export function ungroup (parent) { - parent = parent || this.parent() + ungroup (parent) { + parent = parent || this.parent() - this.each(function () { - return this.toParent(parent) - }) + this.each(function () { + return this.toParent(parent) + }) - this.remove() + this.remove() - return this + return this + } } -registerMethods('Container', { - children, add, put, has, index, get, first, last, each, - removeElement, clear, svg, writeDataToDom, flatten, ungroup -}) + +// registerMethods('Container', { +// children, add, put, has, index, get, first, last, each, +// removeElement, clear, svg, writeDataToDom, flatten, ungroup +// }) diff --git a/src/Path.js b/src/Path.js index 7ed3c13..42ab411 100644 --- a/src/Path.js +++ b/src/Path.js @@ -1,12 +1,12 @@ import {proportionalSize} from './helpers.js' import {nodeOrNew} from './tools.js' -import Base from './Base.js' +import Shape from './Shape.js' import PathArray from './PathArray.js' import find from './selector.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Path extends Base { +export default class Path extends Shape { // Initialize node constructor (node) { super(nodeOrNew('path', node), Path) diff --git a/src/Pattern.js b/src/Pattern.js index 2c61baf..0c26d79 100644 --- a/src/Pattern.js +++ b/src/Pattern.js @@ -1,10 +1,11 @@ -import Base from './Base.js' +import Container from './Container.js' import {nodeOrNew} from './tools.js' -import attr from './attr.js' +//import attr from './attr.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' +import Box from './Box.js' -export default class Pattern extends Base { +export default class Pattern extends Container { // Initialize node constructor (node) { super(nodeOrNew('pattern', node), Pattern) @@ -36,12 +37,17 @@ export default class Pattern extends Base { // custom attr to handle transform attr (a, b, c) { if (a === 'transform') a = 'patternTransform' - return attr.call(this, a, b, c) + return super.attr(a, b, c) + //return attr.call(this, a, b, c) } targets () { return find('svg [fill*="' + this.id() + '"]') } + + bbox () { + return new Box() + } } registerMethods({ diff --git a/src/Polygon.js b/src/Polygon.js index 69337e3..1272e44 100644 --- a/src/Polygon.js +++ b/src/Polygon.js @@ -1,5 +1,5 @@ import {proportionalSize} from './helpers.js' -import Base from './Base.js' +import Shape from './Shape.js' import {nodeOrNew, extend} from './tools.js' import * as pointed from './pointed.js' import * as poly from './poly.js' @@ -7,7 +7,7 @@ import PointArray from './PointArray.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Polygon extends Base { +export default class Polygon extends Shape { // Initialize node constructor (node) { super(nodeOrNew('polygon', node), Polygon) diff --git a/src/Polyline.js b/src/Polyline.js index 4fad379..d651abd 100644 --- a/src/Polyline.js +++ b/src/Polyline.js @@ -1,4 +1,4 @@ -import Base from './Base.js' +import Shape from './Shape.js' import {nodeOrNew, extend} from './tools.js' import PointArray from './PointArray.js' import * as pointed from './pointed.js' @@ -6,7 +6,7 @@ import * as poly from './poly.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Polyline extends Base { +export default class Polyline extends Shape { // Initialize node constructor (node) { super(nodeOrNew('polyline', node), Polyline) diff --git a/src/Rect.js b/src/Rect.js index 037064c..232f591 100644 --- a/src/Rect.js +++ b/src/Rect.js @@ -1,13 +1,24 @@ -import Base from './Base.js' +import Shape from './Shape.js' import {nodeOrNew, extend} from './tools.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Rect extends Base { +export default class Rect extends Shape { // Initialize node constructor (node) { super(nodeOrNew('rect', node), Rect) } + + // FIXME: unify with circle + // Radius x value + rx (rx) { + return this.attr('rx', rx) + } + + // Radius y value + ry (ry) { + return this.attr('ry', ry) + } } registerMethods({ diff --git a/src/SVGArray.js b/src/SVGArray.js index bb98aad..5927945 100644 --- a/src/SVGArray.js +++ b/src/SVGArray.js @@ -17,19 +17,22 @@ extend2(SVGArray, { }, toArray () { - const ret = [] - ret.push(...this) - //Array.prototype.push.apply(ret, this) - return ret - //return Array.prototype.concat.apply([], this) + // const ret = [] + // ret.push(...this) + // return ret + return Array.prototype.concat.apply([], this) }, toString () { return this.join(' ') }, + // Flattens the array if needed valueOf () { - return this.toArray() + const ret = [] + ret.push(...this) + return ret + // return this.toArray() }, // Parse whitespace separated string diff --git a/src/Shape.js b/src/Shape.js new file mode 100644 index 0000000..bf4ae8f --- /dev/null +++ b/src/Shape.js @@ -0,0 +1,2 @@ +import Parent from './Parent.js' +export default class Shape extends Parent {} diff --git a/src/Stop.js b/src/Stop.js index 0cd21e6..7db6027 100644 --- a/src/Stop.js +++ b/src/Stop.js @@ -1,9 +1,9 @@ -import Base from './Base.js' +import Element from './Element.js' import SVGNumber from './SVGNumber.js' import {nodeOrNew} from './tools.js' import {register} from './adopter.js' -export default class Stop extends Base { +export default class Stop extends Element { constructor (node) { super(nodeOrNew('stop', node), Stop) } diff --git a/src/Symbol.js b/src/Symbol.js index fbd4f3b..22d85da 100644 --- a/src/Symbol.js +++ b/src/Symbol.js @@ -1,9 +1,9 @@ -import Base from './Base.js' +import Container from './Container.js' import {nodeOrNew} from './tools.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' -export default class Symbol extends Base { +export default class Symbol extends Container { // Initialize node constructor (node) { super(nodeOrNew('symbol', node), Symbol) diff --git a/src/Text.js b/src/Text.js index 02a601b..239b429 100644 --- a/src/Text.js +++ b/src/Text.js @@ -1,4 +1,4 @@ -import Base from './Base.js' +import Parent from './Parent.js' import SVGNumber from './SVGNumber.js' import {nodeOrNew, extend} from './tools.js' import {attrs} from './defaults.js' @@ -6,7 +6,7 @@ import * as textable from './textable.js' import {register, adopt} from './adopter.js' import {registerMethods} from './methods.js' -export default class Text extends Base { +export default class Text extends Parent { // Initialize node constructor (node) { super(nodeOrNew('text', node), Text) diff --git a/src/Tspan.js b/src/Tspan.js index e2e14e3..677adf4 100644 --- a/src/Tspan.js +++ b/src/Tspan.js @@ -1,11 +1,11 @@ -import Base from './Base.js' +import Parent from './Parent.js' import {nodeOrNew, extend} from './tools.js' import * as textable from './textable.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' import Text from './Text.js' -export default class Tspan extends Base { +export default class Tspan extends Parent { // Initialize node constructor (node) { super(nodeOrNew('tspan', node), Tspan) @@ -1,10 +1,10 @@ -import Base from './Base.js' +import Shape from './Shape.js' import {xlink} from './namespaces.js' import {register} from './adopter.js' import {registerMethods} from './methods.js' import {nodeOrNew} from './tools.js' -export default class Use extends Base { +export default class Use extends Shape { constructor (node) { super(nodeOrNew('use', node), Use) } diff --git a/src/classes.js b/src/classes.js index 7241d90..8385c20 100644 --- a/src/classes.js +++ b/src/classes.js @@ -1,3 +1,8 @@ +export {default as EventTarget} from './EventTarget.js' +export {default as Element} from './Element.js' +export {default as Shape} from './Shape.js' +export {default as Parent} from './Parent.js' +export {default as Container} from './Container.js' export {default as HtmlNode} from './HtmlNode.js' export {default as Doc} from './Doc.js' export {default as Defs} from './Defs.js' diff --git a/src/event.js b/src/event.js index 9fa99e1..acc4dd6 100644 --- a/src/event.js +++ b/src/event.js @@ -1,42 +1,10 @@ -import Base from './Base.js' import {delimiter} from './regex.js' import {registerMethods} from './methods.js' -// Add events to elements -const methods = [ 'click', - 'dblclick', - 'mousedown', - 'mouseup', - 'mouseover', - 'mouseout', - 'mousemove', - 'mouseenter', - 'mouseleave', - 'touchstart', - 'touchmove', - 'touchleave', - 'touchend', - 'touchcancel' ].reduce(function (last, event) { - // add event to Element - const fn = function (f) { - if (f === null) { - off(this, event) - } else { - on(this, event, f) - } - return this - } - - last[event] = fn - return last - }, {}) - -registerMethods('Element', methods) - let listenerId = 0 function getEventTarget (node) { - return node instanceof Base && node.is('EventTarget') + return typeof node.getEventTarget === 'function' ? node.getEventTarget() : node } diff --git a/src/pointed.js b/src/pointed.js index 11df4f3..d5deaf1 100644 --- a/src/pointed.js +++ b/src/pointed.js @@ -1,6 +1,6 @@ import PointArray from './PointArray.js' -export let MorphArray = PointArray +export let MorphArray = PointArray // Move by left top corner over x-axis export function x (x) { diff --git a/src/selector.js b/src/selector.js index fcd7363..973787d 100644 --- a/src/selector.js +++ b/src/selector.js @@ -37,4 +37,4 @@ export function find (query) { return baseFind(query, this.node) } -registerMethods('Container', {find}) +registerMethods('Element', {find}) diff --git a/src/sugar.js b/src/sugar.js index 9a075a0..e5d6b61 100644 --- a/src/sugar.js +++ b/src/sugar.js @@ -122,7 +122,7 @@ registerMethods(['Element', 'Runner'], { registerMethods('radius', { // Add x and y radius radius: function (x, y) { - var type = (this._target || this).type + var type = (this._element || this).type return type === 'radialGradient' || type === 'radialGradient' ? this.attr('r', new SVGNumber(x)) : this.rx(x).ry(y == null ? x : y) @@ -140,7 +140,7 @@ registerMethods('Path', { } }) -registerMethods(['Container', 'Runner'], { +registerMethods(['Parent', 'Runner'], { // Set font font: function (a, v) { if (typeof a === 'object') { @@ -58,21 +58,11 @@ extend([ Classes.Gradient ], getMethodsFor('radius')) -const containerMethods = getMethodsFor('Container') -// FIXME: We need a container array -for (let i in containers) { - extend(containers[i], containerMethods) -} - -const elementMethods = getMethodsFor('Element') -const eventTargetMethods = getMethodsFor('EventTarget') -for (let i in elements) { - extend(elements[i], elementMethods) - extend(elements[i], eventTargetMethods) - extend(elements[i], getConstructor('EventTarget')) - extend(elements[i], getConstructor('Element')) - extend(elements[i], getConstructor('Memory')) -} +extend(Classes.EventTarget, getMethodsFor('EventTarget')) +extend(Classes.Element, getMethodsFor('Element')) +extend(Classes.Element, getMethodsFor('Parent')) +extend(Classes.Element, getConstructor('Memory')) +extend(Classes.Container, getMethodsFor('Container')) registerMorphableType([ Classes.SVGNumber, @@ -102,15 +92,13 @@ import * as regex from './regex.js' SVG.regex = regex - - // satisfy tests, fix later -import * as ns from './namespaces' +import * as ns from './namespaces.js' SVG.get = SVG SVG.find = find Object.assign(SVG, ns) -import Base from './Base.js' -SVG.Element = SVG.Parent = SVG.Shape = SVG.Container = Base +// import Base from './Base.js' +// SVG.Element = SVG.Parent = SVG.Shape = SVG.Container = Base import {easing} from './Controller.js' SVG.easing = easing import * as events from './event.js' @@ -121,3 +109,5 @@ SVG.ObjectBag = ObjectBag SVG.NonMorphable = NonMorphable import parser from './parser.js' SVG.parser = parser +import * as defaults from './defaults.js' +SVG.defaults = defaults diff --git a/src/tools.js b/src/tools.js index 4dc381e..d33566a 100644 --- a/src/tools.js +++ b/src/tools.js @@ -18,11 +18,7 @@ export function extend (modules, methods) { modules = Array.isArray(modules) ? modules : [modules] for (i = modules.length - 1; i >= 0; i--) { - if (methods.name) { - modules[i].extensions = (modules[i].extensions || []).concat(methods) - } for (key in methods) { - if (modules[i].prototype[key] || key == 'name' || key == 'setup') continue modules[i].prototype[key] = methods[key] } } |