can
Version:
MIT-licensed, client-side, JavaScript framework that makes building rich web applications easy.
184 lines (177 loc) • 4.7 kB
HTML
<style>
.breadcrumb li {
display: inline-block;
padding: 5px 0px;
}
.breadcrumb li:before {
content: ">";
font-weight: normal;
}
.breadcrumb li:hover {
font-weight: bold;
cursor: pointer;
}
.breadcrumb li:last-child {
font-weight: bold;
}
.breadcrumb li:first-child:before {
content: ""
}
.breadcrumb li:last-child:hover {
text-decoration: none;
cursor: default;
}
.options li {
padding: 3px 5px;
}
.options li.checked {
background-color: yellow;
}
#selected {
margin-top: 20px;
border-top: solid 1px silver;
}
#selected li{
padding-left: 10px;
}
</style>
<div id='out'></div>
<script id="app" type="text/stache">
<div><tree-combo {items}='locations' title='Locations'/></div>
</script>
<script id="tree-combo-stash" type='text/stache'>
<ul class='breadcrumb'>
<li ($click)='emptyBreadcrumb()'>{{title}}</li>
{{#each breadcrumb}}
<li ($click)='updateBreadcrumb(.)'>{{title}}</li>
{{/each}}
</ul>
<ul class='options'>
<content>
{{#selectableItems}}
<li {{#isSelected}}class='active'{{/isSelected}} ($click)='toggle(.)'>
<input type='checkbox' {{#isSelected(.)}}checked{{/isSelected}}/>
{{title}}
{{#if children.length}}
<button class='showChildren' ($click)='showChildren(.,%event)'>+</button>
{{/if}}
</li>
{{/selectableItems}}
</content>
</ul>
</script>
<script src="../../node_modules/steal/steal.js" main="@empty">
var Component = require("can-component");
var stache = require("can-stache");
var DefineMap = require("can-define/map/map");
var DefineList = require("can-define/list/list");
var ViewModel = DefineMap.extend({
items: {
Value: DefineList
},
breadcrumb: {
Value: DefineList
},
selected: {
Value: DefineList
},
title: "*",
selectableItems: {
get: function(){
var breadcrumb = this.breadcrumb;
// if there's an item in the breadcrumb
if(breadcrumb.length){
// return the last item's children
var i = breadcrumb.length - 1;
return breadcrumb[i].children;
} else{
// return the top list of items
return this.items;
}
}
},
showChildren: function(item, ev) {
ev.stopPropagation();
this.breadcrumb.push(item);
},
emptyBreadcrumb: function( ) {
this.breadcrumb = [];
},
updateBreadcrumb: function( item ){
var breadcrumb = this.breadcrumb,
index = breadcrumb.indexOf(item);
breadcrumb.splice(index + 1, breadcrumb.length - index - 1);
},
toggle: function(item){
var selected = this.selected,
index = selected.indexOf(item);
if(index === -1 ){
selected.push(item);
} else {
selected.splice(index, 1);
}
},
isSelected: function(item){
return this.selected.indexOf(item) > -1;
}
});
Component.extend({
tag: "tree-combo",
template: stache(document.getElementById("tree-combo-stash").innerHTML),
ViewModel: ViewModel
});
var base = new DefineMap({
locations: [
{ id: 1, title: "Midwest", children: [
{ id: 5, title: "Illinois", children: [
{ id: 23423, title: "Chicago"}, { id: 4563, title: "Springfield"},
{ id: 4564, title: "Naperville"}
]
},
{ id: 6, title: "Wisconsin", children: [
{ id: 232423, title: "Milwaulkee"}, { id: 45463, title: "Green Bay"},
{ id: 45464, title: "Madison"}
]
}]
},
{ id: 2, title: "East Coast", children: [
{ id: 25, title: "New York", children: [
{ id: 3413, title: "New York"}, { id: 4613, title: "Rochester"},
{ id: 4516, title: "Syracuse"}
]
},
{ id: 6, title: "Pennsylvania", children: [
{ id: 2362423, title: "Philadelphia"}, { id: 454663, title: "Harrisburg"},
{ id: 454664, title: "Scranton"}
]
}]
},
{ id: 3, title: "West Coast", children: [
{ id: 75, title: "California", children: [
{ id: 347813, title: "Los Angeles"}, { id: 463213, title: "Sunnyvale"},
{ id: 457516, title: "San Diego"}
]
},
{ id: 66, title: "Oregon", children: [
{ id: 23621, title: "Bend"}, { id: 1111, title: "Salem"},
{ id: 45461, title: "Eugene"}
]
}]
},
{ id: 4, title: "South", children: [
{ id: 65, title: "Texas", children: [
{ id: 343413, title: "Austin"}, { id: 463413, title: "Dalas"},
{ id: 498516, title: "El Paso"}
]
},
{ id: 6, title: "Florida", children: [
{ id: 2360, title: "Orlando"}, { id: 4540, title: "Tampa"},
{ id: 4064, title: "Miami"}
]
}]
}]
});
var template = stache(document.getElementById("app").innerHTML);
var frag = template(base);
document.getElementById("out").appendChild(frag);
</script>