summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorSaivan <savian@me.com>2018-03-02 12:48:43 +1100
committerSaivan <savian@me.com>2018-03-02 12:48:43 +1100
commita208ed5c5de4b654efc54c2bcbe8dc7d4875392d (patch)
treed435e0e1e1b926f2fb3484717728b21f96c7a78e /src
parent1582edb4236628fbc7875242f159c16283b769c2 (diff)
parentc4373581ab49dff509a857eb4e896f00fc81add6 (diff)
downloadsvg.js-a208ed5c5de4b654efc54c2bcbe8dc7d4875392d.tar.gz
svg.js-a208ed5c5de4b654efc54c2bcbe8dc7d4875392d.zip
Fixed some tests involving transforms and elements
Diffstat (limited to 'src')
-rw-r--r--src/HtmlNode.js10
-rw-r--r--src/boxes.js2
-rw-r--r--src/doc.js40
-rw-r--r--src/element.js8
-rw-r--r--src/event.js139
-rw-r--r--src/flatten.js2
-rw-r--r--src/matrix.js2
-rw-r--r--src/nested.js16
-rw-r--r--src/parent.js6
-rw-r--r--src/parser.js2
-rw-r--r--src/svg.js8
11 files changed, 112 insertions, 123 deletions
diff --git a/src/HtmlNode.js b/src/HtmlNode.js
index 30cb4cf..e7dae10 100644
--- a/src/HtmlNode.js
+++ b/src/HtmlNode.js
@@ -8,15 +8,9 @@ SVG.HtmlNode = SVG.invent({
extend: {
add: function (element, i) {
element = createElement(element)
- if (element instanceof SVG.Nested) {
- element = new SVG.Doc(element.node)
- element.setData(JSON.parse(element.node.getAttribute('svgjs:data')) || {})
- }
- if (i === null) {
- this.node.appendChild(element.node)
- } else if (element.node !== this.node.children[i]) {
- this.node.insertBefore(element.node, this.node.children[i])
+ if (element.node !== this.node.children[i]) {
+ this.node.insertBefore(element.node, this.node.children[i] || null)
}
return this
diff --git a/src/boxes.js b/src/boxes.js
index cd90207..f14b331 100644
--- a/src/boxes.js
+++ b/src/boxes.js
@@ -126,7 +126,7 @@ SVG.Box = SVG.invent({
}
})
-SVG.extend([SVG.Doc, SVG.Nested, SVG.Symbol, SVG.Image, SVG.Pattern, SVG.Marker, SVG.ForeignObject, SVG.View], {
+SVG.extend([SVG.Doc, SVG.Symbol, SVG.Image, SVG.Pattern, SVG.Marker, SVG.ForeignObject, SVG.View], {
viewbox: function (x, y, width, height) {
// act as getter
if (x == null) return new SVG.Box(this.attr('viewBox'))
diff --git a/src/doc.js b/src/doc.js
index 2097747..72ea59c 100644
--- a/src/doc.js
+++ b/src/doc.js
@@ -4,7 +4,7 @@ SVG.Doc = SVG.invent({
this.constructor(node || SVG.create('svg'))
// set svg element attributes and ensure defs node
- this.namespace().defs()
+ this.namespace()
},
// Inherit from
@@ -12,8 +12,17 @@ SVG.Doc = SVG.invent({
// Add class methods
extend: {
+ isRoot: function () {
+ return !this.node.parentNode || !(this.node.parentNode instanceof window.SVGElement) || this.node.parentNode.nodeName === '#document'
+ },
+ // Check if this is a root svg. If not, call docs from this element
+ doc: function () {
+ if (this.isRoot()) return this
+ return SVG.Element.prototype.doc.call(this)
+ },
// Add namespaces
namespace: function () {
+ if (!this.isRoot()) return this.doc().namespace()
return this
.attr({ xmlns: SVG.ns, version: '1.1' })
.attr('xmlns:xlink', SVG.xlink, SVG.xmlns)
@@ -21,14 +30,23 @@ SVG.Doc = SVG.invent({
},
// Creates and returns defs element
defs: function () {
+ if (!this.isRoot()) return this.doc().defs()
return SVG.adopt(this.node.getElementsByTagName('defs')[0]) || this.put(new SVG.Defs())
},
// custom parent method
- parent: function () {
- return this.node.parentNode.nodeName === '#document' ? null : this.node.parentNode
+ parent: function (type) {
+ if (this.isRoot()) {
+ return this.node.parentNode.nodeName === '#document' ? null : this.node.parentNode
+ }
+
+ return SVG.Element.prototype.parent.call(this, type)
},
- // Removes the doc from the DOM
+ // Removes the doc from the DOM
remove: function () {
+ if (!this.isRoot()) {
+ return SVG.Element.prototype.remove.call(this)
+ }
+
if (this.parent()) {
this.parent().removeChild(this.node)
}
@@ -41,14 +59,12 @@ SVG.Doc = SVG.invent({
this.node.removeChild(this.node.lastChild)
}
return this
- },
- toNested: function () {
- var el = SVG.create('svg')
- this.node.instance = null
- el.appendChild(this.node)
-
- return SVG.adopt(this.node)
+ }
+ },
+ construct: {
+ // Create nested svg document
+ nested: function () {
+ return this.put(new SVG.Doc())
}
}
-
})
diff --git a/src/element.js b/src/element.js
index eca535b..0d08579 100644
--- a/src/element.js
+++ b/src/element.js
@@ -3,8 +3,8 @@
SVG.Element = SVG.invent({
// Initialize node
create: function (node) {
- // last fired event on node
- this._event = null
+ // event listener
+ this.events = {}
// initialize data object
this.dom = {}
@@ -14,6 +14,7 @@ SVG.Element = SVG.invent({
if (this.node) {
this.type = node.nodeName
this.node.instance = this
+ this.events = node.events || {}
if (node.hasAttribute('svgjs:data')) {
// pull svgjs data from the dom (getAttributeNS doesn't work in html5)
@@ -217,7 +218,8 @@ SVG.Element = SVG.invent({
// Get parent document
doc: function () {
- return this instanceof SVG.Doc ? this : this.parent(SVG.Doc)
+ var p = this.parent(SVG.Doc)
+ return p && p.doc()
},
// Get defs
diff --git a/src/event.js b/src/event.js
index c53e0b3..65b13b0 100644
--- a/src/event.js
+++ b/src/event.js
@@ -1,4 +1,5 @@
// Add events to elements
+
;[ 'click',
'dblclick',
'mousedown',
@@ -6,14 +7,14 @@
'mouseover',
'mouseout',
'mousemove',
- // , 'mouseenter' -> not supported by IE
- // , 'mouseleave' -> not supported by IE
+ 'mouseenter',
+ 'mouseleave',
'touchstart',
'touchmove',
'touchleave',
'touchend',
'touchcancel' ].forEach(function (event) {
- // add event to SVG.Element
+ // add event to SVG.Element
SVG.Element.prototype[event] = function (f) {
// bind event to element rather than element node
SVG.on(this, event, f)
@@ -21,32 +22,31 @@
}
})
-// Initialize listeners stack
-SVG.listeners = []
-SVG.handlerMap = []
SVG.listenerId = 0
// Add event binder in the SVG namespace
SVG.on = function (node, events, listener, binding, options) {
+ var l = listener.bind(binding || node)
+ var n = node instanceof SVG.Element ? node.node : node
+
+ // ensure instance object for nodes which are not adopted
+ n.instance = n.instance || {events: {}}
+
+ var bag = n.instance.events
+
+ // add id to listener
+ if (!listener._svgjsListenerId) { listener._svgjsListenerId = ++SVG.listenerId }
+
events.split(SVG.regex.delimiter).forEach(function (event) {
- // create listener, get object-index
- var l = listener.bind(binding || node)
- var n = node instanceof SVG.Element ? node.node : node
- var index = (SVG.handlerMap.indexOf(n) + 1 || SVG.handlerMap.push(n)) - 1
var ev = event.split('.')[0]
var ns = event.split('.')[1] || '*'
// ensure valid object
- SVG.listeners[index] = SVG.listeners[index] || {}
- SVG.listeners[index][ev] = SVG.listeners[index][ev] || {}
- SVG.listeners[index][ev][ns] = SVG.listeners[index][ev][ns] || {}
-
- if (!listener._svgjsListenerId) {
- listener._svgjsListenerId = ++SVG.listenerId
- }
+ bag[ev] = bag[ev] || {}
+ bag[ev][ns] = bag[ev][ns] || {}
// reference listener
- SVG.listeners[index][ev][ns][listener._svgjsListenerId] = l
+ bag[ev][ns][listener._svgjsListenerId] = l
// add listener
n.addEventListener(ev, l, options || false)
@@ -54,91 +54,84 @@ SVG.on = function (node, events, listener, binding, options) {
}
// Add event unbinder in the SVG namespace
-SVG.off = function (node, event, listener) {
- var index = SVG.handlerMap.indexOf(node)
- var ev = event && event.split('.')[0]
- var ns = event && event.split('.')[1]
- var namespace = ''
-
- if (index === -1) return
+SVG.off = function (node, events, listener, options) {
+ var n = node instanceof SVG.Element ? node.node : node
+ if (!n.instance) return
- if (listener) {
- if (typeof listener === 'function') listener = listener._svgjsListenerId
+ // listener can be a function or a number
+ if (typeof listener === 'function') {
+ listener = listener._svgjsListenerId
if (!listener) return
+ }
- // remove listener reference
- if (SVG.listeners[index][ev] && SVG.listeners[index][ev][ns || '*']) {
- // remove listener
- node.removeEventListener(ev, SVG.listeners[index][ev][ns || '*'][listener], false)
+ var bag = n.instance.events
- delete SVG.listeners[index][ev][ns || '*'][listener]
- }
- } else if (ns && ev) {
- // remove all listeners for a namespaced event
- if (SVG.listeners[index][ev] && SVG.listeners[index][ev][ns]) {
- for (listener in SVG.listeners[index][ev][ns]) {
- SVG.off(node, [ev, ns].join('.'), listener)
+ ;(events || '').split(SVG.regex.delimiter).forEach(function (event) {
+ var ev = event && event.split('.')[0]
+ var ns = event && event.split('.')[1]
+ var namespace, l
+
+ if (listener) {
+ // remove listener reference
+ if (bag[ev] && bag[ev][ns || '*']) {
+ // removeListener
+ n.removeEventListener(ev, bag[ev][ns || '*'][listener], options || false)
+
+ delete bag[ev][ns || '*'][listener]
}
+ } else if (ev && ns) {
+ // remove all listeners for a namespaced event
+ if (bag[ev] && bag[ev][ns]) {
+ for (l in bag[ev][ns]) { SVG.off(n, [ev, ns].join('.'), l) }
- delete SVG.listeners[index][ev][ns]
- }
- } else if (ns) {
- // remove all listeners for a specific namespace
- for (event in SVG.listeners[index]) {
- for (namespace in SVG.listeners[index][event]) {
- if (ns === namespace) {
- SVG.off(node, [event, ns].join('.'))
+ delete bag[ev][ns]
+ }
+ } else if (ns) {
+ // remove all listeners for a specific namespace
+ for (event in bag) {
+ for (namespace in bag[event]) {
+ if (ns === namespace) { SVG.off(n, [event, ns].join('.')) }
}
}
- }
- } else if (ev) {
- // remove all listeners for the event
- if (SVG.listeners[index][ev]) {
- for (namespace in SVG.listeners[index][ev]) {
- SVG.off(node, [ev, namespace].join('.'))
+ } else if (ev) {
+ // remove all listeners for the event
+ if (bag[ev]) {
+ for (namespace in bag[ev]) { SVG.off(n, [ev, namespace].join('.')) }
+
+ delete bag[ev]
}
+ } else {
+ // remove all listeners on a given node
+ for (event in bag) { SVG.off(n, event) }
- delete SVG.listeners[index][ev]
- }
- } else {
- // remove all listeners on a given node
- for (event in SVG.listeners[index]) {
- SVG.off(node, event)
+ n.instance.events = {}
}
-
- delete SVG.listeners[index]
- delete SVG.handlerMap[index]
- }
+ })
}
-//
SVG.extend(SVG.Element, {
// Bind given event to listener
on: function (event, listener, binding, options) {
SVG.on(this, event, listener, binding, options)
return this
},
-
// Unbind event from listener
off: function (event, listener) {
SVG.off(this.node, event, listener)
return this
},
-
- // Fire given event
- fire: function (event, data) {
+ dispatch: function (event, data) {
// Dispatch event
if (event instanceof window.Event) {
this.node.dispatchEvent(event)
} else {
this.node.dispatchEvent(event = new window.CustomEvent(event, {detail: data, cancelable: true}))
}
-
- this._event = event
- return this
+ return event
},
-
- event: function () {
- return this._event
+ // Fire given event
+ fire: function (event, data) {
+ this.dispatch(event, data)
+ return this
}
})
diff --git a/src/flatten.js b/src/flatten.js
index 1c32a76..3ba6e22 100644
--- a/src/flatten.js
+++ b/src/flatten.js
@@ -2,7 +2,7 @@ SVG.extend(SVG.Parent, {
flatten: function (parent) {
if (this instanceof SVG.Defs) return this
- parent = parent || (this instanceof SVG.Doc ? this : this.parent(SVG.Parent))
+ parent = parent || (this instanceof SVG.Doc && this.isRoot() ? this : this.parent(SVG.Parent))
this.each(function () {
if (this instanceof SVG.Defs) return this
diff --git a/src/matrix.js b/src/matrix.js
index 970f6ed..557010c 100644
--- a/src/matrix.js
+++ b/src/matrix.js
@@ -270,7 +270,7 @@ SVG.Matrix = SVG.invent({
This is needed because FF does not return the transformation matrix
for the inner coordinate system when getScreenCTM() is called on nested svgs.
However all other Browsers do that */
- if (this instanceof SVG.Nested) {
+ if (this instanceof SVG.Doc && !this.isRoot()) {
var rect = this.rect(1, 1)
var m = rect.node.getScreenCTM()
rect.remove()
diff --git a/src/nested.js b/src/nested.js
deleted file mode 100644
index 217d59a..0000000
--- a/src/nested.js
+++ /dev/null
@@ -1,16 +0,0 @@
-
-SVG.Nested = SVG.invent({
- // Initialize node
- create: 'svg',
-
- // Inherit from
- inherit: SVG.Container,
-
- // Add parent method
- construct: {
- // Create nested svg document
- nested: function () {
- return this.put(new SVG.Nested())
- }
- }
-})
diff --git a/src/parent.js b/src/parent.js
index 0ff1765..d48e086 100644
--- a/src/parent.js
+++ b/src/parent.js
@@ -21,10 +21,8 @@ SVG.Parent = SVG.invent({
add: function (element, i) {
element = createElement(element)
- if (i == null) {
- this.node.appendChild(element.node)
- } else if (element.node !== this.node.children[i]) {
- this.node.insertBefore(element.node, this.node.children[i])
+ if (element.node !== this.node.children[i]) {
+ this.node.insertBefore(element.node, this.node.children[i] || null)
}
return this
diff --git a/src/parser.js b/src/parser.js
index c3ab7a4..84c8d77 100644
--- a/src/parser.js
+++ b/src/parser.js
@@ -11,7 +11,7 @@ SVG.parser = function () {
}
SVG.parser.nodes = {
- svg: new SVG.Nested().size(2, 0).css({
+ svg: SVG().size(2, 0).css({
opacity: 0,
position: 'absolute',
left: '-100%',
diff --git a/src/svg.js b/src/svg.js
index e6903da..9b3bfd6 100644
--- a/src/svg.js
+++ b/src/svg.js
@@ -77,7 +77,7 @@ SVG.adopt = function (node) {
if (!node) return null
// make sure a node isn't already adopted
- if (node.instance) return node.instance
+ if (node.instance instanceof SVG.Element) return node.instance
if (!(node instanceof window.SVGElement)) {
return new SVG.HtmlNode(node)
@@ -88,12 +88,14 @@ SVG.adopt = function (node) {
// adopt with element-specific settings
if (node.nodeName === 'svg') {
- element = node.parentNode instanceof window.SVGElement ? new SVG.Nested(node) : new SVG.Doc(node)
+ element = new SVG.Doc(node)
} else if (node.nodeName === 'linearGradient' || node.nodeName === 'radialGradient') {
element = new SVG.Gradient(node)
} else if (SVG[capitalize(node.nodeName)]) {
element = new SVG[capitalize(node.nodeName)](node)
- } else { element = new SVG.Parent(node) }
+ } else {
+ element = new SVG.Parent(node)
+ }
return element
}