kokoko

by antishok

HTML

<script src="http://cloud.github.com/downloads/SteveSanderson/knockout/knockout-2.1.0.debug.js"></script>
<script type="text/html" id="plumbing-horizontal-pipe">
        <svg width='100' height='100'>
          <linearGradient data-bind="uniqueId: 'horPipeGrad_'" y1='-20%' x1='0%' y2='100%' x2='0%' gradientUnits='objectBoundingBox'>
            <stop  offset='-20%' data-bind="attr: {'stop-color': bodyColor()}"/>
            <stop  offset='40%' data-bind="attr: {'stop-color': bodyColorLight()}"/>
            <stop  offset='100%'  data-bind="attr: {'stop-color': bodyColor()}"/>
          </linearGradient>
          <rect x='0%' y='30%' width='100%' height='40%' data-bind="uniqueStyleFill: 'horPipeGrad_'"/>
        </svg>
</script>

    <div width="100px" height="100px">
    <!-- Load ko template defined above, bind 'pipe' -->
        <svg width="100" height="110" data-bind="template: { name: 'plumbing-horizontal-pipe', data: pipe }" />
    </div>

JavaScript

ko.bindingHandlers.uniqueId = {
    init: function(element, valueAccessor) {
        // Generate new element id
        element.id = ko.bindingHandlers.uniqueId.prefix + valueAccessor() + ko.bindingHandlers.uniqueId.prefix + (++ko.bindingHandlers.uniqueId.counter);
        console.log("Element id:" + element.id);
    },
    prefix: "autoId_",
    counter: 0
};

ko.bindingHandlers.uniqueStyleFill = {
    init: function(element, valueAccessor) {
        // Use recently generated element id in the style.fill value
        var value = ko.bindingHandlers.uniqueId.prefix + valueAccessor() + ko.bindingHandlers.uniqueId.prefix + ko.bindingHandlers.uniqueId.counter.toString();
        element.style.fill = "url(#" + value + ")";
        console.log("Binding:" + element.style.fill);
    }
};

function MyViewModel() {
    this.pipe = {
        bodyColor: ko.observable("#FF0000"),
        bodyColorLight: ko.observable("#FFA0A0")
    };
}
var g_vm = new MyViewModel();
// This should make the browser display a red pipe. Works in Chrome, doesn't work in FF and Opera.
ko.applyBindings(g_vm);