﻿/**************
 * Data Type
 *************/
/*
function DataType(id, name) {
    this.id = id;
    this.name = name;
}

DataType.prototype.isScalar = function() {
    return (this.name == 'scalar' || this.id == 1);
}

DataType.prototype.isImageURL = function() {
    return (this.name == 'image' || this.id == 7);
}

var dataTypeListByID = new Object();
dataTypeListByID[0] = new DataType(0, 'unknown');
dataTypeListByID[1] = new DataType(1, 'scalar');
dataTypeListByID[2] = new DataType(2, 'bmp');
dataTypeListByID[3] = new DataType(3, 'jpg');
dataTypeListByID[4] = new DataType(4, 'gif');
dataTypeListByID[5] = new DataType(5, 'vector');
dataTypeListByID[6] = new DataType(6, 'html');
dataTypeListByID[7] = new DataType(7, 'image');
*/

/**************
 * Sensor Type
 *************/
function getValueIcon(value, min, max, resolution, colorMapIndex, isContinuous) {
    var temp = new Array();
    temp.push('shapes/ColorDot.aspx?');
    temp.push('continuous=' + isContinuous);
    temp.push('&colorMapId=' + colorMapIndex);
    temp.push('&min=' + min);
    temp.push('&max=' + max);
    temp.push('&reso=' + resolution);
    temp.push('&value=' + value);
    return temp.join('');
}

function ExcludeIncludeSenFrmCM (id, sensorLoc){
    var chkBox = $get(id);
    var isExist = false;
    if (chkBox != null && arrSensorsExFrmContourMap != null){
        var val = chkBox.checked;
        for(var i=0;i<arrSensorsExFrmContourMap.length;i++){
            if(arrSensorsExFrmContourMap[i] === id && val == false){
                arrSensorsExFrmContourMap[i] = '';
                arrSensorsExFrmContourMapLoc[i] = '';
            }                         
        }
        if(val){
            arrSensorsExFrmContourMap.push(id);
            arrSensorsExFrmContourMapLoc.push(sensorLoc);
        }
    }
}

function isExistInExcludeArray(id){
     for(var i=0;i<arrSensorsExFrmContourMap.length;i++){
            if(arrSensorsExFrmContourMap[i] === id)
                return true;
     }
     return false;
}

function SensorType(id, name, uri, sensorName, unit, icon, brokenIcon, aggrIcon, valueIconFn, dataType, inView) {
    this.id = id;
    this.name = name;
    this.uri = uri;
    this.sensorName = sensorName;
    this.unit = unit;
    this.icon = icon;
    this.brokenIcon = brokenIcon;
    this.aggrIcon = aggrIcon;
    this.valueIconFn = valueIconFn;
    this.dataType = dataType || 'unknown';
    this.inView = inView || true;
}

/*********************
 * Vector Sensor Type
 *********************/

function VectorSensorType(id, name, uri, sensorName, unit, icon, brokenIcon, aggrIcon, valueIcon, signature) {
    this.superclass(id, name, uri, sensorName, unit, icon, brokenIcon, aggrIcon, valueIcon);
    this.signature = signature;
    var temp = signature.split(';');
    for (var i in temp) {
        if (temp[i] && temp[i].length != 0)
            this.componentTypes.push(sensorTypeListByID[temp[i]]);
    }
}

VectorSensorType.prototype = new SensorType();
VectorSensorType.prototype.superclass = SensorType;
VectorSensorType.prototype.componentTypes = new Array();


var sensorTypeListByID = new Object();
var sensorTypeListByUri = new Object();
var arrSensorsExFrmContourMap = new Array();
var arrSensorsExFrmContourMapLoc = new Array();
var initSensorTypesCount = 0;
function InitSensorTypes() {
    SenseWeb.SensorManagement.GetSensorTypeList(GetSensorTypeDone, GetSensorTypeTimeOut);
    SenseWeb.SensorManagement.GetVectorSensorTypeList(GetSensorTypeDone, GetSensorTypeTimeOut);
}

function InitSensorTypesDone() {
}

function GetSensorTypeDone(result) {
    for (var index in result) {
        var temp = result[index];
        if (temp.DataType == 'vector')
            sensorTypeListByID[temp.ID] = new VectorSensorType(temp.ID
                , temp.Name
                , temp.URI
                , temp.Name + ' Sensor'
                , temp.Unit
                , temp.IconURL
                , temp.BrokenIconURL
                , temp.GroupIconURL
                , temp.IconURL
                , temp.Signature);
        else {
            var valueIcon = getValueIcon;
            if (temp.DataType != 'scalar')
                valueIcon = temp.IconURL;
            sensorTypeListByID[temp.ID] = new SensorType(temp.ID
                , temp.Name
                , temp.URI
                , temp.Name + ' Sensor'
                , temp.Unit
                , temp.IconURL
                , temp.BrokenIconURL
                , temp.GroupIconURL
                , valueIcon
                , temp.DataType);
        }
        sensorTypeListByUri[temp.URI] = sensorTypeListByID[temp.ID];
    }
    initSensorTypesCount ++;
    if (initSensorTypesCount == 2) {
        InitSensorTypesDone();
    }
}
function GetSensorTypeTimeOut() {
    alert("Fail to fetch sensor types!");
}

/**************
 * Sensor
 *************/

function Sensor(name, latitude, longitude, sensorTypeUri, keywords, desc, publisher, state, dataTypeName, timeStamp, webServiceUrl, displayName, metaInfo) {
    this.name = name || '';
    this.latitude = latitude || 0;
    this.longitude = longitude || 0;
    this.sensorTypeUri = sensorTypeUri || 0;
    this.keywords = keywords || '';
    this.desc = desc || '';
    this.publisher = publisher || '';
    this.state = state || Sensor.notWorkingStr;
    this.dataTypeName = dataTypeName || 0;
    this.timeStamp = timeStamp;
    this.webServiceUrl = webServiceUrl || 'http://localhost/SenseWebV3/DataHub/Service.asmx';  
    this.displayName = displayName;
    this.metaInfo = metaInfo;  
}

Sensor.fromString = function(sensorCsv) {
    if ( (sensorCsv != null) && (sensorCsv.length > 0) )
    {
        var sensorAttributes =
            sensorCsv.replace(/\$(?=\$)/g, '\$ ').replace(/([^#])\$/g, '$1$1\$').split(/[^#]\$/);  
            
        if (sensorAttributes != null && sensorAttributes.length >= 9)
        {
            // CSV is received in the following format:
            // 0 [name]
            // 1 [sensorType]
            // 2 [unit]
            // 3 [lat]
            // 4 [long]
            // 5 [desc]
            // 6 [keywords]
            // 7 [pub]
            // 8 [dataType]
            // 9 [state] 9 state
            // 10 numSensors 10 timestamp
            // 11 sum 11 webserviceurl
            // 12 Min 12 displayname
            // 13 Max 13 metainfo
            // 14             
   
            var name = sensorAttributes[0];
            var sensorTypeUri = sensorAttributes[1];
            var latitude = parseFloat(sensorAttributes[3]);
            var longitude = parseFloat(sensorAttributes[4]);
            var desc = sensorAttributes[5];
            var keywords = sensorAttributes[6];
            var publisher = sensorAttributes[7];
            var dataTypeName = sensorAttributes[8];
            var state;
            var timeStamp;
            var webServiceUrl;
            var displayName;
            var metaInfo;
            var numSensors;
            var stateSum;
            var stateMin;
            var stateMax;
            if (sensorAttributes.length < 15)// not a group
            { 
                state = sensorAttributes[9];
                timeStamp = sensorAttributes[10];
                webServiceUrl = sensorAttributes[11];
                displayName = sensorAttributes[12];
                metaInfo = sensorAttributes[13];
                return new Sensor(name, latitude, longitude, sensorTypeUri, keywords, 
                    desc, publisher, state, dataTypeName, timeStamp, webServiceUrl, displayName, metaInfo);
            } else {
                state = parseInt(sensorAttributes[9]);
                numSensors = parseInt(sensorAttributes[10]);
                stateSum = parseFloat(sensorAttributes[11]);
                stateMin = parseFloat(sensorAttributes[12]);
                stateMax = parseFloat(sensorAttributes[13]);   
                name, latitude, longitude, sensorTypeUri, keywords, desc, publisher, state, dataTypeName, numSensors, stateSum, stateMin, stateMax
                return new SensorGroup(name, latitude, longitude, sensorTypeUri, keywords, 
                    desc, publisher, state, dataTypeName, 
                    numSensors, stateSum, stateMin, stateMax);
            }
        }
    }
}

Sensor.prototype.updateState = function(sensorDataCSV) {
    if (sensorDataCSV) {
        var dataFields = sensorDataCSV.split(/\$/);   
        this.state = dataFields[3] || Sensor.notWorkingStr;
        this.timeStamp = dataFields[2];
    }
}

Sensor.prototype.notWorking = function() {
    return (!this.state || this.state.length == 0 || this.state == ' ');
}

Sensor.prototype.getIcon = function() {
    var icon = null;
    var sensorType = sensorTypeListByUri[this.sensorTypeUri];
    if(sensorType != null){
        if (this.notWorking())
             icon = sensorType.brokenIcon;
        else
             icon = sensorType.icon;
    }
    return icon;
}

Sensor.prototype.getTitle = function() {
    var sensorName = null;
    var sensorType = sensorTypeListByUri[this.sensorTypeUri];
    if(sensorType != null)
        sensorName = sensorType.sensorName;
    return sensorName;
}

Sensor.prototype.getValueIcon = function(min, max, resolution, colorMapIndex, isContinuous) {
    var temp = sensorTypeListByUri[this.sensorTypeUri].valueIconFn;
    if (typeof temp != 'function') {
        return this.getIcon();
    } else {
        return temp(this.state, min, max, resolution, colorMapIndex, isContinuous);
    }
}
Sensor.prototype.getDisplayName = function() {
    if (this.displayName) return this.displayName;
    // get display name
    var temp = this.name.lastIndexOf('@');
    this.displayName = sensorTypeListByUri[this.sensorTypeUri].name;
    if (temp == -1) {
        this.displayName += ' (' + this.name + ')';
    } else {
        this.displayName = this.name.substring(temp+1, this.name.length) + ' ' + this.displayName;
        this.displayName += ' (' + this.name.substring(0, temp) + ')';
    }
    return this.displayName;
}

Sensor.prototype.getStateHTML = function(mode3d) {
    if (this.dataTypeName == 'vector') return '';
    var output = new Array();
    if (this.notWorking()) {
        if (this.dataTypeName == 'scalar' && !mode3d) {
                output.push('&nbsp;<input class="sl_button" type="button" value="chart" ');
                output.push('onclick="javascript:OnClickHistoricChart(\''
                    + this.webServiceUrl + '\', \''
                    + this.name + '\', \''
                    + this.getDisplayName() + '\', \''
                    + this.sensorTypeUri + '\', \''
                    + this.publisher + '\');" /><br />');
        }
        //alert(typeof(this.metaInfo));
        if(typeof this.metaInfo != 'undefined' && this.metaInfo != '' && this.metaInfo != ' ')
            output.push('&nbsp;&nbsp;&nbsp;(' + this.metaInfo +')<br/>');
        output.push('&nbsp;&nbsp;&nbsp;&nbsp;');
        output.push('not available');
    } 
    else {
        switch (this.dataTypeName) {
            case 'scalar':
                if (!mode3d) {
                    output.push('&nbsp;<input class="sl_button" type="button" value="chart" ');
                    output.push('onclick="javascript:OnClickHistoricChart(\''
                        + this.webServiceUrl + '\', \''
                        + this.name + '\', \''
                        + this.getDisplayName() + '\', \''
                        + this.sensorTypeUri + '\', \''
                        + this.publisher + '\');" /><br />');
                }
                if(typeof this.metaInfo != 'undefined' && this.metaInfo != '' && this.metaInfo != ' ')
                    output.push('&nbsp;&nbsp;&nbsp;(' + this.metaInfo +')<br/>');
                output.push('&nbsp;&nbsp;');
                output.push(Math.round(this.state * 1000) / 1000 + sensorTypeListByUri[this.sensorTypeUri].unit);
                output.push('<br />&nbsp;&nbsp;' + this.timeStamp +"<br/>");
                break;
            case 'image':
                output.push('<br /><img width="100px" height="100px" src="' + this.state + '"/><br />');
                output.push('<a href="javascript:void(0)" onclick="window.open(\'');
                output.push(this.state);
                output.push('\', \'DataWindow\')">Open in new window</a>');
                break;
            case 'html':
                output.push('<br /><iframe src="' + this.state + '" width="200px" height="200px">');
                output.push('<p>If you cannot see the data, click <a href="' + this.state + '">here</a>.</p>');
                output.push('</iframe><br>');
                output.push('<a href="javascript:void(0)" onclick="window.open(\'');
                output.push(this.state);
                output.push('\', \'DataWindow\')">Open In New Window</a>');
                break;
        }
    }
    output.push('<br />');
    return output.join('');
}

Sensor.prototype.getMetaDetailHTML = function() {
    var output = new Array();
    var cbId = 'cb^' + this.name + '^' +  this.publisher;
    var sensorLoc = this.latitude +':'+ this.longitude;
    var isExist = isExistInExcludeArray(cbId) == true ? 'checked' : '';
    //output.push('<div style="color: #000000; font-weight: bold">' + sensorTypeListByUri[this.sensorTypeUri].sensorName + this.getDeleteLink() + '</div>');
    output.push('<div style="color: #000000; font-weight: bold">' + this.name + this.getDeleteLink() + '</div>');
    //output.push('Name: ' + this.name + '<br>');
    output.push('Publisher: ' + this.publisher + '<br>');
    output.push('Description: ' + this.desc + '<br>');
    output.push('<div><input type="checkbox" id="'+ cbId +'" onclick="ExcludeIncludeSenFrmCM(\''+cbId+'\',\''+ sensorLoc + '\')" ' + isExist +'>Exclude from Contour Map</input></div>');    
    output.push('<b>Data:</b><br />');
    return output.join('');
}

Sensor.prototype.getDetailHTML = function(mode3d) {
    var output = new Array();
    output.push(this.getMetaDetailHTML());
    output.push(this.getStateHTML(mode3d));
    return output.join('');
}

Sensor.prototype.getComponentMetaDetailHTML = function() {
    var output = new Array();
    output.push('<div style="color: #000000; font-weight: bold">Assorted Sensors</div>');
    output.push('Publisher: ' + this.publisher + '<br>');
    output.push('Description: ' + this.desc + '<br>');
    return output.join('');
}

Sensor.prototype.getComponentStateHTML = function() {
    var displayName = this.displayName;
    if(displayName == ' ' || displayName == '') 
        displayName = sensorTypeListByUri[this.sensorTypeUri].name;
    var output = new Array();
    output.push('<b>');
    output.push(this.name.substring(this.name.lastIndexOf('@') + 1, this.name.length + 1));
    output.push('&nbsp;');
    output.push(displayName);
    output.push('</b>');
    output.push('&nbsp;');
    output.push(this.getStateHTML());
    return output.join('');
}

Sensor.prototype.getDeleteLink = function()
{
    var output = new Array();
    var userLogin = GetUserName();
    if(userLogin !='' && this.publisher.toLowerCase() == userLogin.toLowerCase()){
        output.push('&nbsp;(<a href="javascript:DeleteSensor(\''
            + this.publisher + '\', \''
            + this.name + '\', \''
            + this.sensorTypeUri + '\', \''
            + this.dataTypeName + '\');">delete</a>)');
     }
     return output.join();
} 

/**************
 * Sensor: SensorGroup
 *************/
function SensorGroup(name, latitude, longitude, sensorTypeUri, keywords, desc, publisher, state, dataTypeName, numSensors, stateSum, stateMin, stateMax) {
    this.superclass(name, latitude, longitude, sensorTypeUri
        , keywords, desc, publisher, state, dataTypeName,'','','','');
    this.numSensors = numSensors || 1;
    this.stateSum = stateSum || 0;
    this.stateMin = stateMin || 0;
    this.stateMax = stateMax || 0;
}

SensorGroup.prototype = new Sensor();
SensorGroup.prototype.superclass = Sensor;

SensorGroup.prototype.getIcon = function() {
    return sensorTypeListByUri[this.sensorTypeUri].aggrIcon;
}

SensorGroup.prototype.getTitle = function() {
    return sensorTypeListByUri[this.sensorTypeUri].sensorName + ' Group';
}

SensorGroup.prototype.getStateHTML = function() {
    var output = new Array();
    switch (this.dataTypeName) {
        case 'scalar':
            if (this.stateMin < this.stateMax) {
                output.push('Average: ');
                output.push(Math.round(this.stateSum / this.numSensors * 100) / 100);
                output.push(sensorTypeListByUri[this.sensorTypeUri].unit);
                output.push('<br>');

                output.push('Min: ' + Math.round(this.stateMin * 100) / 100);
                output.push(sensorTypeListByUri[this.sensorTypeUri].unit);
                output.push('<br>');

                output.push('Max: ' + Math.round(this.stateMax * 100) / 100);
                output.push(sensorTypeListByUri[this.sensorTypeUri].unit);
                output.push('<br>');
            }
             break;
    }
    return output.join('');
}

SensorGroup.prototype.getMetaDetailHTML = function() {
    var output = new Array();
    output.push('<div style="color: #000000; font-weight: bold">');
    output.push(sensorTypeListByUri[this.sensorTypeUri].sensorName);
    output.push(' Group</div>');
    output.push('Number in group: ' + this.numSensors + '<br>');
    return output.join('');
}

SensorGroup.prototype.getDetailHTML = function() {
    var output = new Array();
    output.push(this.getMetaDetailHTML());
    output.push(this.getStateHTML());
    return output.join('');
}



