/*
* Copyright (c) 2021 Xilinx, Inc.
* 
* Permission is hereby granted, free of charge, to any person obtaining a copy of this software and 
* associated documentation files (the "Software"), to deal in the Software without restriction, including 
* without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 
* copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to 
* the following conditions: 
* 
* The above copyright notice and this permission notice shall be included in all copies or substantial 
* portions of the Software. 
* 
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT 
* LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, 
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
* 
*
*
*/
import { html, PolymerElement } from '@polymer/polymer/polymer-element.js';
import './datatable-imports.js';
import "@polymer/paper-dialog/paper-dialog.js";
import { api_url, configObj, notificationRef } from './constants';
import { handlePaging, redirectToLogin, handleErrorResponse, _updatepaginationtext } from './shared-script.js';
class moduleTable extends PolymerElement {
  static get template() {
    return html`
    <style>
            :host {
              display: block;
            }
            paper-card {
              display: block;
              width: 100%;
              margin: auto;
              --paper-card-background-color: white;
            }
            paper-button {
              background-color: #1E88E5;
              color:white;
              height:30px;
              float:right;
              font-size:14px;
              margin-right: 0px;
            }
            h2 span,
            .buttons {
              width: 100%;
              margin: 20px auto;
            }
            exmg-paper-toolbar .flex {
              @apply --layout-flex;
            }
            iron-input {
              width: 100%;
            }
            input {
              font-size: 14px;
              margin: 0px 4px;
              padding: 4px;
              border: 0px solid var(--divider-color);
              width: 100%;
            }
            exmg-paper-toolbar span.interactive-content {
              margin-left: 10px;
              white-space: nowrap;
              overflow: hidden;
              color: rgba(0,0,0,0.38);
              font-size: 14px;
              text-overflow: ellipsis;
              letter-spacing: .005em;
              box-sizing: border-box;
              font-weight: 400;
              cursor: pointer;
              width: 100%;
            }
            .search {
              background: #fff;
              box-shadow: 0 2px 2px 0 rgba(0, 0, 0, 0.14),
                  0 1px 5px 0 rgba(0, 0, 0, 0.12),
                  0 3px 1px -2px rgba(0, 0, 0, 0.2);
            }
            .search input {
              outline: none;
            }
            exmg-paper-datatable{
              font-size:14px;
            }
            paper-menu-button {
              float: right;
              padding: 0px;
            }
            .refClass {
              padding-top: 6px;
            }
            #Confirmationmodal {
              min-width: 25vw;
              width: 35vw;
              border-radius:5px;
            }
            #Confirmationmodal .refreshallcancelBtn, #Confirmationmodal .refreshallconfirmBtn {
              padding: 4px 8px;
              background-color: #1E88E5;
              color: #fff;
              font-size: 14px;
              font-weight: bold;
              text-align: center;
            }
            #Confirmationmodal .dialogfooter {
              display: flex;
              justify-content: flex-end;
            }
          </style>
          <h2>
            <span>Module Summary</span>
            <paper-menu-button horizontal-align="right" vertical-align="top" id="downloadtcl" vertical-offset="30">
              <paper-button slot="dropdown-trigger" noink raised>
                <span>Download</span>
              </paper-button>
              <paper-listbox slot="dropdown-content">
                <paper-item on-tap="_generateTCL">TCL</paper-item>
                <paper-item on-tap="_generateTCL">ZIP</paper-item>
              </paper-listbox>
            </paper-menu-button>
            <paper-button class="refClass" id="refreshBtn" raised noink on-tap="_opendialogforconfirmation">REFRESH ALL</paper-button>
          </h2>
          <iron-ajax method="post" id="refreshall" url={{urlRefresh}} body={{refreshBody}} handle-as="json" content-type="application/json" last-response="{{refreshItems}}" on-error="_handleErrorResponse"></iron-ajax>
          <paper-card elevation="1">
          <!-- Table Toobar -->
            <exmg-paper-toolbar>
              <div slot="default" class$="[[_computeSearchClasses(isSearch)]]">
                <template is="dom-if" if="[[isSearch]]" restamp="true">
                  <iron-icon icon="exmg-paper-icons:search"></iron-icon>
                  <iron-input bind-value="{{filterValue}}">
                    <input id="searchInput" placeholder="[[placeHolder]]" on-keyup="_handleKeyUp" on-blur="_handleInputBlur">
                  </iron-input>
                </template>
                <template is="dom-if" if="[[!isSearch]]" restamp="true">
                  <iron-icon icon="exmg-paper-icons:search"></iron-icon>
                  <span class="interactive-content" on-tap="_showSearch">[[_getFilterValue(filterValue)]]</span>
                </template>
              </div>
            </exmg-paper-toolbar>
            <!-- DataTable -->
            <exmg-paper-datatable>
              <!-- THead -->
              <exmg-paper-thead sorted="{{sorted}}" sort-direction="{{sortDirection}}">
                <template>
                  <div class="tr">
                    <div title="Name" class="th flex-none" sortable="instance_name" style="width:20%">
                      <span>Module Name</span>
                    </div>
                    <div title="Base Address" class="th flex-none" sortable="base_address" style="width:12%">
                      <span>Base Address</span>
                    </div>
                    <!-- <div title="Version" class="th flex-none" sortable="module_version" style="width:8%">
                      <span>Version</span>
                    </div> -->
                    <div title="Description" class="th flex-none" sortable="instance_description" style="width:48%">
                      <span>Description</span>
                    </div>
                    <div title="Refresh" class="th flex-none" style="width:10%">
                      <span>Refresh</span>
                    </div>
                    <div title="Download" class="th flex-none" style="width:10%">
                      <span>Download</span>
                    </div>
                  </div>
                </template>
              </exmg-paper-thead>
              <!-- TBody -->
              <exmg-paper-tbody items="[[items]]" id="moduleTableBody">
                <template>
                  <div class="tr" style="height:100%" data-modname$="{{item.name}}" data-key$="{{item.key}}" data-instancename$="{{item.instance_name}}" data-modaddress$="{{item.base_address}}">
                    <div class="td flex-none" style="width:20%;height: auto;padding-top: .5em;padding-bottom: .5em;">
                      <span title="[[item.instance_name]]" style="color: #1E88E5;cursor:pointer" on-tap="_loadRegisters">[[item.instance_name]]</span>
                    </div>
                    <div class="td flex-none" style="width:12%;height: auto;padding-top: .5em;padding-bottom: .5em;">
                      <span title="[[item.base_address]]">[[item.base_address]]</span>
                    </div>
                    <!-- <div class="td flex-none" style="width:8%;height: auto;padding-top: .5em;padding-bottom: .5em;">
                      <span title="[[item.module_version]]">[[item.module_version]]</span>
                    </div> -->
                    <div class="td flex-none" style="width:48%;height: auto;padding-top: .5em;padding-bottom: .5em;">
                      <span style="white-space: normal;" title="[[item.instance_description]]">[[item.instance_description]]</span>
                    </div>
                    <div class="td flex-none" style="width:10%;height: auto;padding-top: .5em;padding-bottom: .5em;">
                      <button class="refreshCol" style$="[[_computedStyle(item)]]" on-tap="_refreshOffset">
                        <iron-icon icon="refresh"></iron-icon>
                      </button>
                    </div>
                    <div class="td flex-none" style="width:10%;height: auto;padding-top: .5em;padding-bottom: .5em;">
                      <button style="cursor:pointer;padding:0px;" on-tap="_generateTCL">
                        <iron-icon icon="file-download"></iron-icon>
                      </button>
                    </div>
                  </div>
                </template>
              </exmg-paper-tbody>
            </exmg-paper-datatable>
            <!-- Table Paging -->
            <exmg-paper-paging total-items={{totalItems}} page-index="{{pageIndex}}" page-size="{{pageSize}}"></exmg-paper-paging>
          </paper-card>
          <!-- Load contacts from json file  -->
          <iron-ajax method="post" id="modulerequest" url=[[url]] body={{reqObj}} handle-as="json" content-type="application/json" last-response="{{rawItems}}" on-error="_handleErrorResponse"></iron-ajax>
          <iron-ajax method="post" id="generateTCL" url=[[urlTCL]] body={{moduleData}} handle-as="json" content-type="application/json" last-response="{{responseTCL}}" on-error="_handleErrorResponse"></iron-ajax>
          <iron-ajax method="post" id="generateTable" url={{urlSearch}} body={{searchBody}} handle-as="json" content-type="application/json" last-response="{{rawItems}}" on-error="_handleErrorResponse"></iron-ajax>
          <!-- Filter items by filter value and return resulting items to the data provider  -->
          <exmg-paper-data-filter raw-items="[[rawItems]]" items="{{filteredItems}}" filter-value="[[filterValue]]" filter-fields="instance_name,base_address"></exmg-paper-data-filter>
          <!-- Manage sorting and paging  -->
          <exmg-paper-data-helper raw-items="[[filteredItems]]" items="{{items}}" page-index="[[pageIndex]]" page-size="[[pageSize]]" sorted="[[sorted]]" sort-direction="[[sortDirection]]" total-items={{totalItems}}></exmg-paper-data-helper>
          <paper-dialog id="Confirmationmodal" entry-animation="scale-up-animation" exit-animation="fade-out-animation">
              <div class="header"><h2>Confirmation</h2></div>
              <div class="dialogbody">
                <div class="confirmationmsgblock">
                  This functionality will take around 18 mins approximately for execution, do you want to continue ..?
                </div>
              </div>
              <div class="dialogfooter">
                <paper-button class="refreshallconfirmBtn" on-tap="_refreshAllModules" raised noink>Continue</paper-button>
                <paper-button class="refreshallcancelBtn" dialog-dismiss raised noink>Close</paper-button>
              </div>
            </paper-dialog>
          `;
  }
  static get properties() {
    return {
      pageIndex: {
        type: Number,
        value: 0,
      },
      pageSize: {
        type: Number,
        value: 25,
      },
      sorted: {
        type: String,
        value: 'instance_name',
      },
      sortDirection: {
        type: String,
        value: 'ASC',
      },
      filterValue: {
        type: String,
        value: '',
      },
      isSearch: {
        type: Boolean,
        value: false,
      },
      placeHolder: {
        type: String,
        value: 'Search Module by name or address',
      },
      url: {
        type: String,
        value: this.url
      },
      reqObj: {
        type: Object,
        value: {}
      },
      key: {
        type: String,
        value: this.key
      },
      refreshset: {
        type: Boolean,
        value: false
      },
      moduleData: {
        type: Object,
        value: {}
      },
      urlTCL: {
        type: String,
        value: ''
      },
      urlSearch: {
        type: String,
        value: ''
      },
      urlRefresh: {
        type: String,
        value: `${api_url}checkmodule`
      },
      refreshBody: {
        type: Object,
        value: { 'hw_name': '' }
      },
      searchBody: {
        type: Object,
        value: ''
      }
    };
  }
  _computedClass(isSelected) {
    let classes = 'tr item';
    if (isSelected) {
      classes += ' selected';
    }
    return classes;
  }

  _computedStyle(ele) {
    let style = 'cursor: pointer;padding:0px;';
    if (ele.color)
      style += 'color:' + ele.color;
    return style;
  }

  _stopTap(e) {
    // Do something
    e.stopPropagation();
  }

  _getFilterValue(filterValue) {
    return filterValue || this.placeHolder;
  }

  _handleKeyUp(e) {
    if (e.keyCode === 27) {
      this._hideSearch();
    }
    this.pageIndex = 0;
    let self = this;
    let eve = "";
    _updatepaginationtext(eve, self);
  }

  _handleInputBlur() {
    this._hideSearch();
  }

  _hideSearch() {
    this.set('isSearch', false);
  }

  _showSearch() {
    this.set('isSearch', true);
    setTimeout(() => this.shadowRoot.querySelector('#searchInput').focus(), 200);
  }

  _computeSearchClasses(isSearch) {
    return isSearch ? 'search' : '';
  }

  _opendialogforconfirmation(e) {
    this.$.Confirmationmodal.toggle();
  }

  _refreshAllModules(e) {
    let self = this;
    console.log("in regresh all function");
    this.$.Confirmationmodal.close();
    if (MyAppGlobals.boardstatus) {
      let key = self.key.toUpperCase();
      self.refreshBody.hw_name = key;
      document.querySelector("#pageloader").style.display = "block";
      const session = JSON.parse(localStorage.getItem('storedUser'));
      self.$.refreshall.headers['uid'] = session.uid;
      self.$.refreshall.headers['version'] = session.version;
      let request = self.$.refreshall.generateRequest();
      request.completes.then((req) => {
        const results = req.response.response;
        configObj['refresh_status'] = true;
        self.$.moduleTableBody.shadowRoot.querySelectorAll('.tr').forEach((element, k) => {
          const inst_name = element.getAttribute('data-instancename');
          let resobj = _.findWhere(results, { "instance_name": inst_name });
          if (resobj !== undefined) {
            if (resobj.match == false) {
              element.querySelector('.refreshCol').style.color = resobj.color;
            }
          }
        });
        self.rawItems.forEach((element, i) => {
          let resobj = _.findWhere(results, { "instance_name": element.instance_name });
          if (resobj !== undefined) {
            if (resobj.match == false) {
              element.color = resobj.color;
            }
          }
        });
        self.set('rawItems', self.rawItems);
        document.querySelector("#pageloader").style.display = "none";
      }, () => {
        if (request.status == 400)
          redirectToLogin();
      });
    } else {
      notificationRef.setAttribute('text', 'Please Connect to board and try again');
      notificationRef.open();
    }
  }

  _refreshOffset(e) {
    if (MyAppGlobals.boardstatus) {
      this.refreshset = true;
      let key = this.key;
      if (this.urlSearch)
        key = e.currentTarget.parentNode.parentNode.dataset.key.toLowerCase();
      this._redirectingPage(e, key);
    } else {
      notificationRef.setAttribute('text', 'Please Connect to board and try again');
      notificationRef.open();
    }
  }

  _loadRegisters(e) {
    this.refreshset = false;
    let key = this.key;
    if (this.urlSearch)
      key = e.currentTarget.parentNode.parentNode.dataset.key.toLowerCase();
    key = (key === "am012")? "ps": key;
    document.querySelector("#pageloader").style.display = "block";
    this._redirectingPage(e, key);
  }

  _redirectingPage(e, key) {
    configObj[`${key}`] = {};
    const element = e.currentTarget.parentNode.parentNode;
    configObj[`${key}`]['modulename'] = element.getAttribute("data-modname");
    configObj[`${key}`]['moduleinstancename'] = element.getAttribute("data-instancename");
    configObj[`${key}`]['moduleaddress'] = element.getAttribute("data-modaddress");
    import(`./../templates/configuration/${key}-register.js`);
    if (this.parentNode.parentNode.querySelector("#" + key + "registerWidgetlevel")) {
      this.parentNode.parentNode.querySelector("#" + key + "registerWidgetlevel").remove();
    }
    const registerBlock = document.createElement('div');
    registerBlock.setAttribute('id', `${key}registerWidgetlevel`);
    registerBlock.innerHTML = "";
    registerBlock.innerHTML = `<${key}-register data-refreshset=${this.refreshset}></${key}-register>`;
    registerBlock.style.display = "block";
    if (this.urlSearch)
      this.parentNode.parentNode.querySelector('#foundDataTable').append(registerBlock);
    else
      this.parentNode.parentNode.append(registerBlock);
    this.style.display = "none";
  }

  _generateTCL(e) {
    let temp = {};
    const key = (this.key === "ps")? "am012" :  this.key.toUpperCase();
    temp.hw_name = key;
    temp.format = 'tcl';
    let fileName = temp.hw_name;
    if (e.target.innerText.trim()) {
      temp.format = e.target.innerText.trim().toLowerCase();
    }
    if (e.currentTarget.parentNode.parentNode.getAttribute('data-instancename')) {
      temp.instance_name = e.currentTarget.parentNode.parentNode.getAttribute('data-instancename');
      fileName += '_' + temp.instance_name;
    }
    this.moduleData = temp;
    const session = JSON.parse(localStorage.getItem('storedUser'));
    this.$.generateTCL.headers['uid'] = session.uid;
    this.$.generateTCL.headers['version'] = session.version;
    let request = this.$.generateTCL.generateRequest();
    request.completes.then((req) => {
      const element = document.createElement('a');
      element.setAttribute('href', `${api_url}files/${fileName}.${temp.format}`);
      e.target.appendChild(element);
      element.click();
      e.target.removeChild(element);
    }, () => {
      if (request.status == 400)
        redirectToLogin();
    });
  }

  _handleErrorResponse(req) {
    handleErrorResponse(req);
  }

  ready() {
    super.ready();
    let self = this;
    if (this.dataset.urlsearch && this.dataset.searchbody) {
      this.urlTCL = `${api_url}generatetclfile`;
      this.searchBody = this.dataset.searchbody;
      this.$.refreshBtn.style.display = 'none';
      this.urlSearch = this.dataset.urlsearch;
      if (this.key === 'all') {
        this.$.downloadtcl.style.display = 'none';
      } else {
        this.$.downloadtcl.style.display = 'block';
      }
      const session = JSON.parse(localStorage.getItem('storedUser'));
      this.$.generateTable.headers['uid'] = session.uid;
      this.$.generateTable.headers['version'] = session.version;
      let request = this.$.generateTable.generateRequest();
      request.completes.then((req) => {
        document.querySelector("#pageloader").style.display = "none";
        if (req.response.length > 0) {
          this.style.display = "block";
          let e = "";
          _updatepaginationtext(e, self);
          this.parentNode.parentNode.querySelector('#errorMsg').style.display = 'none';
        } else {
          this.style.display = "none";
          this.parentNode.parentNode.querySelector('#errorMsg').style.display = 'block';
        }
      }, () => {
        if (request.status == 400)
          redirectToLogin();
      });
    } else {
      this.$.refreshBtn.style.display = 'block';
      this.urlTCL = this.dataset.urltcl;
      const session = JSON.parse(localStorage.getItem('storedUser'));
      this.$.modulerequest.headers['uid'] = session.uid;
      this.$.modulerequest.headers['version'] = session.version;
      let request = this.$.modulerequest.generateRequest();
      request.completes.then((req) => {
        document.querySelector("#pageloader").style.display = "none";
        let e = "";
        _updatepaginationtext(e, self);
      }, () => {
        if (request.status == 400)
          redirectToLogin();
      });
    }
    const pagingTable = this.shadowRoot.querySelector('exmg-paper-paging').shadowRoot.querySelector('paper-dropdown-menu');
    pagingTable.addEventListener('iron-select', e => { handlePaging(e, this) });
    const paginationbtns = this.shadowRoot.querySelector('exmg-paper-paging').shadowRoot.querySelector('.page-actions').querySelectorAll('paper-icon-button');
    _.each(paginationbtns, (ele, ind) => {
      ele.addEventListener('click', e => {
        _updatepaginationtext(e, self);
      });
    });
  }
}
window.customElements.define('module-table', moduleTable);
