<?php include ("./link/session.php") ?>
<!doctype html>
<html lang="uft-8">
 <head>
     <?php include ("./public/head.inc") ?>
 </head>
  <body>
  <?php include ("./public/menu.inc") ?>
    <div data-simplebar>
        <main class="page-content dashboard" id="app" v-cloak>
            <div class="row">
                <div class="col-lg-6">
                    <div class="card">
                        <div class="card-header bg-transparent">
                            <div class="p-2 mb-0 d-flex align-items-end">
                                <cn>系统状态</cn>
                                <en>System state</en>
                            </div>
                        </div>
                        <div class="card-body" >
                            <div class="row row-cols-3 text-center">
                                <div class="col-lg-4 ">
                                    <pie-chart v-model="cpu" :active-color="theme_color"></pie-chart>
                                    <div>
                                        <cn>CPU使用率</cn>
                                        <en>CPU usage</en>
                                    </div>
                                </div>
                                <div class="col-lg-4 text-center">
                                    <pie-chart v-model="mem" :active-color="theme_color"></pie-chart>
                                    <div>
                                        <cn>内存使用率</cn>
                                        <en>Memory usage</en>
                                    </div>
                                </div>
                                <div class="col-lg-4 text-center">
                                    <tmp-compt v-model="tmp" :active-color="theme_color"></tmp-compt>
                                    <div>
                                        <cn>核心温度</cn>
                                        <en>Core temperature</en>
                                    </div>
                                </div>
                            </div>
                        </div>
                    </div>
                </div>
    
                <div class="col-lg-6">
                    <div class="card">
                        <div class="card-header bg-transparent">
                            <div class="p-2 mb-0 d-flex align-items-end">
                                <cn>网络状态</cn>
                                <en>Network state</en>
                            </div>
                        </div>
                        <div class="card-body">
                            <net-chart v-if="tx.length > 0" :maxy="maxy" :data1="tx" :data2="rx" :key="netFlotKey"
                                       :line1-color="theme_color" :line2-color="line2_color" :tick-color="tickColor" :border-color="borderColor"
                                       :tip-border-color="tipBorderColor" :tip-bg-color="tipBgColor" :tip-txt-color="tipTxtColor"></net-chart>
                        </div>
                    </div>
                </div>
            </div>
            <div class="row">
                <div class="col-lg-12">
                    <div class="card">
                        <div class="card-body iface py-3">
                            <div v-for="(item,index) in input" :key="index" :class="[{'ms-5':index > 0},{'hdmi':item.protocol==='HDMI'},{'sdi':item.protocol==='SDI' || item.protocol==='AHD'},{'disable':!item.avalible}]">
                                <span class="info">{{item.info}}</span>
                                <div class="icon my-1"></div>
                                <span class="name">{{item.name}}</span>
                            </div>
                        </div>
                    </div>
                </div>
            </div>
            <div class="row mt-2">
                <div class="col-lg-12">
                    <div class="card">
                        <div class="card-header bg-transparent">
                            <div class="p-2 mb-0 d-flex align-items-end">
                                <cn>预览</cn>
                                <en>Preview</en>
                                <small style="margin-left: 5px;color: grey;font-size: 12px;">
                                    <cn>非实时视频，仅预览图片</cn>
                                    <en>Not a realtime video, picture only</en>
                                </small>
                            </div>
                        </div>
                        <div class="card-body">
                            <div class="row row-cols-2 row-cols-lg-4 g-3">
                                <div v-for="(item,index) in preview" :key="index" class="col">
                                    <div class="card">
                                        <img :src="makeImgUrl(item.id)" class="card-img-top">
                                        <div class="chn-volume" :style="{'width':handleChnVolume(item.id,'L')}"></div>
                                        <div class="chn-volume" :style="{'width':handleChnVolume(item.id,'R')}"></div>
                                        <div class="card-body">
                                            <p class="card-text text-center">{{item.name}}</p>
                                        </div>
                                    </div>
                                </div>
                            </div>
                        </div>
                    </div>
                </div>
            </div>
        </main>
    </div>
  <?php include ("./public/foot.inc") ?>
  <script src="assets/plugins/easyPieChart/jquery.easypiechart.js" type="module"></script>
  <script src="assets/plugins/flotChart/jquery.flot.js" type="module"></script>
  <script src="assets/plugins/flotChart/jquery.flot.resize.js" type="module"></script>

  <script type="module">
      import { rpc } from "./assets/js/lp.utils.js";
      import { useDefaultConf } from "./assets/js/vue.hooks.js";
      import { ignoreCustomElementPlugin,filterKeywordPlugin,bootstrapSwitchComponent,statusPieChartComponent,statusTemperatureComponent,netFlotChartComponent } from "./assets/js/vue.helper.js"
      import vue from "./assets/js/vue.build.js";
      import mutationObserver from './assets/plugins/polyfill/mutationobserver.esm.js';

      const { createApp,ref,reactive,onMounted } = vue;
      const app  = createApp({
          components:{
              "bs-switch":bootstrapSwitchComponent,
              "net-chart":netFlotChartComponent,
              "pie-chart":statusPieChartComponent,
              "tmp-compt":statusTemperatureComponent
          },
          setup(prop,context){

              const state = {
                  cpu: ref(0),
                  tmp: ref(0),
                  mem: ref(0),
                  maxy: ref(0),
                  tx : reactive([]),
                  rx : reactive([]),
                  data1:reactive([]),
                  data2:reactive([]),
                  theme_color:ref("#ffbb00"),
                  line2_color:ref("#555555"),
                  tipBorderColor:ref("#ffbb00"),
                  tipBgColor:ref("#ffffff"),
                  tipTxtColor:ref("#555555"),
                  tickColor:ref("#eeeeee"),
                  borderColor:ref("#cccccc"),
                  netFlotKey:ref(0),
                  preview : reactive([]),
                  input : reactive([]),
                  volume: reactive([])
              }

              const { defaultConf } = useDefaultConf();

              const getData1 = (d) => {
                  state.data1.shift();
                  state.data1.push( d );
                  state.tx.splice(0);
                  for (let i = 0; i < 100; i++)
                      state.tx.push([i,state.data1[i]]);
              }

              const getData2 = (d) => {
                  state.data2.shift();
                  state.data2.push( d );
                  state.rx.splice(0);
                  for (let i = 0; i < 100; i++)
                      state.rx.push([i,state.data2[i]]);
              }

              const updateNetState = () => {
                  if(state.data1.length === 0 && state.data2.length === 0) {
                      for ( let i = 0; i < 100; i++ ) {
                          state.data1.push( 0 );
                          state.data2.push( 0 );
                      }
                  }
                  rpc("enc.getNetState").then(data => {
                      getData1(data.tx);
                      getData2(data.rx);
                      if ( data.tx * 1.3 > state.maxy.value )
                          state.maxy.value = data.tx * 1.3;
                      if ( data.rx * 1.3 > state.maxy.value )
                          state.maxy.value = data.rx * 1.3;
                      if ( state.maxy.value < 1024 )
                          state.maxy.value = Math.ceil( state.maxy.value / 100 ) * 100;
                      else
                          state.maxy.value = Math.ceil( state.maxy.value / 1024 ) * 1024;
                      if ( state.maxy.value > 1024000 )
                          state.maxy.value = 1024000;
                      setTimeout(updateNetState, 500);
                  });
              }

              const updateSysState = () => {
                  rpc("enc.getSysState").then(data => {
                      state.cpu.value = data.cpu;
                      state.mem.value = data.mem;
                      state.tmp.value = data.temperature;
                      setTimeout(updateSysState, 2000);
                  });
              }

              const makeImgUrl = (id) => {
                  return "snap/snap" + id + ".jpg?rnd=" + Math.random();
              }

              const updatePreview = () => {
                  if(state.preview.length === 0) {
                      for(let i=0;i<defaultConf.length;i++) {
                          if (!defaultConf[i].enable  || ( defaultConf[i].type === "net" && !defaultConf[i].net.decodeV))
                              continue;
                          state.preview.push(defaultConf[i]);
                      }
                  }
                  setTimeout(() => rpc("enc.snap"),300);
                  setTimeout(updatePreview,800);
              }

              const handleChnVolume = (chnId,type) => {
                  let volume = state.volume.filter((item,index)=>{
                      return chnId === index;
                  })
                  let retVal = 0;
                  if(volume.length > 0)
                      retVal = volume[0][type] * 100/96;
                  return retVal + "%";
              }

              const updateVolume = () => {
                  rpc( "enc.getVolume").then(data => {
                      state.volume.splice(0,state.volume.length,...data);
                  });

                  if(window.location.host === "wx.linkpi.cn")
                      setTimeout(updateVolume,1000);
                  else
                      setTimeout(updateVolume,500);
              }

              const updateInputState = () => {
                  rpc("enc.getInputState").then(ret => {
                      state.input.splice(0, state.input.length, ...ret);
                      for(let i=0;i<state.input.length;i++) {
                          let ipt = state.input[i];
                          ipt.info = "- - -";
                          if(ipt.avalible)
                              ipt.info = "" + ipt.height + ( ipt.interlace ? "I" : "P" ) + ipt.framerate;
                          state.input[i] = ipt;
                      }
                  });
                  setTimeout(updateInputState,3000);
              }

              const onListenThemeChange = () => {
                  const html = document.querySelector('html');
                  const observer = new mutationObserver(mutations => {
                      mutations.forEach(mutation => {
                          if (mutation.type === 'attributes' && mutation.attributeName === "data-bs-theme") {
                              const theme = mutation.target.getAttribute("data-bs-theme");
                              if(theme === "default") {
                                  state.tickColor.value = '#eee';
                                  state.borderColor.value = '#ccc';
                                  state.tipBgColor.value = '#fff';
                                  state.tipBorderColor.value = '#fb0';
                                  state.tipTxtColor.value = '#555';
                                  state.line2_color.value = '#555';
                              }
                              if(theme === "dark") {
                                  state.tickColor.value = '#555';
                                  state.borderColor.value = '#555';
                                  state.tipBgColor.value = '#333';
                                  state.tipBorderColor.value = '#aaa';
                                  state.tipTxtColor.value = '#adb5bd';
                                  state.line2_color.value = '#999';
                              }
                              state.netFlotKey.value++;
                          }
                      });
                  });
                  const config = {
                      attributes: true,
                      attributeFilter: ["data-bs-theme"],
                      subtree: false
                  };
                  observer.observe(html, config);
              }

              onMounted(()=>{
                  updateSysState();
                  updateNetState();
                  updatePreview();
                  updateInputState();
                  updateVolume();
                  onListenThemeChange();
                }
              )

              return {...state, makeImgUrl,handleChnVolume}
          }
      })
      app.use(ignoreCustomElementPlugin);
      app.use(filterKeywordPlugin);
      app.mount('#app')
  </script>
  </body>
</html>