pull/3/head
Jim Heising 2013-11-07 15:11:24 -08:00
parent 723f2e70b3
commit 337b31b09d
5 changed files with 297 additions and 40 deletions

View File

@ -1029,7 +1029,7 @@ table#datasources-list tbody
.sub-section-height-4
{
height : 210px;
height : 225px;
}
.sub-section:last-of-type

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.1 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 KiB

View File

@ -1,3 +1,152 @@
// Jquery plugin to watch for attribute changes
(function($)
{
function isDOMAttrModifiedSupported()
{
var p = document.createElement('p');
var flag = false;
if(p.addEventListener) p.addEventListener('DOMAttrModified', function()
{
flag = true
}, false);
else if(p.attachEvent) p.attachEvent('onDOMAttrModified', function()
{
flag = true
});
else return false;
p.setAttribute('id', 'target');
return flag;
}
function checkAttributes(chkAttr, e)
{
if(chkAttr)
{
var attributes = this.data('attr-old-value');
if(e.attributeName.indexOf('style') >= 0)
{
if(!attributes['style']) attributes['style'] = {}; //initialize
var keys = e.attributeName.split('.');
e.attributeName = keys[0];
e.oldValue = attributes['style'][keys[1]]; //old value
e.newValue = keys[1] + ':' + this.prop("style")[$.camelCase(keys[1])]; //new value
attributes['style'][keys[1]] = e.newValue;
}
else
{
e.oldValue = attributes[e.attributeName];
e.newValue = this.attr(e.attributeName);
attributes[e.attributeName] = e.newValue;
}
this.data('attr-old-value', attributes); //update the old value object
}
}
//initialize Mutation Observer
var MutationObserver = window.MutationObserver || window.WebKitMutationObserver;
$.fn.attrchange = function(o)
{
var cfg = {
trackValues: false,
callback : $.noop
};
//for backward compatibility
if(typeof o === "function")
{
cfg.callback = o;
}
else
{
$.extend(cfg, o);
}
if(cfg.trackValues)
{ //get attributes old value
$(this).each(function(i, el)
{
var attributes = {};
for(var attr, i = 0, attrs = el.attributes, l = attrs.length; i < l; i++)
{
attr = attrs.item(i);
attributes[attr.nodeName] = attr.value;
}
$(this).data('attr-old-value', attributes);
});
}
if(MutationObserver)
{ //Modern Browsers supporting MutationObserver
/*
Mutation Observer is still new and not supported by all browsers.
http://lists.w3.org/Archives/Public/public-webapps/2011JulSep/1622.html
*/
var mOptions = {
subtree : false,
attributes : true,
attributeOldValue: cfg.trackValues
};
var observer = new MutationObserver(function(mutations)
{
mutations.forEach(function(e)
{
var _this = e.target;
//get new value if trackValues is true
if(cfg.trackValues)
{
/**
* @KNOWN_ISSUE: The new value is buggy for STYLE attribute as we don't have
* any additional information on which style is getting updated.
* */
e.newValue = $(_this).attr(e.attributeName);
}
cfg.callback.call(_this, e);
});
});
return this.each(function()
{
observer.observe(this, mOptions);
});
}
else if(isDOMAttrModifiedSupported())
{ //Opera
//Good old Mutation Events but the performance is no good
//http://hacks.mozilla.org/2012/05/dom-mutationobserver-reacting-to-dom-changes-without-killing-browser-performance/
return this.on('DOMAttrModified', function(event)
{
if(event.originalEvent) event = event.originalEvent; //jQuery normalization is not required for us
event.attributeName = event.attrName; //property names to be consistent with MutationObserver
event.oldValue = event.prevValue; //property names to be consistent with MutationObserver
cfg.callback.call(this, event);
});
}
else if('onpropertychange' in document.body)
{ //works only in IE
return this.on('propertychange', function(e)
{
e.attributeName = window.event.propertyName;
//to set the attr old value
checkAttributes.call($(this), cfg.trackValues, e);
cfg.callback.call(this, e);
});
}
return this;
}
})(jQuery);
var deccoboard = (function()
{
var datasourcePlugins = {};
@ -797,28 +946,7 @@ var deccoboard = (function()
// Initialize our grid
grid = $(element).gridster({
widget_margins : [10, 10],
widget_base_dimensions: [300, 40],
draggable : {
stop : function(event, ui)
{
var paneElement = event.target;
while(_.isUndefined($(paneElement).attr("data-col")))
{
paneElement = $(paneElement).parent();
if(_.isUndefined(paneElement))
{
return;
}
}
var paneModel = $(paneElement).data("deccoPaneModel");
paneModel.row($(paneElement).data("row"));
paneModel.col($(paneElement).data("col"));
}
}
widget_base_dimensions: [300, 40]
}).data("gridster");
grid.disable();
@ -841,6 +969,21 @@ var deccoboard = (function()
}
$(element).data("deccoPaneModel", viewModel);
$(element).attrchange({
trackValues: true,
callback : function(event)
{
if(event.attributeName == "data-row")
{
viewModel.row(event.newValue);
}
else if(event.attributeName == "data-col")
{
viewModel.col(event.newValue);
}
}
});
},
update: function(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext)
{

View File

@ -19,6 +19,12 @@
document.styleSheets[0].addRule('.sparkline', "width:100%;height: 75px;");
document.styleSheets[0].addRule('.sparkline-inline', "width:50%;float:right;height:30px;");
document.styleSheets[0].addRule('.indicator-light', "border-radius:50%;width:22px;height:22px;border:2px solid #3d3d3d;margin-top:5px;float:left;background-color:#222;margin-right:10px;");
document.styleSheets[0].addRule('.indicator-light.on', "background-color:#FFC773;box-shadow: 0px 0px 15px #FF9900;border-color:#FDF1DF;");
document.styleSheets[0].addRule('.indicator-text', "margin-top:10px;");
document.styleSheets[0].addRule('div.pointer-value', "position:absolute;height:95px;margin: auto;top: 0px;bottom: 0px;width: 100%;text-align:center;");
function easeTransitionText(currentValue, newValue, textElement, duration)
{
if(currentValue == newValue)
@ -237,6 +243,7 @@
var self = this;
var thisGaugeID = "gauge-" + gaugeID++;
var titleElement = $('<h2 class="section-title"></h2>');
var gaugeElement = $('<div class="gauge-widget" id="' + thisGaugeID + '"></div>');
var gaugeObject;
@ -267,7 +274,7 @@
this.render = function(element)
{
rendered = true;
$(element).append($('<div class="gauge-widget-wrapper"></div>').append(gaugeElement));
$(element).append(titleElement).append($('<div class="gauge-widget-wrapper"></div>').append(gaugeElement));
createGauge();
}
@ -282,6 +289,8 @@
{
currentSettings = newSettings;
}
titleElement.html(newSettings.title);
}
this.onCalculatedValueChanged = function(settingName, newValue)
@ -402,6 +411,8 @@
var triangle;
var width, height;
var currentValue = 0;
var valueDiv = $('<div class="text-widget-big-value"></div>');
var unitsDiv = $('<div></div>');
function polygonPath(points)
{
@ -429,37 +440,42 @@
circle.attr("stroke", "#FF9900");
circle.attr("stroke-width", strokeWidth);
triangle = paper.path(polygonPath([width / 2, 0, 15, 20, -30, 0]));
triangle = paper.path(polygonPath([width / 2, (height / 2) - radius + strokeWidth, 15, 20, -30, 0]));
triangle.attr("stroke-width", 0);
triangle.attr("fill", "#fff");
$(element).append($('<div class="pointer-value"></div>').append(valueDiv).append(unitsDiv));
}
this.onSettingsChanged = function(newSettings)
{
unitsDiv.html(newSettings.units);
}
this.onCalculatedValueChanged = function(settingName, newValue)
{
if(!_.isUndefined(triangle))
if(settingName == "direction")
{
var direction = "r";
/*var oppositeCurrent = currentValue + 180;
if(oppositeCurrent > 360)
if(!_.isUndefined(triangle))
{
oppositeCurrent = oppositeCurrent - 360;
var direction = "r";
var oppositeCurrent = currentValue + 180;
if(oppositeCurrent < newValue)
{
//direction = "l";
}
triangle.animate({transform: "r" + newValue + "," + (width / 2) + "," + (height / 2)}, 250, "bounce");
}
if(oppositeCurrent < newValue)
{
direction = "l";
}*/
triangle.animate({transform: "r" + newValue + "," + (width / 2) + "," + (height / 2)}, 250, "bounce");
currentValue = newValue;
}
else if(settingName == "value_text")
{
valueDiv.html(newValue);
}
currentValue = newValue;
}
this.onDispose = function()
@ -483,6 +499,16 @@
display_name: "Direction",
type : "calculated",
suffix : "degrees"
},
{
name : "value_text",
display_name: "Value Text",
type : "calculated"
},
{
name : "units",
display_name: "Units",
type : "text"
}
],
newInstance : function(settings)
@ -546,4 +572,92 @@
}
});
var indicatorWidget = function(settings)
{
var self = this;
var titleElement = $('<h2 class="section-title"></h2>');
var stateElement = $('<div class="indicator-text"></div>');
var indicatorElement = $('<div class="indicator-light"></div>');
var currentSettings = settings;
var isOn = false;
function updateState()
{
indicatorElement.toggleClass("on", isOn);
if(isOn)
{
stateElement.text((_.isUndefined(currentSettings.on_text) ? "" : currentSettings.on_text));
}
else
{
stateElement.text((_.isUndefined(currentSettings.off_text) ? "" : currentSettings.off_text));
}
}
this.render = function(element)
{
$(element).append(titleElement).append(indicatorElement).append(stateElement);
}
this.onSettingsChanged = function(newSettings)
{
currentSettings = newSettings;
titleElement.html((_.isUndefined(newSettings.title) ? "" : newSettings.title));
updateState();
}
this.onCalculatedValueChanged = function(settingName, newValue)
{
if(settingName == "value")
{
isOn = Boolean(newValue);
}
updateState();
}
this.onDispose = function()
{
}
this.getHeight = function()
{
return 1;
}
this.onSettingsChanged(settings);
};
deccoboard.loadWidgetPlugin({
type_name : "indicator",
display_name: "Indicator Light",
settings : [
{
name : "title",
display_name: "Title",
type : "text"
},
{
name : "value",
display_name: "Value",
type : "calculated"
},
{
name : "on_text",
display_name: "On Text",
type : "calculated"
},
{
name : "off_text",
display_name: "Off Text",
type : "calculated"
}
],
newInstance : function(settings)
{
return new indicatorWidget(settings);
}
});
}());