Skip to content

Commit f0dc4d5

Browse files
author
wout
committed
Added SVG.Bare for creation of non-described elements
1 parent c2d1b29 commit f0dc4d5

15 files changed

Lines changed: 251 additions & 216 deletions

File tree

CHANGELOG.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@
33
- added `morph()` method to `SVG.PathArray` -> __TODO!__
44
- added `rotate()` method to linear gradients -> __TODO!__
55
- added `'random'` option and `randomize()` method to `SVG.Color` -> __TODO!__
6-
- added `SVG.Title` and `SVG.Desc` -> __TODO!__
76

87
# 1.0.0-rc.10 (?/08/2014)
98

@@ -40,6 +39,8 @@
4039
- renamed `SVG.SetFX` to `SVG.FX.Set`
4140
- added distinction between relative and absolute matrix transformations -> __TODO!__
4241
- added specs for `SVG.FX` -> __TODO!__
42+
- implemented the `element()` method using the `SVG.Bare` class to create elements that are not described by SVG.js
43+
- removed `SVG.Symbol` but kept the `symbol()` method using the new `element()` method
4344

4445
# 1.0.0-rc.9 (17/06/2014)
4546

README.md

Lines changed: 32 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -798,10 +798,40 @@ symbol.rect(100, 100).fill('#f09')
798798
var use = draw.use(symbol).move(200, 200)
799799
```
800800

801-
__`returns`: `SVG.Symbol`__
801+
__`returns`: `SVG.Bare`__
802802

803-
_Javascript inheritance stack: `SVG.Symbol` < `SVG.Container` < `SVG.Element`_
803+
_Javascript inheritance stack: `SVG.Bare` < `SVG.Element` [with a shallow inheritance from `SVG.Parent`]_
804804

805+
## Bare
806+
For all SVG elements that are not described by SVG.js, the `SVG.Bare` class comes in handy. This class inherits directly from `SVG.Element` and makes it possible to add custom methods in a separate namespace.
807+
808+
### element()
809+
the `SVG.Bare` class can be instantiated with the `element()` method on any parent element:
810+
811+
```javascript
812+
var element = draw.element('title')
813+
```
814+
The stirng value passed as the first argument is the node name that should be generated.
815+
816+
Additionally the class name can be passed as the second argument from which the element should inherit:
817+
818+
```javascript
819+
var element = draw.element('symbol', SVG.Parent)
820+
```
821+
822+
This gives you as the user a lot of power. But remember, with great power comes great responsibility.
823+
824+
__`returns`: `SVG.Bare`__
825+
826+
### words()
827+
The `SVG.Bare` instance carries an additional method to add plain text:
828+
829+
```javascript
830+
var element = draw.element('title').words('This is a title.')
831+
//-> <title>This is a title.</title>
832+
```
833+
834+
__`returns`: `itself`__
805835

806836
## Referencing elements
807837

dist/svg.js

Lines changed: 85 additions & 94 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
* @copyright Wout Fierens <wout@impinc.co.uk>
77
* @license MIT
88
*
9-
* BUILT: Fri Aug 01 2014 15:10:13 GMT+0200 (CEST)
9+
* BUILT: Fri Aug 01 2014 20:15:09 GMT+0200 (CEST)
1010
*/
1111
;(function() {
1212
// The main wrapping element
@@ -902,15 +902,15 @@ SVG.extend(SVG.ViewBox, {
902902
SVG.Element = SVG.invent({
903903
// Initialize node
904904
create: function(node) {
905-
// Make stroke value accessible dynamically
905+
// make stroke value accessible dynamically
906906
this._stroke = SVG.defaults.attrs.stroke
907907

908-
// Create circular reference
908+
// create circular reference
909909
if (this.node = node) {
910910
this.type = node.nodeName
911911
this.node.instance = this
912912

913-
// Store current attribute value
913+
// store current attribute value
914914
this._stroke = node.getAttribute('stroke') || this._stroke
915915
}
916916
}
@@ -1085,7 +1085,7 @@ SVG.Element = SVG.invent({
10851085
// act as a setter if svg is given
10861086
if (svg && this instanceof SVG.Parent) {
10871087
// dump raw svg
1088-
well.innerHTML = '<svg>' + svg + '</svg>'
1088+
well.innerHTML = '<svg>' + svg.replace(/\n/, '').replace(/<(\w+)([^<]+?)\/>/g, '<$1$2></$1>') + '</svg>'
10891089

10901090
// transplant nodes
10911091
for (var i = 0, il = well.firstChild.childNodes.length; i < il; i++)
@@ -2149,55 +2149,6 @@ SVG.Container = SVG.invent({
21492149
}
21502150
}
21512151

2152-
})
2153-
SVG.extend(SVG.Parent, SVG.Text, {
2154-
// Import svg SVG data
2155-
svg: function(svg) {
2156-
// create temporary div to receive svg content
2157-
var element = document.createElement('div')
2158-
2159-
if (svg) {
2160-
// strip away newlines and properly close tags
2161-
svg = svg
2162-
.replace(/\n/, '')
2163-
.replace(/<(\w+)([^<]+?)\/>/g, '<$1$2></$1>')
2164-
2165-
// ensure SVG wrapper for correct element type casting
2166-
element.innerHTML = '<svg>' + svg + '</svg>'
2167-
2168-
// transplant content from well to target
2169-
for (var i = element.firstChild.childNodes.length - 1; i >= 0; i--)
2170-
if (element.firstChild.childNodes[i].nodeType == 1)
2171-
this.node.appendChild(element.firstChild.childNodes[i])
2172-
2173-
return this
2174-
2175-
} else {
2176-
// clone element and its contents
2177-
var clone = this.node.cloneNode(true)
2178-
2179-
// add target to clone
2180-
element.appendChild(clone)
2181-
2182-
return element.innerHTML
2183-
}
2184-
}
2185-
})
2186-
//
2187-
SVG.extend(SVG.Element, SVG.FX, {
2188-
// Relative move over x axis
2189-
dx: function(x) {
2190-
return this.x((this.target || this).x() + x)
2191-
}
2192-
// Relative move over y axis
2193-
, dy: function(y) {
2194-
return this.y((this.target || this).y() + y)
2195-
}
2196-
// Relative move over x and y axes
2197-
, dmove: function(x, y) {
2198-
return this.dx(x).dy(y)
2199-
}
2200-
22012152
})
22022153
// Add events to elements
22032154
;[ 'click'
@@ -2762,21 +2713,49 @@ SVG.Shape = SVG.invent({
27622713

27632714
})
27642715

2765-
SVG.Symbol = SVG.invent({
2766-
// Initialize node
2767-
create: 'symbol'
2716+
SVG.Bare = SVG.invent({
2717+
// Initialize
2718+
create: function(element, inherit) {
2719+
// construct element
2720+
this.constructor.call(this, SVG.create(element))
27682721

2769-
// Inherit from
2770-
, inherit: SVG.Container
2722+
// inherit custom methods
2723+
if (inherit)
2724+
for (var method in inherit.prototype)
2725+
if (typeof inherit.prototype[method] === 'function')
2726+
element[method] = inherit.prototype[method]
2727+
}
2728+
2729+
// Inherit from
2730+
, inherit: SVG.Element
2731+
2732+
// Add methods
2733+
, extend: {
2734+
// Insert some plain text
2735+
words: function(text) {
2736+
// remove contents
2737+
while (this.node.hasChildNodes())
2738+
this.node.removeChild(this.node.lastChild)
2739+
2740+
// create text node
2741+
this.node.appendChild(document.createTextNode(text))
2742+
2743+
return this
2744+
}
2745+
}
2746+
})
2747+
2748+
2749+
SVG.extend(SVG.Parent, {
2750+
// Create an element that is not described by SVG.js
2751+
element: function(element, inherit) {
2752+
return this.put(new SVG.Bare(element, inherit))
2753+
}
2754+
// Add symbol element
2755+
, symbol: function() {
2756+
return this.defs().element('symbol', SVG.Container)
2757+
}
27712758

2772-
// Add parent method
2773-
, construct: {
2774-
// Create a new symbol
2775-
symbol: function() {
2776-
return this.defs().put(new SVG.Symbol)
2777-
}
2778-
}
2779-
27802759
})
27812760
SVG.Use = SVG.invent({
27822761
// Initialize node
@@ -3151,11 +3130,11 @@ SVG.Text = SVG.invent({
31513130
create: function() {
31523131
this.constructor.call(this, SVG.create('text'))
31533132

3154-
this._leading = new SVG.Number(1.3) /* store leading value for rebuilding */
3155-
this._rebuild = true /* enable automatic updating of dy values */
3156-
this._build = false /* disable build mode for adding multiple lines */
3133+
this._leading = new SVG.Number(1.3) // store leading value for rebuilding
3134+
this._rebuild = true // enable automatic updating of dy values
3135+
this._build = false // disable build mode for adding multiple lines
31573136

3158-
/* set default font */
3137+
// set default font
31593138
this.attr('font-family', SVG.defaults.attrs['font-family'])
31603139
}
31613140

@@ -3166,11 +3145,11 @@ SVG.Text = SVG.invent({
31663145
, extend: {
31673146
// Move over x-axis
31683147
x: function(x) {
3169-
/* act as getter */
3148+
// act as getter
31703149
if (x == null)
31713150
return this.attr('x')
31723151

3173-
/* move lines as well if no textPath is present */
3152+
// move lines as well if no textPath is present
31743153
if (!this.textPath)
31753154
this.lines.each(function() { if (this.newLined) this.x(x) })
31763155

@@ -3181,7 +3160,7 @@ SVG.Text = SVG.invent({
31813160
var oy = this.attr('y')
31823161
, o = typeof oy === 'number' ? oy - this.bbox().y : 0
31833162

3184-
/* act as getter */
3163+
// act as getter
31853164
if (y == null)
31863165
return typeof oy === 'number' ? oy - o : oy
31873166

@@ -3197,26 +3176,26 @@ SVG.Text = SVG.invent({
31973176
}
31983177
// Set the text content
31993178
, text: function(text) {
3200-
/* act as getter */
3179+
// act as getter
32013180
if (typeof text === 'undefined') return this.content
32023181

3203-
/* remove existing content */
3182+
// remove existing content
32043183
this.clear().build(true)
32053184

32063185
if (typeof text === 'function') {
3207-
/* call block */
3186+
// call block
32083187
text.call(this, this)
32093188

32103189
} else {
3211-
/* store text and make sure text is not blank */
3190+
// store text and make sure text is not blank
32123191
text = (this.content = text).split('\n')
32133192

3214-
/* build new lines */
3193+
// build new lines
32153194
for (var i = 0, il = text.length; i < il; i++)
32163195
this.tspan(text[i]).newLine()
32173196
}
32183197

3219-
/* disable build mode and rebuild lines */
3198+
// disable build mode and rebuild lines
32203199
return this.build(false).rebuild()
32213200
}
32223201
// Set font size
@@ -3225,22 +3204,22 @@ SVG.Text = SVG.invent({
32253204
}
32263205
// Set / get leading
32273206
, leading: function(value) {
3228-
/* act as getter */
3207+
// act as getter
32293208
if (value == null)
32303209
return this._leading
32313210

3232-
/* act as setter */
3211+
// act as setter
32333212
this._leading = new SVG.Number(value)
32343213

32353214
return this.rebuild()
32363215
}
32373216
// Rebuild appearance type
32383217
, rebuild: function(rebuild) {
3239-
/* store new rebuild flag if given */
3218+
// store new rebuild flag if given
32403219
if (typeof rebuild == 'boolean')
32413220
this._rebuild = rebuild
32423221

3243-
/* define position of all lines */
3222+
// define position of all lines
32443223
if (this._rebuild) {
32453224
var self = this
32463225

@@ -3303,13 +3282,13 @@ SVG.Tspan = SVG.invent({
33033282
}
33043283
// Create new line
33053284
, newLine: function() {
3306-
/* fetch text parent */
3285+
// fetch text parent
33073286
var t = this.doc(SVG.Text)
33083287

3309-
/* mark new line */
3288+
// mark new line
33103289
this.newLined = true
33113290

3312-
/* apply new hy¡n */
3291+
// apply new hy¡n
33133292
return this.dy(t._leading * t.attr('font-size')).attr('x', t.x())
33143293
}
33153294
}
@@ -3319,11 +3298,11 @@ SVG.Tspan = SVG.invent({
33193298
SVG.extend(SVG.Text, SVG.Tspan, {
33203299
// Create plain text node
33213300
plain: function(text) {
3322-
/* clear if build mode is disabled */
3301+
// clear if build mode is disabled
33233302
if (this._build === false)
33243303
this.clear()
33253304

3326-
/* create text node */
3305+
// create text node
33273306
this.node.appendChild(document.createTextNode((this.content = text)))
33283307

33293308
return this
@@ -3333,14 +3312,14 @@ SVG.extend(SVG.Text, SVG.Tspan, {
33333312
var node = (this.textPath || this).node
33343313
, tspan = new SVG.Tspan
33353314

3336-
/* clear if build mode is disabled */
3315+
// clear if build mode is disabled
33373316
if (this._build === false)
33383317
this.clear()
33393318

3340-
/* add new tspan and reference */
3319+
// add new tspan and reference
33413320
node.appendChild(tspan.node)
33423321

3343-
/* only first level tspans are considered to be "lines" */
3322+
// only first level tspans are considered to be "lines"
33443323
if (this instanceof SVG.Text)
33453324
this.lines.add(tspan)
33463325

@@ -3350,11 +3329,11 @@ SVG.extend(SVG.Text, SVG.Tspan, {
33503329
, clear: function() {
33513330
var node = (this.textPath || this).node
33523331

3353-
/* remove existing child nodes */
3332+
// remove existing child nodes
33543333
while (node.hasChildNodes())
33553334
node.removeChild(node.lastChild)
33563335

3357-
/* reset content references */
3336+
// reset content references
33583337
if (this instanceof SVG.Text) {
33593338
delete this.lines
33603339
this.lines = new SVG.Set
@@ -3620,6 +3599,18 @@ SVG.extend(SVG.Element, SVG.FX, {
36203599
, opacity: function(value) {
36213600
return this.attr('opacity', value)
36223601
}
3602+
// Relative move over x axis
3603+
, dx: function(x) {
3604+
return this.x((this.target || this).x() + x)
3605+
}
3606+
// Relative move over y axis
3607+
, dy: function(y) {
3608+
return this.y((this.target || this).y() + y)
3609+
}
3610+
// Relative move over x and y axes
3611+
, dmove: function(x, y) {
3612+
return this.dx(x).dy(y)
3613+
}
36233614
})
36243615

36253616
SVG.extend(SVG.Rect, SVG.Ellipse, SVG.Circle, SVG.Gradient, SVG.FX, {

dist/svg.min.js

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)