Browse files

added attributes

  • Loading branch information...
1 parent 1582f02 commit 5ca624f9263c682d13e21f423d8b4a68ee32df20 @matthewmueller committed Dec 10, 2012
Showing with 121 additions and 10 deletions.
  1. +52 −3 Readme.md
  2. +46 −5 index.js
  3. +23 −2 test/json-to-dom.js
View
55 Readme.md
@@ -1,7 +1,7 @@
# json-to-dom
- Fill in DOM nodes with JSON. Supports arrays.
+ Fill in DOM nodes with JSON. Supports arrays and attributes.
## Example
@@ -73,8 +73,6 @@ document.body.innerHTML = body.innerHTML;
## Design
-json-to-dom assumes the tags you are interested in are **classes** and that you are looking to replace `innerText`. *I'm looking for ways to make this more flexible.*
-
### Arrays
#### json-to-dom will iterate over the selected block, even if you don't have any matched tags:
@@ -161,6 +159,8 @@ var email = {
to : 'matt@matt.com',
message : 'Reply with your bank credentials so we can send you the money'
}
+
+render(document.querySelector('.email'), email)
```
outputs:
@@ -174,6 +174,55 @@ outputs:
</div>
```
+### Setting attributes
+
+json-to-dom will also work with attributes. The supported attributes are:
+
+* `data-html` : will set the `innerHTML`
+* `data-text` : will set the `innerText` (the default)
+* `data-[attr]` : will set the `attr` (ex. `data-value`)
+
+When you use data attributes, you have access to the other keys in the object block.
+
+```html
+<div class="note">
+ <a class="title" data-href="url"></a>
+</div>
+```
+
+```js
+var note = {
+ title : "This is a note",
+ url : "http://notes.com"
+}
+
+render(document.querySelector('.note'), note);
+```
+
+outputs:
+
+```html
+<div class="note">
+ <a class="title" href="http://notes.com">This is a note</a>
+</div>
+```
+
+If you'd like to not add the `innerText`, simply use a data attribute with the name of the class:
+
+```html
+<div class="note">
+ <a class="title" data-href="title"></a>
+</div>
+```
+
+outputs:
+
+```html
+<div class="note">
+ <a class="title" href="this is a note"></a>
+</div>
+```
+
## License
MIT
View
51 index.js
@@ -12,14 +12,24 @@ var isArray = require('isArray'),
module.exports = json_to_dom;
/**
+ * Dataset mappings
+ */
+
+var map = {
+ 'text' : 'innerText',
+ 'html' : 'innerHTML'
+};
+
+/**
* json-to-dom
*
* @param {DomNode} el
* @param {Mixed} val
* @return {DomNode}
*/
-function json_to_dom(el, val, key) {
+function json_to_dom(el, val, key, obj) {
+ obj = obj || {};
var node = el;
if(key && typeof key == 'string')
@@ -40,14 +50,45 @@ function json_to_dom(el, val, key) {
} else if(isObject(val)) {
for(var k in val) {
if(val.hasOwnProperty(k)) {
- json_to_dom(node, val[k], k);
+ json_to_dom(node, val[k], k, val);
}
}
} else {
- var keyNode = node.querySelector('.key');
- if(typeof key != 'number') return node.innerText = val;
- else if(keyNode) keyNode.innerText = val;
+ var keyNode = node.querySelector('.key'),
+ dataset = node.dataset,
+ values = [];
+
+ Object.keys(dataset).forEach(function(attr) {
+ var dsv = dataset[attr],
+ val = obj[dsv] || val;
+ delete dataset[attr];
+ attr = map[attr] || attr;
+ if(keyNode) set(keyNode, attr, val);
+ else if(typeof key != 'number') set(node, attr, val);
+ values.push(dsv);
+ });
+
+ if(!values.length || !~values.indexOf(key)) {
+ if(keyNode) set(keyNode, 'innerText', val);
+ else if(typeof key != 'number') set(node, 'innerText', val);
+ }
}
return el;
}
+
+/**
+ * Set
+ */
+
+function set(node, attr, val) {
+ switch(attr) {
+ case 'innerHTML':
+ case 'innerText':
+ node[attr] = val;
+ break;
+ default:
+ node.setAttribute(attr, val);
+ }
+ return node;
+}
View
25 test/json-to-dom.js
@@ -1,8 +1,9 @@
-var render = require('json-to-dom'),
+ var render = require('json-to-dom'),
assert = require('component-assert');
var note = {
title : 'this is a note',
+ url : 'http://note.com',
date : new Date(),
tags : [ 'javascript', 'travel' ],
authors : [
@@ -100,13 +101,33 @@ describe('render', function() {
it('should handle arrays as the initial value', function() {
html.innerHTML = '<div class="people"><span class="first">First Name</span><span class="last">Last Name</span></div>';
- // console.log(html.firstChild);
html = render(html.firstChild, [
{ first : "matt", last : "mueller" },
{ first : "andrew", last : "quinn" }
]);
var expected = '<div class="people"><span class="first">matt</span><span class="last">mueller</span><span class="first">andrew</span><span class="last">quinn</span></div>';
assert(html.outerHTML === expected);
});
+
+ it('should replace attributes with data-attr', function() {
+ html.innerHTML = '<div class="authors"><input class="name" data-value="name" type="text"/></div>';
+ html = render(html, note);
+ var expected = '<div class="authors"><input class="name" type="text" value="matt"><input class="name" type="text" value="andrew"></div>';
+ assert(html.innerHTML === expected);
+ });
+
+ it('should replace attributes with anything in the object', function() {
+ html.innerHTML = '<a data-href="url" class="title"></a>';
+ html = render(html, note);
+ var expected = '<a class="title" href="http://note.com">this is a note</a>';
+ assert(html.innerHTML === expected);
+ });
+
+ it('should replace attributes with anything in the object', function() {
+ html.innerHTML = '<a data-href="url" class="title" data-alt="title"></a>';
+ html = render(html, note);
+ var expected = '<a class="title" href="http://note.com" alt="this is a note"></a>';
+ assert(html.innerHTML === expected);
+ });
});

0 comments on commit 5ca624f

Please sign in to comment.