define([
  // Application variable, always include it to have access to app methods.
  'app',

  //templates-loader: this loads templates async.
  'js/templates-loader',
  'backgrid',
  'modules/modal2',
  'moment',
  'backgrid/moment-cell'

],
function (app, T, Backgrid, Modal, moment) {

    var Screen = { Models: {}, Views: {}, Collections: {} }

    Screen.Models.Main = Backbone.Epoxy.Model.extend({
        defaults: {
            furnaceCode: 1,
            furnaces: [{ label: 'A', value: 1 }, { label: 'B', value: 2 }],

            equipmentLocations: {},
            equipmentLocationId: null,

            hasData: false,
            isLoading: false,
        },
        initialize: function () {
            this.fetchEquipmentTypesPicker();
        },
        fetchEquipmentTypesPicker: function () {
            var that = this;
            var qp = new Core.Database.QueryParameters();
            Core.Json.CallProcedure(
                app.DatabaseNames.MES + '.EAF.GetEquipmentLocationsPicker',
                qp,
                {
                    onSuccess: function (resp) {
                        try {

                            if ((resp) && (resp.Table)) {
                                var records = resp.Table,
                                    newColl;
                                newColl = _.map(records, function (obj) {
                                    return {
                                        label: (obj.Name ? obj.Name : '') + ((obj.EquipmentTypeId && obj.Name) ? (' - ' + obj.EquipmentTypeName) : (obj.EquipmentTypeId ? obj.EquipmentTypeName : '') ),
                                        value: obj.Id,
                                    }
                                });
                                that.set('equipmentLocations', newColl);
                            }
                            else {
                                if ((resp) && (resp.Message))
                                    console.error(resp.Message);
                                else
                                    console.error('Server response not valid.');
                            }
                        }
                        catch (error) { console.error((error.stack) ? error.stack : new Error(error).stack); }
                    },
                    Secured: true,
                    Async: false,
                },
                app.ConnectionStrings.app
            );

            return this;
        },
        
    });

    Screen.Models.Item = Backbone.Epoxy.Model.extend({
        parse: function (obj) {
            var result = {
                EventId: obj.EventId,
                DateTime :new moment(obj.DateTime).format('YYYY-MM-DD HH:mm:ss'),
                EquipmentId :obj.EquipmentId,
                EquipmentName :obj.EquipmentName,
                Comments: obj.Comments,
                EquipmentLocationId: obj.EquipmentLocationId,
            };
            return result;
        }
    })

    Screen.Collections.Items = Backbone.Collection.extend({
        model: Screen.Models.Item,
       
        fetch: function (params) {
            var that = this;
            var qp = new Core.Database.QueryParameters();
            qp.Add('@furnaceCode', 'INT', params.furnaceCode);
            qp.Add('@equipmentLocationId', 'INT', params.equipmentLocationId == 'all' ? null : params.equipmentLocationId);
            Core.Json.CallProcedure(
                app.DatabaseNames.MES + '.EAF.GetEquipmentChangeEvents',
                qp,
                {
                    onSuccess: function (resp) {
                        try {

                            if ((resp) && (resp.Table)) {
                                var records = resp.Table,
                                    newColl;
                                newColl = _.map(records, that.model.prototype.parse);
                                that.set(newColl).trigger('fetch', that, resp);
                            }
                            else {
                                if ((resp) && (resp.Message))
                                    console.error(resp.Message);
                                else
                                    console.error('Server response not valid.');
                            }
                        }
                        catch (error) { console.error((error.stack) ? error.stack : new Error(error).stack); }
                    },
                    Secured: true,
                    Async: false,
                },
                app.ConnectionStrings.app
            );

            return this;
        },

        insertEquipment: function (params, model) {
            var that = this;
            var qp = new Core.Database.QueryParameters();
            qp.Add('@datetime', 'DATETIME', new moment(params.dateModal, 'MM/DD/YYYY').format('YYYY-MM-DD') + ' ' + new moment(params.timeModal, 'HH:mm:ss').format('HH:mm:ss'));
            qp.Add('@FurnaceCode', 'INT', model.furnaceCode);
            qp.Add('@EquipmentLocationId', 'INT', params.equipmentLocationId);
            qp.Add('@EquipmentId', 'INT', params.equipmentId);
            qp.Add('@Comments', 'VARCHAR(MAX)', params.comments);

            Core.Json.CallProcedure(
                app.DatabaseNames.MES + '.EAF.ChangeComponentWeb',
                qp,
                {
                    onSuccess: function (resp) {
                        try {

                            if (resp) {
                            }
                            else {
                                if ((resp) && (resp.Message)) {
                                    app.views.topMessages.showMessage(resp.Message, { stay: 5000, });
                                    console.error(resp.Message);
                                } else {
                                    app.views.topMessages.showMessage(resp.Message, { stay: 5000, });
                                    console.error(resp.Message);
                                }
                            }
                        }
                        catch (error) { console.error((error.stack) ? error.stack : new Error(error).stack); }
                    },
                    Secured: true,
                    Async: false,
                },
                app.ConnectionStrings.app
            );

            return this;
        },

        removeEvent: function (params) {
            var that = this;
            var qp = new Core.Database.QueryParameters();
            qp.Add('@eventId', 'INT', params.EventId);
            Core.Json.CallProcedure(
                app.DatabaseNames.MES + '.EAF.RemoveEvent',
                qp,
                {
                    onSuccess: function (resp) {
                        try {

                            if ((resp)) {
                            }
                            else {
                                if ((resp) && (resp.Message)) {
                                    app.views.topMessages.showMessage(resp.Message, { stay: 5000, });
                                    console.error(resp.Message);
                                } else {
                                    app.views.topMessages.showMessage(resp.Message, { stay: 5000, });
                                    console.error(resp.Message);
                                }
                            }
                        }
                        catch (error) { console.error((error.stack) ? error.stack : new Error(error).stack); }
                    },
                    Secured: true,
                    Async: false,
                },
                app.ConnectionStrings.app
            );

            return this;
        },

    })

    Screen.Views.Main = Backbone.Epoxy.View.extend({
        template: 'eaf-equipment-events',
        id: 'eaf-equipment-events',
        title: 'EAF Equipment Events',
        events: function () {
            return {
                'click #refreshBtn': this.refreshBtn_click,
                'click #addEvent': this.addEventBtn_click,
            };
        },
        bindings: 'data-bind',

        initialize: function () {
            this.options.state = app.view_states.loading;
            this.options.onappend = (_.isFunction(this.options.onappend)) ? this.options.onappend : function () { };

            this.model = new Screen.Models.Main();
            this.items = new Screen.Collections.Items();

            this.bus = _.extend({}, Backbone.Events);
            this.bus.on("modalAcceptBtn", this.onModalAcceptBtn, this);
            this.bindEvents();
        },
        
        bindEvents: function () {
            this.listenTo(this.items, 'fetch', this.items_fetched);
        
        },

        render: function (container, urlParams) {
            var that = this;
            var thatContainer = (this.options.container) ? this.options.container : container;
            this.options.container = thatContainer;

            var customPath = '/app/custom-screens/' + this.template + '/';

            T.render.call(
                this,
                this.template,
                function (tmp) {
                    if (!that.options.i18n) that.options.i18n = {};

                    app.getI18NJed(
                        that,
                        that.template,
                        function (i18nJED) {
                            that.options.i18n[that.template] = i18nJED;
                            that.$el.html(tmp());
                            that.applyBindings();

                            that.$el.find('.input-date').datepicker();
                            var columns = [
                                {
                                    name: 'DateTime',
                                    label: app.translate(that, 'item_DateTime_col_label'),
                                    cell: Backgrid.StringCell.extend({
                                        className: 'string-cell align-center-cell',
                                        modelFormat: 'YYYY-MM-DD HH:mm:ss',
                                        displayFormat: 'YYYY-MM-DD HH:mm:ss',
                                    }),
                                    editable: false,
                                },
                                {
                                    name: 'EquipmentName',
                                    label: app.translate(that, 'item_EquipmentName_col_label'),
                                    cell: Backgrid.StringCell.extend({
                                        className: 'string-cell align-center-cell',
                                    }),
                                    editable: false,
                                },
                                {
                                    name: 'Comments',
                                    label: app.translate(that, 'item_Comments_col_label'),
                                    cell: Backgrid.StringCell.extend({
                                        className: 'string-cell align-center-cell',
                                    }),
                                    editable: false,
                                },
                                {
                                    name: 'Actions',
                                    label: '',
                                    editable: false,
                                    sortable: false,
                                    cell: Backgrid.Cell.extend({
                                        template: Handlebars.compile(that.$el.find('#actions_cell_template').html()),
                                        className: 'actions-cell five-percent',
                                        events: {
                                            'click .btn-cell-action': 'cellActionClick'
                                        },

                                        initialize: function () {
                                            Backgrid.Cell.prototype.initialize.apply(this, arguments);
                                           
                                        },
                                        render: function () {
                                            this.$el.html(this.template());

                                            this.$el.find('[data-toggle="tooltip"]').tooltip();
                                            this.delegateEvents();
                                            return this;
                                        },
                                        cellActionClick: function (e) {
                                            try {
                                                var target = $(e.target);
                                                var actionData = target.closest('[data-cell-action]').data('cell-action');
                                               
                                                if (actionData) {
                                                    that.actionOnRow(this.model,actionData);
                                                }
                                            }
                                            catch (error) { console.error((error.stack) ? error.stack : new Error(error).stack); }
                                        },
                                    }),
                                },

                            ];

                            var grid = new Backgrid.Grid({
                                className: 'backgrid table table-hover table-condensed production-table',
                                collection: that.items,
                                columns: columns,
                            });

                            //container.append(grid.render().el);
                            that.$el.find('.items-grid-container').append(grid.render().el);

                                                       
                            //appending view to the main container
                            that.append(thatContainer, that.$el);

                            var fixedParams = _.extend({}, urlParams);
                            that.model.set(fixedParams);
                            that.refresh(); 
                                                       
                        },
                        true,
                        customPath
                    );
                },
                customPath
            );
        },

        onModalAcceptBtn: function (params) {
            this.items.insertEquipment(params, this.model.toJSON());
            this.refresh();
        },
        addEventBtn_click: function () {
            var that = this;
            var modal = new Screen.Views.DelaysModal({
                equipmentLocations: that.model.get('equipmentLocations'),
                equipmentLocationId: that.model.get('equipmentLocationId'),
                bus: that.bus,
            });
            modal.show();
        },
        actionOnRow: function (model,action) {
            try {
                var that = this;
                switch (action) {
                    case 'DELETE':
                        modal = new Modal.Views.Main({
                            focusOk: false,
                            focusSelector: '#btn-cancel',
                            title: app.translate([this, app], "delete_item_modal_confirm_title"),
                            message: app.translate([this, app], "delete_item_modal_confirm_message"),
                            buttons_type: "CONTINUE-CANCEL",
                        });

                        this.listenToOnce(modal, "continue", function (modal) {
                            try {
                                that.items.removeEvent(model.toJSON());
                                that.refresh();
                            }
                            catch (error) { console.error((error.stack) ? error.stack : new Error(error).stack); }
                        });
                        modal.show();
                        break;
                }
            }
            catch (error) { console.error((error.stack) ? error.stack : new Error(error).stack); }

        },

        refresh: function () {
            this.model.set({
                isLoading: true,
                hasData: false,
            });
            params = this.model.toJSON();
            this.items.fetch(params);

        },
        UpdateURL: function () {
            try {
                var params = this.model.toJSON();
                app.router.navigate(
                    app.router.resolveURL(
                        app.router.currentModule,
                        _.extend(
                            {},
                            params,
                            {
                                furnaceCode: params.furnaceCode,
                            }
                        ),
                        false
                    ),
                    { trigger: false, }
                );
            }
            catch (e) { console.error((e.stack) ? e.stack : new Error(e).stack); }
        },

        refreshBtn_click: function (e) {
            this.UpdateURL();
            this.refresh();
        },

        items_fetched: function () {
            try {
                var that = this;
                setTimeout(
                    function () {
                        that.model.set({
                            hasData: (that.items.length > 0),
                            isLoading: false,
                        });

                    },
                    100
                );
            }
            catch (e) { console.error((e.stack) ? e.stack : new Error(e).stack); }
        },

        append: function (container, el) {
            el = (el != null && el != undefined) ? el : this.$el;

            if (this.options.state == app.view_states.loading
                || this.options.state == app.view_states.shown) {
                //appending view to the main container and set state to shown

                this.options.state = app.view_states.shown;
                container.append(el);

                this.options.onappend(this);
            }

            if (this.options.state == app.view_states.hidden) {
                //append and remain hidden
                container.append(el);
            }

            if (this.options.state == app.view_states.closed) {
                //return without appending.
                return;
            }
        },
        bindViewScopedEvents: function () {
            var that = this;
        },
        unbindViewScopedEvents: function () {

        },
        close: function () {
            this.options.state = app.view_states.closed;
            
            this.closeSubviews();
            this.remove();
            this.unbindViewScopedEvents();
            this.unbind();
        },
        closeSubviews: function () {
            _.each(this.subviews, function (sview) {
                sview.close();
            });
        },
        show: function () {
            this.options.state = app.view_states.shown;

            this.showSubviews();
            this.bindEvents();
            this.$el.show();
        },
        showSubviews: function () {
            _.each(this.subviews, function (sview) {
                sview.show();
            });
        },
        hide: function () {
            this.options.state = app.view_states.hidden;

            this.hideSubviews();

            this.$el.hide();
            this.unbind();
            this.stopListening();
        },
        hideSubviews: function () {
            _.each(this.subviews, function (sview) {
                sview.hide();
            });
        },
        preRender: function () {
            app.models.subnavbar.set("subnavbar", false);
        },
        reRender: function (urlParams) {
            try {
                this.refresh(viewParams);
            } catch (Error) { }
        },

    });

    Screen.Models.DelaysModalMain = Backbone.Epoxy.Model.extend({
        defaults: {
            title: '',
            errorMsg: '',
            processing: false,

            dateModal: new moment().format('MM/DD/YYYY'),
            timeModal: new moment().format('HH:mm:ss'),

            equipmentId: null,
            equipments: {},
            comments: '',
            equipmentTypeName: '',
            equipmentLocations: {},
            equipmentLocationId: null,
            equipmentsLength: null,
        },

        fetchEquipmentsPicker: function () {
            var that = this;
            var qp = new Core.Database.QueryParameters();
            qp.Add('@EquipmentLocationId', 'INT', this.get('equipmentLocationId'));
            Core.Json.CallProcedure(
                app.DatabaseNames.MES + '.EAF.GetEquipmentsByLocation',
                qp,
                {
                    onSuccess: function (resp) {
                        try {

                            if ((resp) && (resp.Table)) {
                                var records = resp.Table,
                                    newColl;
                                newColl = _.map(records, function (obj) {
                                    return {
                                        label: obj.EquipmentName,
                                        value: obj.EquipmentId,
                                        equipmentTypeName: obj.EquipmentTypeName,
                                    }
                                });
                                that.set('equipments', newColl);
                            }
                            else {
                                if ((resp) && (resp.Message))
                                    console.error(resp.Message);
                                else
                                    console.error('Server response not valid.');
                            }
                        }
                        catch (error) { console.error((error.stack) ? error.stack : new Error(error).stack); }
                    },
                    Secured: true,
                    Async: false,
                },
                app.ConnectionStrings.app
            );

            return this;
        },

    });

    Screen.Views.DelaysModal = Backbone.Epoxy.View.extend({
        template: "eaf-equipment-events",
        id: "delays-modal",
        className: "modal modal-delays hide fade",
        bindings: "data-bind",
        isCacheable: true,
        events: function () {
            return {
                "click #acceptBtn": this.acceptBtn_click,
                "click #cancelBtn": this.cancelBtn_click,
                "submit form": this.form_submit,
                "keypress": this.modal_keypress,
                "show.bs.modal": this.modal_show,
                "shown.bs.modal": this.modal_shown,
                "hidden.bs.modal": this.modal_hidden,
            };
        },

        container: null,
        disposed: false,
        isRendered: false,
        preventDispose: false,
        visible: false,

        initialize: function (options) {
            _.extend(this, options);
            if (!this.model) {
                this.model = new Screen.Models.DelaysModalMain();
            }
            var currentEquipmentLocationObj = _.findWhere(options.equipmentLocations, { value: parseInt(options.equipmentLocationId) });
            currentEquipmentLocationName = currentEquipmentLocationObj ? currentEquipmentLocationObj.label : ''; 

            this.model.set({
                dateModal: new moment().format('MM/DD/YYYY'),
                timeModal: new moment().format('HH:mm:ss'),
                equipmentLocations: options.equipmentLocations,
                equipmentLocationId: options.equipmentLocationId,
                title: 'New Event:' + ' ' + currentEquipmentLocationName,
            });
            this.model.fetchEquipmentsPicker();

            this.model.set({
                equipmentsLength: this.model.get('equipments') ? (this.model.get('equipments').length == 0 ? null : this.model.get('equipments').length) : null,
            });
            this.bus = options.bus;

            this.bindEvents();

            return this;
        },

        hide: function (preventDispose) {
            this.preventDispose = (preventDispose);

            this.$el.modal('hide');
        },
        render: function (container) {
            if (container)
                this.container = container;

            var that = this;
            var customPath = '/app/custom-screens/' + this.template + '/';
            T.render.call(this, this.template, function (tmp) {
                if (!that.i18n) that.i18n = {};
                app.getI18NJed(that, that.template, function (i18nJED) {
                    that.i18n[that.template] = i18nJED;
                    that.$el.html(tmp(that.model.toJSON()));
                    that.applyBindings();

                    that.isRendered = true;


                    that.$el.find('#dateModal').datepicker();
                    that.$el.find('#timeModal').timepicker({
                        showMeridian: false,
                        secondStep: 1,
                        minuteStep: 1,
                        showSeconds: true,
                    });

                    that.trigger("render");
                    if (!that.model.get("equipmentsLength")) {
                        that.$el.find('#equipments').attr("disabled", true);
                    }

                }, true, customPath);

            }, customPath, "delays_declare_modal");

        },
        show: function () {
            if (!this.isRendered) {
                this.render();
            }
            else {
                this.$el.modal({
                    keyboard: true,
                    backdrop: 'both',
                });
            }

            return this;
        },

        bindEvents: function () {
            this.listenToOnce(this, "render", this.view_render);
            this.listenTo(this.model, "change : equipmentId", this.getEquipmentTypeName);
        },

        getEquipmentTypeName: function () {
            var params = this.model.toJSON();
            var equip = _.findWhere(params.equipments, { value: parseInt(params.equipmentId) });
            this.model.set('equipmentTypeName', equip ? equip.equipmentTypeName  : '' );
        },

        close: function () {
            if (this.disposed == false) {
                if (this.visible == true) {
                    this.hide();
                }
                else {
                    this.trigger('close');

                    this.remove();
                    this.unbind();

                    this.disposed = true;
                }
            }
        },
        preRender: function () {
            app.models.subnavbar.set("dateControl", false);
        },
        reRender: function () {
        },

        acceptBtn_click: function (e) {
            try {
                var params = this.model.toJSON();
                this.bus.trigger("modalAcceptBtn",params);

                this.close();
            }
            catch (e) { console.error((e.stack) ? e.stack : new Error(e).stack); }
        },
        form_submit: function (e) {
            try {
                e.preventDefault();
            }
            catch (e) { console.error((e.stack) ? e.stack : new Error(e).stack); }
        },
        modal_hidden: function (e) {
            try {
                this.visible = false;

                if (!this.preventDispose)
                    this.close();
                else
                    this.preventDispose = false;
            }
            catch (e) { console.error((e.stack) ? e.stack : new Error(e).stack); }
        },
        modal_show: function (e) {
            try {
                this.visible = true;
            }
            catch (e) { console.error((e.stack) ? e.stack : new Error(e).stack); }
        },
        modal_shown: function (e) {
            try {
                this.$el.find(".autofocus").focus();
            }
            catch (e) { console.error((e.stack) ? e.stack : new Error(e).stack); }
        },
        view_render: function () {
            try {
                this.show();
            }
            catch (e) { console.error((e.stack) ? e.stack : new Error(e).stack); }
        },
       
    });


    // Required, return the module for AMD compliance.
    return Screen;
});