'use strict';
/* global Backbone, _, $, AmCharts */
/* global  mainview */
/* jshint browser: true , devel: true*/


(function($) {

  var mqttConfig = {
    orgId: 'qz0da4',
    userName: 'a-qz0da4-dfwwdkmkzr',
    appKey: '9txJEf3Cjy7hkSOvkv',
    prefix: 'iot-2/type/mDot/id/'
  };

  var sendAuthentication = function(xhr) {
    var user = 'a-qz0da4-dfwwdkmkzr'; // Your actual username
    var pass = '9txJEf3Cjy7hkSOvkv'; // Your actual password
    var token = user.concat(':', pass);
    xhr.setRequestHeader('Authorization', ('Basic '.concat(btoa(token))));

    console.log('Auth:', ('Basic '.concat(btoa(token))));
  };

  var EventsModel = Backbone.Model.extend({
    initialize: function() {
      _.bindAll(this, 'processAdded');
      this.on('all',function(d) {
        console.log('model:all',d);
        this.temporal = {low: 0,high: 0};
      });

      this.on('add',function() {
        this.processAdded();
      });

    },
    processAdded: function() {
      console.log('Model:ProcessAdded');

      var tempCollection = new Backbone.Collection();

      _.invoke(DeviceCollection.toArray(), 'destroy');

      this.temporal = {low: 0,high: 0};

      _(this.get('events')).each(function(i) {
        if (this.temporal.low === 0 || this.temporal.low > i.timestamp) {
          this.temporal.low = i.timestamp;
        }

        if (this.temporal.high === 0 || this.temporal.high < i.timestamp) {
          this.temporal.high = i.timestamp;
        }

        tempCollection.add({dt: i.timestamp,lux: i.lux, temp: i.temp, co2: i.co2, humid: i.humidity, noise: i.sound});
      }, this);

      DeviceCollection.temporal = this.temporal;

      DeviceCollection.models = tempCollection.models;
      DeviceCollection.trigger('update');
      console.log('temporal:', this.temporal);
    },
    decoder: function(data) {
      var _obj = {};
      var _data = window.atob(data).split('');

      var bytes = _data.map(i => i.charCodeAt());

      _obj.light =  parseInt('0x' + ('0' + bytes[0]).substr(-2) + ('0' + bytes[1]).substr(-2));
      _obj.co2 = parseInt(_data[2] + _data[3] + _data[4] + _data[5] + _data[6], 10);
      _obj.temp = (parseInt(_data[7] + _data[8] + _data[9] + _data[10] + _data[11], 10) - 1000) / 10;
      _obj.humid = (parseInt(_data[12] + _data[13] + _data[14] + _data[15] + _data[16], 10) / 10);
      _obj.noise = parseInt('0x' + ('0' + bytes[17]).substr(-2) + ('0' + bytes[18]).substr(-2));
      _obj.binData = bytes;
      return _obj;
    },
    dateTime: function($date) {
      var dateTime = new Date.create($date);
      var date = dateTime.format('{yyyy}-{MM}-{dd}');
      var time = dateTime.format('{HH}:{mm}:{ss}');
      return {dateTime: dateTime.format('{yyyy}-{MM}-{dd} {HH}:{mm}:{ss}'), date: date, time: time};
    }
  });

  var mDotCollection = Backbone.Collection.extend({
    model: EventsModel,
    url: 'https://qz0da4.internetofthings.ibmcloud.com/api/v0002/historian/types/mDot/devices/',
    initialize: function() {
      this.on('update', function() {
        // Console.log('Collection:update',this);
      });
    }

  });

  var ItemView = Backbone.View.extend({
    tagName: 'div', className: 'item mui-container', initialize: function() {
      this.template = _.template($('#item-template').html());
      console.log('ItemView:Init');
      //  This.render();
    }, render: function() {

      console.log('ItemView:Render');
      _(this.model.events).each(function(i) {
        this.$el.append(this.template({item: i}));
      }, this);

      return this;
    }
  });



  var MDOT = Backbone.View.extend({
    model: EventsModel, el: $('#output'),

    events: {
      'click button#refresh': 'refresh'
    }, initialize: function() {
      _.bindAll(this, 'render', 'refresh', 'update');
      this.collection.bind('change reset add remove', this.render, this);

      this.template = _.template($('#list-template').html());
      this.render();
    }, refresh: function() {

    }, update: function() {
      console.log('MDOT:update');
      this.collection.each(function(model) {

        //   Var events = model.get('events');
        //   var e = new ItemView({model: model.toJSON()});
      });

    }, render: function() {
      console.log('MDOT:render');

      var that = this;
      this.$el.empty();
      this.collection.each(function(model) {
        var events = model.get('events');
        var e = new ItemView({model: model.toJSON()}).render().el;

        console.log('render:done:');
        that.$el.append(e);

      });
      console.log('bah');
      return this;
    }
  });


  var MainModel = Backbone.Model.extend({});

  var MainView = Backbone.View.extend({
    el: $('#main'),
    template: _.template($('#main-template').html()),
    events: {
            'change select#device': 'changeDevice',
            'click button#refresh': 'updateDevice',
            'change input#from': 'changeDate',
            'change input#to': 'changeDate',
            submit: function(event) {}

          },
    initialize: function() {
          _.bindAll(this, 'render','changeDevice', 'updateDevice');

          this.model.on('change',this.updateDevice);
          console.log('MainView:', this);
          this.render();
        },
    render: function() {
      $(this.el).html(this.template());
      return this;
    },changeDate: function(elm) {
          console.log('ChangeDate', elm);

          if (elm.currentTarget.valueAsDate === null) {
            this.model.unset(elm.currentTarget.id);
          } else {
            this.model.set(elm.currentTarget.id, elm.currentTarget.valueAsDate);
          }

        },
    changeDevice: function() {
      var newDevice;
      console.log('MainView:ChangeDevice');
      newDevice = this.$el.find('#device')[0].value;

      this.model.set('device', newDevice);
    },
    updateDevice: function() {
      var fetchObj = {beforeSend: sendAuthentication};
      var rangeObj = {start: null, end: null};
      console.log('MainView:Updatedevice');
      if (this.model.has('from') && this.model.has('to')) {
        rangeObj.start = this.model.get('from');
        rangeObj.end = this.model.get('to');
        fetchObj.data = $.param(rangeObj);
      }
      if (this.model.has('device')) {
        // FetchObj.data = $.param({key:'"'+ this.model.get('device') + '"'});
        // this.collection.url =  'https://qz0da4.internetofthings.ibmcloud.com/api/v0002/historian/types/mDot/devices/' + this.model.get('device');
        // this.collection.url =  '/api/mdot/' + this.model.get('device');
        this.collection.url =  '/apiv2/mdot/' + this.model.get('device');
        // this.collection.url =  'http://127.0.0.1:5984/mdot/_design/getDevice/_view/getDevice';
        this.collection.fetch(fetchObj);
      } else {
        console.error('Nothing to get!');
      }

    }

  });

  var GraphView = Backbone.View.extend({
    el: $('#graph'),
    template: _.template($('#AMChart-template').html()),
    initialize: function() {
          this.modes = ['','lux','temp','co2','humid','noise'];
          this.mode = 0;

          // Config AMChart
          this.chart = new AmCharts.AmStockChart();
          this.categoryAxesSettings = new AmCharts.CategoryAxesSettings();
          this.dataSet = new AmCharts.DataSet();

          console.log('GraphView!');
          _.bindAll(this, 'render', 'changeMode', 'updateGraph','setupChart');
          this.collection.on('update',function(d) {
            if (this.mode > 0) {
              this.updateGraph();
            }
          }, this);

          this.render();
          // This.setupChart();
        },
    events: {
                  'change select#displaymode': 'changeMode'
                },
    render: function() {
      $(this.el).html(this.template());


      return this;
    },
    setupChart: function() {
      console.log('chart:SetupChart');

      this.categoryAxesSettings.minPeriod = 'mm';
      this.chart.categoryAxesSettings = this.categoryAxesSettings;

      this.dataSet.color = '#b0de09';

      this.chart.dataSets = [this.dataSet];
      //      This.chart.write('chartdiv');
    },

    changeMode: function() {
          this.mode = this.$el.find('#displaymode')[0].value;
          this.updateGraph();
          console.log('new mode:', this.mode);

        },
    updateGraph: function() {
var self = this;
          let getMode = this.modes[this.mode];

          var chartData = [];

      var temporal = {high:0, low:0};
      var HL = {high:0,low:0}

          _(this.collection.models).each(function(i) {
            var dt = i.get('dt');
            var value = i.get(getMode);
            if (temporal.low === 0 || dt < temporal.low) {
                        temporal.low = dt;
            }
            if (temporal.high === 0 || dt > temporal.high) {
                        temporal.high = dt;
            }

            if (HL.low === 0 || value < HL.low) {
                        HL.low = value;
            }
            if (HL.high === 0 || value > HL.high) {
                        HL.high = value;
            }

                chartData.push({
                            date: dt,
                            value: value
                          });

              }, this);


      console.log('this.temporal', this.temporal);
      console.log('temporal', temporal);
          console.log(chartData);


        console.log('Doing chart now');

        //debugger;
                      // SERIAL CHART
                      self.chart = new AmCharts.AmSerialChart();

      //"2016-08-10T23:04:31.000Z"
                      self.chart.dataProvider = chartData;
                      self.chart.dataDateFormat = "YYYY-MM-DDTHH:NN:SS.QQQ";
                      self.chart.categoryField = "date";


                      // AXES
                      // category
                      var categoryAxis = self.chart.categoryAxis;
                      categoryAxis.parseDates = true; // as our data is date-based, we set parseDates to true
                      categoryAxis.minPeriod = "mm"; // our data is daily, so we set minPeriod to DD
                      categoryAxis.gridAlpha = 0.1;
                      categoryAxis.minorGridAlpha = 0.1;
                      categoryAxis.axisAlpha = 0;
                      categoryAxis.minorGridEnabled = true;
                      categoryAxis.inside = true;

                      // value
                      var valueAxis = new AmCharts.ValueAxis();
                      valueAxis.tickLength = 0;
                      valueAxis.axisAlpha = 0;
                      valueAxis.showFirstLabel = false;
                      valueAxis.showLastLabel = false;
                      self.chart.addValueAxis(valueAxis);

                      // GRAPH
                      var graph = new AmCharts.AmGraph();
                      graph.dashLength = 3;
                      graph.lineColor = "#00CC00";
                      graph.valueField = "value";
                      graph.dashLength = 3;
                      graph.bullet = "round";
                      graph.balloonText = "[[category]]<br><b><span style='font-size:14px;'>value:[[value]]</span></b>";
                      self.chart.addGraph(graph);

                      // CURSOR
                      var chartCursor = new AmCharts.ChartCursor();
                      chartCursor.valueLineEnabled = true;
                      chartCursor.valueLineBalloonEnabled = true;
                      self.chart.addChartCursor(chartCursor);

                      // SCROLLBAR
                      var chartScrollbar = new AmCharts.ChartScrollbar();
                      self.chart.addChartScrollbar(chartScrollbar);

                      // HORIZONTAL GREEN RANGE
                      var guide = new AmCharts.Guide();
                      guide.value = 525;
                      guide.toValue = 575;
                      guide.fillColor = "#00CC00";
                      guide.inside = true;
                      guide.fillAlpha = 0.2;
                      guide.lineAlpha = 0;
                      valueAxis.addGuide(guide);


                      // WRITE

      $('#chartdiv').empty();
                      self.chart.write("chartdiv");


        }

  });

  var DeviceCollection = new Backbone.Collection;

  var mdotCollection = new mDotCollection();

  var mainSettings = new MainModel();
  var mainview = new MainView({collection: mdotCollection, model: mainSettings});

  var mdot = new MDOT({collection: mdotCollection});

  var grapher = new GraphView({collection: DeviceCollection});

})(jQuery);