@twab/visualization 1.4.3 → 1.4.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/dist/visualization.js +107 -105
  2. package/package.json +1 -1
@@ -1364,43 +1364,50 @@ FramesInterface.prototype.changeTime = async function (time) {
1364
1364
  };
1365
1365
 
1366
1366
  FramesInterface.prototype.loadFrames = async function () {
1367
- let prev = (await this.framesManager.getPrevImages()) || [];
1368
- let next = (await this.framesManager.getNextImages()) || [];
1369
- let current = (await this.framesManager.getCurrentImages()) || [];
1367
+ let frames = await Promise.all([
1368
+ this.constructImagesComponent(this.framesManager.getPrevImages() || []),
1369
+ this.constructImagesComponent(this.framesManager.getCurrentImages() || []),
1370
+ this.constructImagesComponent(this.framesManager.getNextImages() || []),
1371
+ ]);
1370
1372
 
1371
- prev = await this.constructImagesComponent(prev);
1372
- current = await this.constructImagesComponent(current);
1373
- next = await this.constructImagesComponent(next);
1374
-
1375
- this.frames = { prev, current, next };
1373
+ this.frames = { prev: frames[0], current: frames[1], next: frames[2] };
1376
1374
  };
1377
1375
 
1378
1376
  FramesInterface.prototype.loadNextFrames = async function () {
1379
- this.framesManager.next();
1380
-
1381
- let next = (await this.framesManager.getNextImages()) || [];
1382
- next = await this.constructImagesComponent(next);
1383
-
1384
- this.frames.prev = this.frames.current;
1385
- this.frames.current = this.frames.next;
1386
- this.frames.next = next;
1377
+ return new Promise((resolve) => {
1378
+ this.framesManager.next();
1379
+
1380
+ this.constructImagesComponent(
1381
+ this.framesManager.getNextImages() || []
1382
+ ).then((next) => {
1383
+ this.frames.prev = this.frames.current;
1384
+ this.frames.current = this.frames.next;
1385
+ this.frames.next = next;
1386
+ resolve();
1387
+ });
1388
+ })
1387
1389
  };
1388
1390
 
1389
1391
  FramesInterface.prototype.loadPrevFrames = async function () {
1390
- this.framesManager.previous();
1391
-
1392
- if (this.framesManager.currentTime < this.firstFrameTime) {
1393
- await this.framesManager.goTo(this.firstFrameTime);
1394
- await this.loadFrames();
1395
- return
1396
- }
1397
-
1398
- let prev = (await this.framesManager.getPrevImages()) || [];
1399
- prev = await this.constructImagesComponent(prev);
1400
-
1401
- this.frames.next = this.frames.current;
1402
- this.frames.current = this.frames.prev;
1403
- this.frames.prev = prev;
1392
+ return new Promise((resolve) => {
1393
+ this.framesManager.previous();
1394
+
1395
+ if (this.framesManager.currentTime < this.firstFrameTime) {
1396
+ this.framesManager
1397
+ .goTo(this.firstFrameTime)
1398
+ .then(this.loadFrames)
1399
+ .then(resolve);
1400
+ } else {
1401
+ this.constructImagesComponent(
1402
+ this.framesManager.getPrevImages() || []
1403
+ ).then((prev) => {
1404
+ this.frames.next = this.frames.current;
1405
+ this.frames.current = this.frames.prev;
1406
+ this.frames.prev = prev;
1407
+ resolve();
1408
+ });
1409
+ }
1410
+ })
1404
1411
  };
1405
1412
 
1406
1413
  FramesInterface.prototype.constructImagesComponent = async function (array) {
@@ -3343,6 +3350,17 @@ var script = {
3343
3350
  // }
3344
3351
  },
3345
3352
  methods: {
3353
+ stopVideoPlaying(array) {
3354
+ for (const frame of array || this.$refs.frames) {
3355
+ if (
3356
+ frame.videoStatus === frame.Status.playing ||
3357
+ frame.videoStatus === frame.Status.paused
3358
+ ) {
3359
+ frame.stop(false);
3360
+ }
3361
+ }
3362
+ this.activeVideo = null;
3363
+ },
3346
3364
  toogleCommandsVisibility() {
3347
3365
  this.commandBarShow = !this.commandBarShow;
3348
3366
  setTimeout(this.resize, 0);
@@ -3419,7 +3437,7 @@ var script = {
3419
3437
  nextLoopActivate() {
3420
3438
  this.breakLoop();
3421
3439
  this.loopInterval = setInterval(
3422
- () => this.next(true),
3440
+ () => this.next({ ignoreTime: true }),
3423
3441
  this.swapImagesDelay
3424
3442
  );
3425
3443
  setTimeout(() => {
@@ -3763,7 +3781,7 @@ var script = {
3763
3781
  },
3764
3782
  arrowUp() {
3765
3783
  if (
3766
- this.activeFrame - this.numberOfRows * this.framesPerRow >
3784
+ this.activeFrame - this.numberOfRows * this.framesPerRow >=
3767
3785
  Math.round((this.numberOfRows * this.framesPerRow) / 2)
3768
3786
  ) {
3769
3787
  this.activeFrame -= this.framesPerRow;
@@ -3778,9 +3796,16 @@ var script = {
3778
3796
  }
3779
3797
  },
3780
3798
  checkLimitRight(value) {
3781
- this.endAudienceTime.match(/.{1,2}/g);
3799
+ const hours = this.endAudienceTime.match(/.{1,2}/g);
3782
3800
  const d = this.getDateParts();
3783
- const high = Date.UTC(d.year, d.month, d.day, 26, 59, 59);
3801
+ const high = Date.UTC(
3802
+ d.year,
3803
+ d.month,
3804
+ d.day,
3805
+ hours[0],
3806
+ parseInt(hours[1]) + 30,
3807
+ hours[2]
3808
+ );
3784
3809
 
3785
3810
  if (value) {
3786
3811
  return (
@@ -3812,64 +3837,58 @@ var script = {
3812
3837
  )
3813
3838
  }
3814
3839
  },
3815
- async next(ignoreTime = false) {
3840
+ async next(config = {}) {
3816
3841
  if (
3817
- (ignoreTime || Date.now() - this.lastNext > this.swapImagesDelay) &&
3818
- this.checkLimitRight(true)
3842
+ (config.ignoreTime ||
3843
+ Date.now() - this.lastNext > this.swapImagesDelay) &&
3844
+ this.checkLimitRight(true) &&
3845
+ !this.navigationPending
3819
3846
  ) {
3820
- const array = this.$refs.frames.filter(
3821
- (fc) =>
3822
- fc.videoStatus === fc.Status.playing ||
3823
- fc.videoStatus === fc.Status.paused
3824
- );
3847
+ this.navigationPending = true;
3848
+ this.stopVideoPlaying();
3825
3849
 
3826
- if (array.length === 1) {
3827
- const frame = array[0];
3828
- frame.stop(false);
3829
- }
3830
- this.fInterface.setCurrentStep(this.secondsPerFrame);
3831
- await this.fInterface.loadNextFrames();
3832
-
3833
- this.activeFrame = this.getIndex(1, 0, Positions.current);
3834
- this.activeVideo = null;
3850
+ this.navigationPending = await new Promise((resolve) => {
3851
+ this.fInterface.loadNextFrames().then(() => {
3852
+ this.activeFrame = this.getIndex(1, 0, Positions.current);
3835
3853
 
3836
- this.getFramesArray();
3837
- this.lastNext = Date.now();
3854
+ this.getFramesArray();
3855
+ this.lastNext = Date.now();
3856
+ resolve(false);
3857
+ });
3858
+ });
3859
+ } else {
3860
+ console.error('next blocked');
3838
3861
  }
3839
3862
  },
3840
3863
  async prev(config = {}) {
3841
3864
  if (
3842
3865
  (config.ignoreTime ||
3843
3866
  Date.now() - this.lastPrev > this.swapImagesDelay) &&
3844
- this.checkLimitLeft(true)
3867
+ this.checkLimitLeft(true) &&
3868
+ !this.navigationPending
3845
3869
  ) {
3846
- const array = this.$refs.frames.filter(
3847
- (fc) =>
3848
- fc.videoStatus === fc.Status.playing ||
3849
- fc.videoStatus === fc.Status.paused
3850
- );
3851
- if (array.length === 1) {
3852
- const frame = array[0];
3853
- frame.stop(false);
3854
- }
3855
-
3856
- this.fInterface.setCurrentStep(this.secondsPerFrame);
3857
- await this.fInterface.loadPrevFrames();
3858
-
3859
- if (config.stayOnLast) {
3860
- this.activeFrame = this.getIndex(
3861
- this.numberOfRows,
3862
- this.framesPerRow - 1,
3863
- Positions.current
3864
- );
3865
- } else {
3866
- this.activeFrame = this.getIndex(1, 0, Positions.current);
3867
- }
3868
-
3869
- this.activeVideo = null;
3870
+ this.navigationPending = true;
3871
+ this.stopVideoPlaying();
3872
+
3873
+ this.navigationPending = await new Promise((resolve) => {
3874
+ this.fInterface.loadPrevFrames().then(() => {
3875
+ if (config.stayOnLast) {
3876
+ this.activeFrame = this.getIndex(
3877
+ this.numberOfRows,
3878
+ this.framesPerRow - 1,
3879
+ Positions.current
3880
+ );
3881
+ } else {
3882
+ this.activeFrame = this.getIndex(1, 0, Positions.current);
3883
+ }
3870
3884
 
3871
- this.getFramesArray();
3872
- this.lastPrev = Date.now();
3885
+ this.getFramesArray();
3886
+ this.lastPrev = Date.now();
3887
+ resolve(false);
3888
+ });
3889
+ });
3890
+ } else {
3891
+ console.error('prev blocked');
3873
3892
  }
3874
3893
  },
3875
3894
  async setStartTime(time) {
@@ -3905,16 +3924,7 @@ var script = {
3905
3924
  if (value) {
3906
3925
  return new Promise((resolve) => {
3907
3926
  setTimeout(async () => {
3908
- const array = this.$refs.frames.filter(
3909
- (fc) =>
3910
- fc.videoStatus === fc.Status.playing ||
3911
- fc.videoStatus === fc.Status.paused
3912
- );
3913
-
3914
- if (array.length === 1) {
3915
- const frame = array[0];
3916
- frame.stop(false);
3917
- }
3927
+ this.stopVideoPlaying();
3918
3928
 
3919
3929
  await this.setStartTime(value, true);
3920
3930
  resolve();
@@ -3944,15 +3954,7 @@ var script = {
3944
3954
  const array = this.$refs.frames.filter(
3945
3955
  (fc) => fc.frame.time !== frame.time
3946
3956
  );
3947
-
3948
- for (let ref of array) {
3949
- if (
3950
- ref.videoStatus === ref.Status.playing ||
3951
- ref.videoStatus === ref.Status.paused
3952
- ) {
3953
- ref.stop(false);
3954
- }
3955
- }
3957
+ this.stopVideoPlaying(array);
3956
3958
 
3957
3959
  this.videoTotalTime = totalTime;
3958
3960
  this.videoPlaying = true;
@@ -3987,8 +3989,8 @@ var script = {
3987
3989
  if (this.removeSelectionOnInsert) {
3988
3990
  this.hourIniSelected = null;
3989
3991
  this.hourEndSelected = null;
3992
+ this.canInsertTime = false;
3990
3993
  }
3991
- this.canInsertTime = false;
3992
3994
  },
3993
3995
  insertTimeForce() {
3994
3996
  this.$emit('timeToInsert', {
@@ -4005,8 +4007,8 @@ var script = {
4005
4007
  if (this.removeSelectionOnInsert) {
4006
4008
  this.hourIniSelected = null;
4007
4009
  this.hourEndSelected = null;
4010
+ this.canInsertTime = false;
4008
4011
  }
4009
- this.canInsertTime = false;
4010
4012
  },
4011
4013
  async getChannelMedia() {
4012
4014
  // this.media = (await ChannelService.show(this.channel)).data.MEDIA
@@ -4049,14 +4051,14 @@ var script = {
4049
4051
  },
4050
4052
  },
4051
4053
  watch: {
4052
- secondsPerFrame(value) {
4054
+ async secondsPerFrame(value) {
4053
4055
  const activeF =
4054
4056
  this.frames[this.activeFrame - this.numberOfRows * this.framesPerRow];
4055
4057
 
4056
4058
  if (activeF) {
4057
4059
  this.changeHour(this.getAudienceTime(activeF.time, 0, 0, 0));
4058
4060
  this.fInterface.setCurrentStep(this.secondsPerFrame);
4059
- this.fInterface.loadFrames();
4061
+ await this.fInterface.loadFrames();
4060
4062
  this.getFramesArray();
4061
4063
  }
4062
4064
  },
@@ -4680,11 +4682,11 @@ __vue_render__._withStripped = true;
4680
4682
  /* style */
4681
4683
  const __vue_inject_styles__ = function (inject) {
4682
4684
  if (!inject) return
4683
- inject("data-v-11249812_0", { source: "\n.visualization-row[data-v-11249812] {\r\n display: flex;\r\n flex-wrap: wrap;\r\n flex: 1 1 auto;\n}\n.visualization-col[data-v-11249812] {\r\n flex-basis: 0;\r\n flex-grow: 1;\r\n max-width: 100%;\r\n padding: 12px;\n}\n.visualization-divider[data-v-11249812] {\r\n display: block;\r\n flex: 1 1 100%;\r\n height: 0px;\r\n max-height: 0px;\r\n opacity: 1;\r\n transition: inherit;\r\n border-style: solid;\r\n border-width: thin 0 0 0;\r\n border-color: rgba(0, 0, 0, 0.12);\r\n margin: 0;\n}\n.visualization-divider.vertical[data-v-11249812] {\r\n align-self: stretch;\r\n border-width: 0 thin 0 0;\r\n display: inline-flex;\r\n height: inherit;\r\n margin-left: -1px;\r\n max-height: 100%;\r\n max-width: 0px;\r\n vertical-align: text-bottom;\r\n width: 0px;\n}\n.visualization-card[data-v-11249812] {\r\n flex-basis: 0;\r\n flex-grow: 1;\r\n max-width: 100%;\r\n padding: 12px;\r\n width: 100%;\r\n transition-property: box-shadow, opacity, -webkit-box-shadow;\r\n overflow-wrap: break-word;\r\n /*box-shadow: 0 3px 1px -2px rgba(0, 0, 0, 0.2), 0 2px 2px 0 rgba(0, 0, 0, 0.14),\r\n 0 1px 5px 0 rgba(0, 0, 0, 0.12);*/\n}\n.visualization-justify-center[data-v-11249812],[data-v-11249812] .visualization-justify-center {\r\n justify-content: center;\n}\n.visualization-align-center[data-v-11249812] {\r\n align-items: center;\n}\n#visualization-container[data-v-11249812] {\r\n max-width: 100% !important;\r\n margin: 0 auto !important;\r\n height: 100%;\r\n border-bottom: none;\n}\n#visualization-container > .card[data-v-11249812] {\r\n border-radius: 0 !important;\r\n font-size: 12px;\r\n width: 100%;\r\n box-shadow: none;\r\n height: 100%;\n}\n#command-bar[data-v-11249812],\r\n#info-bar[data-v-11249812] {\r\n background-color: #f5f5f5;\r\n box-shadow: 0 3px 1px -2px rgba(0, 0, 0, 0.2), 0 2px 2px 0 rgba(0, 0, 0, 0.14),\r\n 0 1px 5px 0 rgba(0, 0, 0, 0.12);\n}\n#command-bar button[data-v-11249812] {\r\n width: 42px;\r\n height: 36px;\r\n border: none;\r\n background: none;\n}\n#command-bar button[data-v-11249812]:hover {\r\n cursor: pointer;\r\n background: rgba(0, 0, 0, 0.12);\n}\n#command-bar svg[data-v-11249812] {\r\n font-size: 16px;\n}\n#command-bar[data-v-11249812] {\r\n padding: 0 !important;\n}\n#info-bar[data-v-11249812] {\r\n padding: 4px;\r\n font-size: 14px;\r\n position: relative;\n}\n.settings-container[data-v-11249812] {\r\n position: absolute;\r\n right: 14px;\r\n top: 50%;\r\n transform: translateY(-50%);\n}\n.settings-container > *[data-v-11249812] {\r\n margin: 0 2px;\r\n cursor: pointer;\n}\n#info-bar svg[data-v-11249812] {\r\n font-size: 16px;\n}\n#info-bar .divider[data-v-11249812] {\r\n margin: 0 8px;\n}\nsvg[data-v-11249812]:focus {\r\n border: none;\n}\n.visualization-card[data-v-11249812] {\r\n border-left: 8px solid #eee;\n}\n.active-tab[data-v-11249812] {\r\n border-left: 8px solid var(--visualization-primary) !important;\r\n border-image-slice: 1;\n}\n[id^='frame-'][data-v-11249812] {\r\n padding: 1px;\r\n display: flex;\r\n flex-flow: column;\n}\n.tooltip[data-v-11249812] {\r\n display: block !important;\r\n z-index: 10000;\n}\n.tooltip .tooltip-inner[data-v-11249812] {\r\n background: var(--visualization-primary);\r\n color: white;\r\n border-radius: 16px;\r\n padding: 5px 10px 4px;\n}\n.tooltip .tooltip-arrow[data-v-11249812] {\r\n width: 0;\r\n height: 0;\r\n border-style: solid;\r\n position: absolute;\r\n margin: 5px;\r\n border-color: var(--visualization-primary);\r\n z-index: 1;\n}\n.tooltip[x-placement^='top'][data-v-11249812] {\r\n margin-bottom: 5px;\n}\n.tooltip[x-placement^='top'] .tooltip-arrow[data-v-11249812] {\r\n border-width: 5px 5px 0 5px;\r\n border-left-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n bottom: -5px;\r\n left: calc(50% - 5px);\r\n margin-top: 0;\r\n margin-bottom: 0;\n}\n.tooltip[x-placement^='bottom'][data-v-11249812] {\r\n margin-top: 5px;\n}\n.tooltip[x-placement^='bottom'] .tooltip-arrow[data-v-11249812] {\r\n border-width: 0 5px 5px 5px;\r\n border-left-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-top-color: transparent !important;\r\n top: -5px;\r\n left: calc(50% - 5px);\r\n margin-top: 0;\r\n margin-bottom: 0;\n}\n.tooltip[x-placement^='right'][data-v-11249812] {\r\n margin-left: 5px;\n}\n.tooltip[x-placement^='right'] .tooltip-arrow[data-v-11249812] {\r\n border-width: 5px 5px 5px 0;\r\n border-left-color: transparent !important;\r\n border-top-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n left: -5px;\r\n top: calc(50% - 5px);\r\n margin-left: 0;\r\n margin-right: 0;\n}\n.tooltip[x-placement^='left'][data-v-11249812] {\r\n margin-right: 5px;\n}\n.tooltip[x-placement^='left'] .tooltip-arrow[data-v-11249812] {\r\n border-width: 5px 0 5px 5px;\r\n border-top-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n right: -5px;\r\n top: calc(50% - 5px);\r\n margin-left: 0;\r\n margin-right: 0;\n}\n.tooltip.popover .popover-inner[data-v-11249812] {\r\n background: #f9f9f9;\r\n color: black;\r\n padding: 24px;\r\n border-radius: 5px;\r\n box-shadow: 0 5px 30px rgba(black, 0.1);\n}\n.tooltip.popover .popover-arrow[data-v-11249812] {\r\n border-color: #f9f9f9;\n}\n.tooltip[aria-hidden='true'][data-v-11249812] {\r\n visibility: hidden;\r\n opacity: 0;\r\n transition: opacity 0.15s, visibility 0.15s;\n}\n.tooltip[aria-hidden='false'][data-v-11249812] {\r\n visibility: visible;\r\n opacity: 1;\r\n transition: opacity 0.15s;\n}\r\n", map: {"version":3,"sources":["C:\\workspace\\visualization\\src\\Visualization.vue"],"names":[],"mappings":";AAmrCA;EACA,aAAA;EACA,eAAA;EACA,cAAA;AACA;AAEA;EACA,aAAA;EACA,YAAA;EACA,eAAA;EACA,aAAA;AACA;AAEA;EACA,cAAA;EACA,cAAA;EACA,WAAA;EACA,eAAA;EACA,UAAA;EACA,mBAAA;EACA,mBAAA;EACA,wBAAA;EACA,iCAAA;EACA,SAAA;AACA;AAEA;EACA,mBAAA;EACA,wBAAA;EACA,oBAAA;EACA,eAAA;EACA,iBAAA;EACA,gBAAA;EACA,cAAA;EACA,2BAAA;EACA,UAAA;AACA;AAEA;EACA,aAAA;EACA,YAAA;EACA,eAAA;EACA,aAAA;EACA,WAAA;EACA,4DAAA;EACA,yBAAA;EACA;qCACA;AACA;AAEA;EAEA,uBAAA;AACA;AAEA;EACA,mBAAA;AACA;AAEA;EACA,0BAAA;EACA,yBAAA;EACA,YAAA;EACA,mBAAA;AACA;AACA;EACA,2BAAA;EACA,eAAA;EACA,WAAA;EACA,gBAAA;EACA,YAAA;AACA;AAEA;;EAEA,yBAAA;EACA;mCACA;AACA;AACA;EACA,WAAA;EACA,YAAA;EACA,YAAA;EACA,gBAAA;AACA;AAEA;EACA,eAAA;EACA,+BAAA;AACA;AAEA;EACA,eAAA;AACA;AAEA;EACA,qBAAA;AACA;AAEA;EACA,YAAA;EACA,eAAA;EACA,kBAAA;AACA;AAEA;EACA,kBAAA;EACA,WAAA;EACA,QAAA;EACA,2BAAA;AACA;AAEA;EACA,aAAA;EACA,eAAA;AACA;AAEA;EACA,eAAA;AACA;AAEA;EACA,aAAA;AACA;AAEA;EACA,YAAA;AACA;AAEA;EACA,2BAAA;AACA;AAEA;EACA,8DAAA;EACA,qBAAA;AACA;AAEA;EACA,YAAA;EACA,aAAA;EACA,iBAAA;AACA;AAEA;EACA,yBAAA;EACA,cAAA;AACA;AAEA;EACA,wCAAA;EACA,YAAA;EACA,mBAAA;EACA,qBAAA;AACA;AAEA;EACA,QAAA;EACA,SAAA;EACA,mBAAA;EACA,kBAAA;EACA,WAAA;EACA,0CAAA;EACA,UAAA;AACA;AAEA;EACA,kBAAA;AACA;AAEA;EACA,2BAAA;EACA,yCAAA;EACA,0CAAA;EACA,2CAAA;EACA,YAAA;EACA,qBAAA;EACA,aAAA;EACA,gBAAA;AACA;AAEA;EACA,eAAA;AACA;AAEA;EACA,2BAAA;EACA,yCAAA;EACA,0CAAA;EACA,wCAAA;EACA,SAAA;EACA,qBAAA;EACA,aAAA;EACA,gBAAA;AACA;AAEA;EACA,gBAAA;AACA;AAEA;EACA,2BAAA;EACA,yCAAA;EACA,wCAAA;EACA,2CAAA;EACA,UAAA;EACA,oBAAA;EACA,cAAA;EACA,eAAA;AACA;AAEA;EACA,iBAAA;AACA;AAEA;EACA,2BAAA;EACA,wCAAA;EACA,0CAAA;EACA,2CAAA;EACA,WAAA;EACA,oBAAA;EACA,cAAA;EACA,eAAA;AACA;AAEA;EACA,mBAAA;EACA,YAAA;EACA,aAAA;EACA,kBAAA;EACA,uCAAA;AACA;AAEA;EACA,qBAAA;AACA;AAEA;EACA,kBAAA;EACA,UAAA;EACA,2CAAA;AACA;AAEA;EACA,mBAAA;EACA,UAAA;EACA,yBAAA;AACA","file":"Visualization.vue","sourcesContent":["<template>\r\n <div\r\n class=\"visualization-row\"\r\n id=\"visualization-container\"\r\n @click=\"framesClicked\"\r\n >\r\n <GlobalEvents\r\n v-if=\"!readOnly && canInsertTime && settingsClosed\"\r\n @keydown.45=\"insertTime\"\r\n />\r\n <GlobalEvents\r\n v-if=\"!readOnly && active && settingsClosed\"\r\n @keydown.83.prevent=\"setHourIni\"\r\n @keydown.69.prevent=\"setHourEnd\"\r\n />\r\n <GlobalEvents\r\n v-if=\"active && settingsClosed\"\r\n @keydown.left.prevent=\"arrowLeft\"\r\n @keydown.right.prevent=\"arrowRight\"\r\n @keydown.up.prevent=\"arrowUp\"\r\n @keydown.down.prevent=\"arrowDown\"\r\n @keydown.shift.page-down.prevent=\"nextLoopActivate\"\r\n @keydown.page-down.prevent=\"() => next()\"\r\n @keydown.page-up.prevent=\"() => prev()\"\r\n @keydown.shift.page-up.prevent=\"prevLoopActivate\"\r\n @keydown.36.prevent=\"goToFirstFrame\"\r\n @keydown.35.prevent=\"goToLastFrame\"\r\n @keydown.71.prevent=\"dialogs.goTo = true\"\r\n @keydown.73.prevent=\"dialogs.secondsPerFrame = true\"\r\n @keydown.76.prevent=\"dialogs.frames = true\"\r\n @keydown.49.97=\"() => (secondsPerFrame = 1)\"\r\n @keydown.50.98=\"() => (secondsPerFrame = 2)\"\r\n @keydown.51.99=\"() => (secondsPerFrame = 3)\"\r\n @keydown.52.100=\"() => (secondsPerFrame = 4)\"\r\n @keydown.53.101=\"() => (secondsPerFrame = 5)\"\r\n />\r\n <GlobalEvents\r\n v-if=\"prevLoop || nextLoop\"\r\n @keydown=\"breakLoop\"\r\n v-on:click=\"breakLoop\"\r\n />\r\n <settings\r\n v-if=\"active\"\r\n :dialogs-visibility=\"dialogs\"\r\n :playback-rate=\"playbackRate\"\r\n :seconds-per-frame=\"secondsPerFrame\"\r\n :frames-per-row=\"framesPerRow\"\r\n :number-of-rows=\"numberOfRows\"\r\n @change-playback-rate=\"(value) => (playbackRate = value)\"\r\n @change-go-to=\"changeHour\"\r\n @change-seconds-per-frame=\"(value) => (secondsPerFrame = value)\"\r\n @set-frames-selection=\"setFrameSelection\"\r\n @close=\"(dialog) => (dialogs[dialog] = false)\"\r\n />\r\n <div\r\n :class=\"{ 'visualization-card': true, 'active-tab': active }\"\r\n style=\"width: 100%; padding: 0\"\r\n >\r\n <command-bar\r\n v-show=\"commandBarShow\"\r\n :read-only=\"readOnly\"\r\n :video-playing=\"videoPlaying\"\r\n :video-paused=\"paused\"\r\n :insert-time=\"canInsertTime\"\r\n :hour-ini-selected=\"!!hourIniSelected\"\r\n :hour-end-selected=\"!!hourEndSelected\"\r\n @prev-loop-activate=\"prevLoopActivate\"\r\n @next-loop-activate=\"nextLoopActivate\"\r\n @prev=\"prev\"\r\n @next=\"next\"\r\n @go-to=\"dialogs.goTo = true\"\r\n @open-frame-selection=\"dialogs.frames = true\"\r\n @open-frames-per-second=\"dialogs.secondsPerFrame = true\"\r\n @open-blocks=\"openBlocks\"\r\n @open-playback-rate=\"dialogs.playbackRate = true\"\r\n @play-or-pause=\"playOrPause\"\r\n @stop-playing=\"stopPlayingBar\"\r\n @set-hour-ini=\"setHourIni\"\r\n @set-hour-end=\"setHourEnd\"\r\n @insert-time=\"insertTime\"\r\n />\r\n <video-progress\r\n v-if=\"videoProgressBar\"\r\n v-show=\"videoPlaying\"\r\n :video-time=\"videoTime\"\r\n />\r\n <info-bar\r\n :playback-rate=\"playbackRate\"\r\n :seconds-per-frame=\"secondsPerFrame\"\r\n :commands-show=\"commandBarShow\"\r\n :cache=\"useCache\"\r\n :block-start-time=\"blockStartTime\"\r\n :video-total-duration=\"videoSliderTotalDuration\"\r\n :alternative-server=\"alternativeServer\"\r\n :frames-per-row=\"framesPerRow\"\r\n :number-of-rows=\"numberOfRows\"\r\n :hour-ini=\"hourIniSelected\"\r\n :hour-end=\"hourEndSelected\"\r\n @toogle-commands-visibility=\"toogleCommandsVisibility\"\r\n @toogle-cache=\"useCache = !useCache\"\r\n @change-server=\"changeServerClick\"\r\n />\r\n <div\r\n class=\"visualization-row\"\r\n v-for=\"rowNumber in numberOfRows\"\r\n :id=\"'row-' + rowNumber\"\r\n :key=\"'row-' + rowNumber\"\r\n style=\"padding: 2px 12px\"\r\n >\r\n <div\r\n v-for=\"(frame, frameNumber) in previousFrames\"\r\n :key=\"\r\n numberOfRows +\r\n '-' +\r\n framesPerRow +\r\n '-' +\r\n getIndex(rowNumber, frameNumber, Positions.previous)\r\n \"\r\n style=\"display: none\"\r\n >\r\n <span v-html=\"frame.img\" />\r\n </div>\r\n <div\r\n v-for=\"(frame, frameNumber) in nextFrames\"\r\n :key=\"\r\n numberOfRows +\r\n '-' +\r\n framesPerRow +\r\n '-' +\r\n getIndex(rowNumber, frameNumber, Positions.next)\r\n \"\r\n style=\"display: none\"\r\n >\r\n <span v-html=\"frame.img\" />\r\n </div>\r\n <div\r\n class=\"visualization-col\"\r\n v-for=\"(frame, frameNumber) in frames.slice(\r\n framesPerRow * (rowNumber - 1),\r\n framesPerRow * rowNumber\r\n )\"\r\n :key=\"'row-' + rowNumber + '-frame-' + frameNumber\"\r\n :id=\"`frame-${getIndex(rowNumber, frameNumber, Positions.current)}`\"\r\n :class=\"{ loaderImg: !!frame.img }\"\r\n @click=\"\r\n frame.time\r\n ? selectFrame(\r\n getIndex(rowNumber, frameNumber, Positions.current),\r\n frame\r\n )\r\n : null\r\n \"\r\n >\r\n <span :id=\"activeFrame ? 'aa' : 0\" style=\"text-align: center\">\r\n <b>\r\n {{\r\n getAudienceTime(\r\n frame.time,\r\n rowNumber,\r\n frameNumber,\r\n Positions.current\r\n )\r\n }}\r\n </b>\r\n </span>\r\n\r\n <frame\r\n ref=\"frames\"\r\n :frame=\"frame\"\r\n :index=\"getIndex(rowNumber, frameNumber, Positions.current)\"\r\n :grid-settings=\"{ numberOfRows, framesPerRow }\"\r\n :initialTime=\"frame.time === hourIniSelected\"\r\n :endTime=\"frame.time === hourEndSelected\"\r\n :betweenTime=\"\r\n frame.time > hourIniSelected && frame.time < hourEndSelected\r\n \"\r\n :active=\"\r\n getIndex(rowNumber, frameNumber, Positions.current) ===\r\n activeFrame\r\n \"\r\n :activeTab=\"active\"\r\n :videoUrl=\"fInterface ? fInterface.getVideoUrl(frame) : ''\"\r\n :videoControls=\"videoControls\"\r\n @startPlaying=\"startPlaying\"\r\n @stopPlaying=\"stopPlaying\"\r\n @playPauseStatus=\"changePlayPause\"\r\n @updateSlider=\"updateSlider\"\r\n :playback-rate=\"playbackRate\"\r\n style=\"margin: 0 auto\"\r\n ></frame>\r\n </div>\r\n </div>\r\n </div>\r\n <!-- <settings\r\n ref=\"settings2\"\r\n :active=\"active\"\r\n @goToTime=\"changeHour\"\r\n @goToBlockInterval=\"changeBlockInterval\"\r\n @setSplitTime=\"setSplitTime\"\r\n @setFrameSelection=\"setFrameSelection\"\r\n @setPlaybackRate=\"\r\n (rate) => {\r\n playbackRate = rate\r\n }\r\n \"\r\n >\r\n </settings> -->\r\n <!-- <v-dialog v-model=\"dialog\" width=\"500\">\r\n <div class=\"card\">\r\n <div class=\"card\"-title class=\"text-h5 grey lighten-2\">\r\n {{ ' Último bloco disponível até: ' }}\r\n <v-btn\r\n @click=\"goToStartBlock\"\r\n class=\"ml-2\"\r\n dark\r\n color=\"success\"\r\n depressed\r\n >\r\n <v-icon left> fa-clock </v-icon>\r\n {{ timeLastBlock }}\r\n </v-btn>\r\n <v-spacer></v-spacer>\r\n <v-btn color=\"error\" fab small class=\"ml-5\" @click=\"dialog = false\">\r\n <v-icon dark> fa fa-xmark </v-icon>\r\n </v-btn>\r\n </div-title>\r\n </div>\r\n </v-dialog>\r\n <Help :media=\"media\" @close=\"media = null\" />\r\n <v-dialog\r\n v-if=\"userMultiTabsGrid\"\r\n v-model=\"userMultiTabsGridsModel\"\r\n persistent\r\n width=\"60%\"\r\n >\r\n <div class=\"card\">\r\n <div class=\"card\"-title class=\"warning text-h5\" primary-title>\r\n <div class=\"row\" class=\"ma-0\" justify=\"center\" align=\"center\">\r\n <v-icon dark left style=\"font-size: 24px !important\">\r\n fa fa-exclamation-triangle\r\n </v-icon>\r\n <div style=\"color: white\">{{ $t('form.alert') }}</div>\r\n </div>\r\n </div-title>\r\n <div class=\"card\"-text class=\"justify-center pa-6 grey lighten-2\">\r\n <h3>\r\n {{ $t('alerts.userMultiTabsGrid') }}\r\n </h3>\r\n </div-text>\r\n <hr class=\"divider\" class=\"grey lighten-1\"></span>\r\n <div class=\"card\"-actions class=\"grey lighten-2 justify-center\">\r\n <v-btn color=\"error\" ml-5 @click=\"userMultiTabsGrid = false\">\r\n <v-icon left color=\"white\">fa fa-times</v-icon>\r\n {{ $t('form.close') }}\r\n </v-btn>\r\n </div-actions>\r\n </div>\r\n </v-dialog> -->\r\n </div>\r\n</template>\r\n<script>\r\nimport Frame from './components/Frame.vue'\r\nimport FramesInterface from './utils/FramesInterface.js'\r\nimport FramesService from './services/FramesService.js'\r\n\r\nimport Commands from './components/Commands.vue'\r\nimport Infos from './components/Infos.vue'\r\nimport VideoProgress from './components/VideoProgress.vue'\r\nimport Settings from './components/Settings.vue'\r\n\r\nconst Positions = Object.freeze({\r\n previous: 0,\r\n current: 1,\r\n next: 2,\r\n})\r\n\r\nexport default {\r\n name: 'visualization-container',\r\n props: {\r\n value: {\r\n type: Boolean,\r\n required: true,\r\n },\r\n date: {\r\n type: String,\r\n required: true,\r\n },\r\n channel: {\r\n type: Number,\r\n required: true,\r\n },\r\n startAudienceTime: {\r\n type: String,\r\n required: true,\r\n },\r\n endAudienceTime: {\r\n type: String,\r\n required: true,\r\n },\r\n videoProgressBar: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n jumpOnInsert: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n removeSelectionOnInsert: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n framesFormat: {\r\n type: [Number, String],\r\n default: 7,\r\n },\r\n maxSize: {\r\n type: Number,\r\n },\r\n videoControls: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n readOnly: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n },\r\n components: {\r\n Frame,\r\n CommandBar: Commands,\r\n InfoBar: Infos,\r\n VideoProgress,\r\n Settings,\r\n // Help,\r\n },\r\n data() {\r\n return {\r\n Positions,\r\n updatingChannel: null,\r\n dialog: false,\r\n timeLastBlock: null,\r\n alternativeServer: false,\r\n useCache: true,\r\n numberOfRows: 1,\r\n framesPerRow: 5,\r\n secondsPerFrame: 1,\r\n fInterface: null,\r\n velocity: 1,\r\n frames: [],\r\n previousFrames: [],\r\n nextFrames: [],\r\n channelCode: 0,\r\n videoPlaying: false,\r\n activeFrame: null,\r\n activeVideo: null,\r\n videoTime: 0,\r\n videoTotalTime: null,\r\n progressVideoDrag: false,\r\n hourIniSelected: false,\r\n hourEndSelected: false,\r\n canInsertTime: false,\r\n lastHeight: 0,\r\n loopInterval: null,\r\n nextLoop: false,\r\n prevLoop: false,\r\n videoSliderTotalDuration: 900,\r\n blockStartTime: null,\r\n media: null,\r\n changeServer: false,\r\n userMultiTabsGrid: false,\r\n userMultiTabsGridsModel: true,\r\n playbackRate: 1,\r\n paused: false,\r\n commandBarShow: true,\r\n dialogs: {\r\n playbackRate: false,\r\n goTo: false,\r\n secondsPerFrame: false,\r\n frames: false,\r\n },\r\n lastNext: 0,\r\n lastPrev: 0,\r\n }\r\n },\r\n async created() {\r\n this.changeServer = this.serverOfFrames === 'alternative'\r\n this.alternativeServer = this.serverOfFrames === 'alternative'\r\n\r\n const settings = [\r\n {\r\n framesPerRow: 1,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 2,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 3,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 3,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 4,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 4,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 5,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 5,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 6,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 6,\r\n numberOfRows: 2,\r\n },\r\n ]\r\n\r\n const storedOnDb = settings[parseInt(this.framesFormat) - 1]\r\n this.framesPerRow = storedOnDb.framesPerRow\r\n this.numberOfRows = storedOnDb.numberOfRows\r\n\r\n await this.createFramesInterface()\r\n // if (this.maxSize) {\r\n // this.resize(this.maxSize)\r\n // }\r\n },\r\n methods: {\r\n toogleCommandsVisibility() {\r\n this.commandBarShow = !this.commandBarShow\r\n setTimeout(this.resize, 0)\r\n },\r\n framesClicked(e) {\r\n if (e.target.parentNode.id != 'insert') {\r\n this.active = true\r\n }\r\n },\r\n async goToStartBlock() {\r\n try {\r\n const d = new Date()\r\n let timestamp = Date.UTC(\r\n d.getFullYear(),\r\n d.getMonth(),\r\n d.getDate(),\r\n d.getHours(),\r\n d.getMinutes(),\r\n d.getSeconds()\r\n )\r\n\r\n const response = (\r\n await FramesService.getNextAvailableBlock({\r\n channel: this.channel,\r\n time: timestamp / 1000,\r\n })\r\n ).data\r\n\r\n this.dialog = false\r\n this.changeHour(this.convertToAudienceTime(response.data.start, ':'))\r\n } catch (err) {\r\n console.error(err)\r\n }\r\n },\r\n async checkAvailableBlock() {\r\n try {\r\n const d = new Date()\r\n let timestamp = Date.UTC(\r\n d.getFullYear(),\r\n d.getMonth(),\r\n d.getDate(),\r\n d.getHours(),\r\n d.getMinutes(),\r\n d.getSeconds()\r\n )\r\n\r\n const response = (\r\n await FramesService.getNextAvailableBlock({\r\n channel: this.channel,\r\n time: timestamp / 1000,\r\n })\r\n ).data\r\n\r\n this.timeLastBlock = this.convertToAudienceTime(response.data.end, ':')\r\n this.dialog = true\r\n if (!response.status) {\r\n this.timeLastBlock = 'N/D'\r\n }\r\n } catch (err) {\r\n console.error(err)\r\n }\r\n },\r\n updateSlider(videoStartTime, time) {\r\n // * atualizar slider se estiver fora do range definido previamente\r\n if (\r\n time < this.blockStartTime ||\r\n time > this.blockStartTime ||\r\n videoStartTime > this.blockStartTime + this.videoSliderTotalDuration\r\n ) {\r\n this.blockStartTime = videoStartTime\r\n this.videoSliderTotalDuration = 900\r\n }\r\n },\r\n nextLoopActivate() {\r\n this.breakLoop()\r\n this.loopInterval = setInterval(\r\n () => this.next(true),\r\n this.swapImagesDelay\r\n )\r\n setTimeout(() => {\r\n this.nextLoop = true\r\n }, 0)\r\n },\r\n prevLoopActivate() {\r\n this.breakLoop()\r\n this.loopInterval = setInterval(\r\n () => this.prev({ ignoreTime: true }),\r\n this.swapImagesDelay\r\n )\r\n setTimeout(() => {\r\n this.prevLoop = true\r\n }, 0)\r\n },\r\n breakLoop() {\r\n clearInterval(this.loopInterval)\r\n this.loopInterval = null\r\n this.nextLoop = false\r\n this.prevLoop = false\r\n },\r\n changePlayPause(status) {\r\n this.paused = !status\r\n },\r\n resize(height = this.lastHeight) {\r\n this.lastHeight = height\r\n if (this.$refs.frames) {\r\n for (let frame of this.$refs.frames) {\r\n frame.resize(height)\r\n }\r\n }\r\n this.$emit('resized')\r\n },\r\n async goToFirstFrame() {\r\n let frames = this.$refs.frames\r\n\r\n let audienceTime = null\r\n if (frames.length > 0) {\r\n let frame = frames[0].frame\r\n audienceTime = this.getAudienceTime(frame.time, 0, 0, 0)\r\n }\r\n if (audienceTime) {\r\n const [hours, minutes, seconds] = audienceTime.split(':')\r\n const totalSeconds =\r\n parseInt(hours) * 3600 + parseInt(minutes) * 60 + parseInt(seconds)\r\n if (totalSeconds >= 9000)\r\n this.changeHour(this.getLastFirtsBlockTime(audienceTime, true))\r\n else this.changeHour(this.getLastFirtsBlockTime('02:30:00', true))\r\n }\r\n },\r\n async goToLastFrame() {\r\n let frames = this.$refs.frames\r\n let audienceTime = null\r\n if (frames.length > 0) {\r\n let frame = frames[0].frame\r\n\r\n audienceTime = this.getAudienceTime(frame.time, 0, 0, 0)\r\n }\r\n if (audienceTime) {\r\n this.changeHour(this.getLastFirtsBlockTime(audienceTime))\r\n }\r\n },\r\n getLastFirtsBlockTime(time, first = false) {\r\n if (time.indexOf(':') !== -1) {\r\n time = time.replace(/:/g, '')\r\n }\r\n let h, m, newTime\r\n const t = time.match(/.{1,2}/g)\r\n if (t[0] && t[1]) {\r\n h = parseInt(t[0])\r\n m = parseInt(t[1])\r\n }\r\n if (h < 26) {\r\n if (m < 15)\r\n if (first) newTime = t[0] + ':00:00'\r\n else newTime = t[0] + ':14:59'\r\n else if (m < 30)\r\n if (first) newTime = t[0] + ':15:00'\r\n else newTime = t[0] + ':29:59'\r\n else if (m < 45)\r\n if (first) newTime = t[0] + ':30:00'\r\n else newTime = t[0] + ':44:59'\r\n else if (first) newTime = t[0] + ':45:00'\r\n else newTime = t[0] + ':59:59'\r\n } else {\r\n if (m < 15)\r\n if (first) newTime = '26:00:00'\r\n else newTime = '26:14:59'\r\n else {\r\n if (first) newTime = '26:15:00'\r\n else newTime = '26:29:59'\r\n }\r\n }\r\n return newTime\r\n },\r\n openBlocks() {\r\n this.$refs.settings2?.openBlocks()\r\n },\r\n playOrPause() {\r\n const array = this.$refs.frames.filter((fc) => !!fc.active)\r\n if (array.length === 1) {\r\n const frame = array[0]\r\n frame.playOrPause(this.playbackRate)\r\n }\r\n },\r\n stopPlayingBar() {\r\n for (let ref of this.$refs.frames) {\r\n if (\r\n ref.videoStatus === ref.Status.playing ||\r\n ref.videoStatus === ref.Status.paused\r\n ) {\r\n ref.stop(false)\r\n }\r\n }\r\n },\r\n async setFrameSelection(selected) {\r\n this.frames = this.loadingArray\r\n const settings = [\r\n {\r\n framesPerRow: 1,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 2,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 3,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 3,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 4,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 4,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 5,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 5,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 6,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 6,\r\n numberOfRows: 2,\r\n },\r\n ]\r\n\r\n const formatSelected = settings[selected - 1]\r\n this.framesPerRow = formatSelected.framesPerRow\r\n this.numberOfRows = formatSelected.numberOfRows\r\n\r\n await this.fInterface.changeSize(this.numberOfRows, this.framesPerRow)\r\n this.getFramesArray()\r\n setTimeout(() => {\r\n for (let ref of this.$refs.frames) {\r\n ref?.resize(this.lastHeight)\r\n }\r\n }, 150)\r\n this.$emit('frames-format-changed', selected)\r\n },\r\n getFramesArray() {\r\n this.frames = this.fInterface.getFrames(Positions.current)\r\n this.nextFrames = this.fInterface.getFrames(Positions.next)\r\n this.previousFrames = this.fInterface.getFrames(Positions.previous)\r\n },\r\n async createFramesInterface() {\r\n this.frames = this.loadingArray\r\n // let ch = this.channel\r\n // let associationTMP = {\r\n // 1735073: 1,\r\n // 1735074: 139,\r\n // 1735075: 3,\r\n // 1735076: 132,\r\n // }\r\n // //\r\n // this.channelCode = associationTMP[ch] ? associationTMP[ch] : ch\r\n\r\n const t = this.startAudienceTime.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const time = Date.UTC(d.year, d.month, d.day, t[0], t[1], t[2]) / 1000\r\n // * iniciar slider\r\n this.blockStartTime = time\r\n this.fInterface = await new FramesInterface(\r\n this.channel,\r\n this.numberOfRows,\r\n this.framesPerRow,\r\n time,\r\n this.startAudienceTime,\r\n this.useCache\r\n )\r\n await this.fInterface.init()\r\n\r\n this.getFramesArray()\r\n\r\n this.activeFrame = this.getIndex(1, 0, Positions.current)\r\n\r\n this.activeVideo = null\r\n },\r\n getIndex(rowNumber, frameIndex, position) {\r\n let from = this.framesPerRow * this.numberOfRows * position\r\n let till = this.framesPerRow * this.numberOfRows * (position + 1)\r\n\r\n return (from + till * (rowNumber - 1)) / rowNumber + frameIndex\r\n },\r\n getAudienceTime(frameTime, rowNumber, frameNumber, position) {\r\n if (!frameTime) {\r\n return 'Loading...'\r\n } else if (\r\n this.getIndex(rowNumber, frameNumber, position) === this.activeVideo\r\n ) {\r\n return this.convertToAudienceTime(this.videoTime)\r\n } else {\r\n return this.convertToAudienceTime(frameTime)\r\n }\r\n },\r\n dateInUtc(miliSeconds) {\r\n var date = new Date(miliSeconds)\r\n var utc = new Date(\r\n date.getUTCFullYear(),\r\n date.getUTCMonth(),\r\n date.getUTCDate(),\r\n date.getUTCHours(),\r\n date.getUTCMinutes(),\r\n date.getUTCSeconds()\r\n )\r\n return utc\r\n },\r\n convertToAudienceTime(time, separator = ':') {\r\n const d = this.getDateParts()\r\n const limit = Date.UTC(d.year, d.month, d.day, 23, 59, 59) / 1000\r\n\r\n let hour = this.dateInUtc(time * 1000)\r\n .toTimeString()\r\n .split(' ')[0]\r\n .split(':')\r\n .map(Number)\r\n\r\n if (time > limit && time <= limit + this.startAudienceSeconds) {\r\n hour[0] = 24 + hour[0]\r\n }\r\n return hour\r\n .map((part) => (part > 9 ? part.toString() : '0' + part))\r\n .join(separator)\r\n },\r\n getDateParts(date = this.date) {\r\n const d = new Date(date)\r\n return {\r\n year: d.getFullYear(),\r\n month: d.getMonth(),\r\n day: d.getDate(),\r\n }\r\n },\r\n selectFrame(index, frame) {\r\n const d = this.getDateParts()\r\n const limit = Date.UTC(d.year, d.month, d.day, 23, 59, 59) / 1000\r\n const frameTime = frame?.time\r\n\r\n if (frameTime - (this.startAudienceSeconds + limit) <= 0) {\r\n if (this.hourIniSelected === true) {\r\n this.hourIniSelected = frameTime\r\n\r\n if (\r\n this.hourEndSelected &&\r\n this.hourIniSelected > this.hourEndSelected\r\n ) {\r\n this.hourEndSelected = false\r\n }\r\n } else if (this.hourEndSelected === true) {\r\n if (frameTime > this.hourIniSelected) {\r\n this.hourEndSelected = frameTime\r\n this.canInsertTime = true\r\n } else {\r\n this.hourEndSelected = false\r\n }\r\n }\r\n }\r\n\r\n if (this.activeFrame !== index) {\r\n // ? Se clicar no frame diferente de onde está a dar play, faz pausa\r\n const array = this.$refs.frames.filter(\r\n (fc) => fc.videoStatus === fc.Status.playing\r\n )\r\n if (array.length === 1) {\r\n const frame = array[0]\r\n frame.playOrPause()\r\n }\r\n this.activeVideo = null\r\n this.activeFrame = index\r\n }\r\n },\r\n setHourIni() {\r\n this.canInsertTime = true\r\n this.hourIniSelected = true\r\n document.getElementById(`frame-${this.activeFrame}`).click()\r\n this.$emit('setHourIni', {\r\n hour_ini: this.hourIniSelected\r\n ? this.convertToAudienceTime(this.hourIniSelected, '')\r\n : null,\r\n })\r\n },\r\n setHourEnd() {\r\n this.canInsertTime = true\r\n this.hourEndSelected = true\r\n document.getElementById(`frame-${this.activeFrame}`).click()\r\n },\r\n //* Navegação\r\n arrowRight() {\r\n if (this.checkLimitRight(false)) {\r\n if (\r\n this.activeFrame ===\r\n this.numberOfRows * this.framesPerRow * 2 - 1\r\n ) {\r\n this.next()\r\n } else {\r\n this.activeFrame++\r\n }\r\n }\r\n },\r\n arrowLeft() {\r\n if (this.checkLimitLeft(false)) {\r\n if (this.activeFrame === this.numberOfRows * this.framesPerRow) {\r\n this.prev({ stayOnLast: true })\r\n } else {\r\n this.activeFrame--\r\n }\r\n }\r\n },\r\n arrowUp() {\r\n if (\r\n this.activeFrame - this.numberOfRows * this.framesPerRow >\r\n Math.round((this.numberOfRows * this.framesPerRow) / 2)\r\n ) {\r\n this.activeFrame -= this.framesPerRow\r\n }\r\n },\r\n arrowDown() {\r\n if (\r\n this.activeFrame - this.numberOfRows * this.framesPerRow <\r\n Math.round((this.numberOfRows * this.framesPerRow) / 2)\r\n ) {\r\n this.activeFrame += this.framesPerRow\r\n }\r\n },\r\n checkLimitRight(value) {\r\n const hours = this.endAudienceTime.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const high = Date.UTC(d.year, d.month, d.day, 26, 59, 59)\r\n\r\n if (value) {\r\n return (\r\n high >\r\n (this.fInterface.getCurrentTime() +\r\n this.numberOfRows * this.framesPerRow -\r\n 1) *\r\n 1000 && this.nextFrames[0].title !== -1\r\n )\r\n } else {\r\n // return high > (this.fInterface.getCurrentTime() + this.activeFrame) * 1000\r\n return high > this.fInterface.getCurrentTime() * 1000\r\n }\r\n },\r\n checkLimitLeft(value) {\r\n const hours = this.startAudienceTime.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const low = Date.UTC(d.year, d.month, d.day, hours[0], hours[1], hours[2])\r\n\r\n if (value) {\r\n return low <= (this.fInterface.getCurrentTime() - 1) * 1000\r\n } else {\r\n return (\r\n low <\r\n (this.fInterface.getCurrentTime() +\r\n this.activeFrame -\r\n this.numberOfRows * this.framesPerRow) *\r\n 1000\r\n )\r\n }\r\n },\r\n async next(ignoreTime = false) {\r\n if (\r\n (ignoreTime || Date.now() - this.lastNext > this.swapImagesDelay) &&\r\n this.checkLimitRight(true)\r\n ) {\r\n const array = this.$refs.frames.filter(\r\n (fc) =>\r\n fc.videoStatus === fc.Status.playing ||\r\n fc.videoStatus === fc.Status.paused\r\n )\r\n\r\n if (array.length === 1) {\r\n const frame = array[0]\r\n frame.stop(false)\r\n }\r\n this.fInterface.setCurrentStep(this.secondsPerFrame)\r\n await this.fInterface.loadNextFrames()\r\n\r\n this.activeFrame = this.getIndex(1, 0, Positions.current)\r\n this.activeVideo = null\r\n\r\n this.getFramesArray()\r\n this.lastNext = Date.now()\r\n }\r\n },\r\n async prev(config = {}) {\r\n if (\r\n (config.ignoreTime ||\r\n Date.now() - this.lastPrev > this.swapImagesDelay) &&\r\n this.checkLimitLeft(true)\r\n ) {\r\n const array = this.$refs.frames.filter(\r\n (fc) =>\r\n fc.videoStatus === fc.Status.playing ||\r\n fc.videoStatus === fc.Status.paused\r\n )\r\n if (array.length === 1) {\r\n const frame = array[0]\r\n frame.stop(false)\r\n }\r\n\r\n this.fInterface.setCurrentStep(this.secondsPerFrame)\r\n await this.fInterface.loadPrevFrames()\r\n\r\n if (config.stayOnLast) {\r\n this.activeFrame = this.getIndex(\r\n this.numberOfRows,\r\n this.framesPerRow - 1,\r\n Positions.current\r\n )\r\n } else {\r\n this.activeFrame = this.getIndex(1, 0, Positions.current)\r\n }\r\n\r\n this.activeVideo = null\r\n\r\n this.getFramesArray()\r\n this.lastPrev = Date.now()\r\n }\r\n },\r\n async setStartTime(time) {\r\n if (time.indexOf(':') !== -1) {\r\n time = time.replace(/:/g, '')\r\n }\r\n const t = time.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const setTime = Date.UTC(d.year, d.month, d.day, t[0], t[1], t[2]) / 1000\r\n // this.frames = this.loadingArray\r\n\r\n await this.fInterface.changeTime(setTime)\r\n\r\n this.getFramesArray()\r\n\r\n this.activeFrame = this.getIndex(1, 0, Positions.current)\r\n\r\n this.activeVideo = null\r\n\r\n return true\r\n },\r\n hourToTimeStamp(time) {\r\n if (time.indexOf(':') !== -1) {\r\n time = time.replace(/:/g, '')\r\n }\r\n const t = time.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const setTime = Date.UTC(d.year, d.month, d.day, t[0], t[1], t[2]) / 1000\r\n\r\n return setTime\r\n },\r\n changeHour(value) {\r\n if (value) {\r\n return new Promise((resolve) => {\r\n setTimeout(async () => {\r\n const array = this.$refs.frames.filter(\r\n (fc) =>\r\n fc.videoStatus === fc.Status.playing ||\r\n fc.videoStatus === fc.Status.paused\r\n )\r\n\r\n if (array.length === 1) {\r\n const frame = array[0]\r\n frame.stop(false)\r\n }\r\n\r\n await this.setStartTime(value, true)\r\n resolve()\r\n }, 0)\r\n })\r\n }\r\n },\r\n changeBlockInterval(value) {\r\n this.changeHour(value.ini)\r\n let time_ini, time_end\r\n time_ini = this.hourToTimeStamp(value.ini)\r\n time_end = this.hourToTimeStamp(value.end)\r\n this.videoSliderTotalDuration = time_end - time_ini\r\n this.$refs.frames[0].changeSettings(time_ini)\r\n this.blockStartTime = time_ini\r\n },\r\n //eslint-disable-next-line\r\n async updateVideoTime(index, videoTime) {\r\n this.activeVideo = index\r\n this.videoTime = videoTime\r\n },\r\n //eslint-disable-next-line\r\n updateVideoStatus(currentTime) {\r\n if (!this.progressVideoDrag) {\r\n // ESTA FUNÇÃO PASSOU PARA DENTRO DOS COMMANDS\r\n // this.updateProgress(null, currentTime)\r\n }\r\n },\r\n async startPlaying(frame, totalTime) {\r\n const array = this.$refs.frames.filter(\r\n (fc) => fc.frame.time !== frame.time\r\n )\r\n\r\n for (let ref of array) {\r\n if (\r\n ref.videoStatus === ref.Status.playing ||\r\n ref.videoStatus === ref.Status.paused\r\n ) {\r\n ref.stop(false)\r\n }\r\n }\r\n\r\n this.videoTotalTime = totalTime\r\n this.videoPlaying = true\r\n },\r\n stopPlaying() {\r\n this.videoTotalTime = null\r\n this.videoPlaying = false\r\n this.paused = false\r\n },\r\n insertTime() {\r\n this.$emit('timeToInsert', {\r\n channel: this.channel,\r\n hour_ini: this.hourIniSelected\r\n ? this.convertToAudienceTime(this.hourIniSelected, '')\r\n : null,\r\n hour_end: this.hourEndSelected\r\n ? this.convertToAudienceTime(this.hourEndSelected, '')\r\n : null,\r\n force: false,\r\n })\r\n\r\n if (this.jumpOnInsert) {\r\n this.changeHour(\r\n this.convertToAudienceTime(\r\n this.hourEndSelected || this.hourIniSelected\r\n )\r\n ).then(() => {\r\n this.activeFrame = this.getIndex(1, 1, Positions.current)\r\n })\r\n }\r\n\r\n if (this.removeSelectionOnInsert) {\r\n this.hourIniSelected = null\r\n this.hourEndSelected = null\r\n }\r\n this.canInsertTime = false\r\n },\r\n insertTimeForce() {\r\n this.$emit('timeToInsert', {\r\n channel: this.channel,\r\n hour_ini: this.hourIniSelected\r\n ? this.convertToAudienceTime(this.hourIniSelected, '')\r\n : null,\r\n hour_end: this.hourEndSelected\r\n ? this.convertToAudienceTime(this.hourEndSelected, '')\r\n : null,\r\n force: true,\r\n })\r\n\r\n if (this.removeSelectionOnInsert) {\r\n this.hourIniSelected = null\r\n this.hourEndSelected = null\r\n }\r\n this.canInsertTime = false\r\n },\r\n async getChannelMedia() {\r\n // this.media = (await ChannelService.show(this.channel)).data.MEDIA\r\n },\r\n async changeServerClick() {\r\n this.changeServer = !this.changeServer\r\n sessionStorage.setItem(\r\n 'server',\r\n this.changeServer ? 'alternative' : 'default'\r\n )\r\n\r\n location.reload()\r\n },\r\n },\r\n computed: {\r\n swapImagesDelay() {\r\n return 0\r\n // return this.numberOfRows * this.framesPerRow * 15\r\n },\r\n active: {\r\n get() {\r\n return this.value\r\n },\r\n set(value) {\r\n this.$emit('input', value)\r\n },\r\n },\r\n settingsClosed() {\r\n return !Object.values(this.dialogs).find((v) => v)\r\n },\r\n startAudienceSeconds() {\r\n const t = this.startAudienceTime.match(/.{1,2}/g)\r\n return parseInt(t[0] * 3600 + t[1] * 60 + t[2])\r\n },\r\n loadingArray() {\r\n return Array.from(Array(this.numberOfRows * this.framesPerRow).keys())\r\n },\r\n serverOfFrames() {\r\n return sessionStorage.getItem('server')\r\n },\r\n },\r\n watch: {\r\n secondsPerFrame(value) {\r\n const activeF =\r\n this.frames[this.activeFrame - this.numberOfRows * this.framesPerRow]\r\n\r\n if (activeF) {\r\n this.changeHour(this.getAudienceTime(activeF.time, 0, 0, 0))\r\n this.fInterface.setCurrentStep(this.secondsPerFrame)\r\n this.fInterface.loadFrames()\r\n this.getFramesArray()\r\n }\r\n },\r\n framesFormat(value) {\r\n this.setFrameSelection(value)\r\n },\r\n active() {\r\n // ? sempre que trocamos de tabs dar reset as horas selected\r\n if (this.removeSelectionOnInsert) {\r\n this.hourIniSelected = false\r\n this.hourEndSelected = false\r\n }\r\n },\r\n useCache() {\r\n this.createFramesInterface()\r\n },\r\n hourIniSelected(value) {\r\n if (value) {\r\n sessionStorage.setItem(\r\n 'currentTimeFrames',\r\n this.convertToAudienceTime(this.hourIniSelected, '')\r\n )\r\n } else {\r\n sessionStorage.removeItem('currentTimeFrames')\r\n }\r\n },\r\n activeFrame(value) {\r\n if (value) {\r\n this.stopPlayingBar()\r\n }\r\n },\r\n channel() {\r\n this.updatingChannel = new Promise((resolve, reject) => {\r\n try {\r\n this.createFramesInterface()\r\n resolve(true)\r\n } catch (err) {\r\n reject(err)\r\n }\r\n })\r\n },\r\n },\r\n}\r\n</script>\r\n<style scoped>\r\n.visualization-row {\r\n display: flex;\r\n flex-wrap: wrap;\r\n flex: 1 1 auto;\r\n}\r\n\r\n.visualization-col {\r\n flex-basis: 0;\r\n flex-grow: 1;\r\n max-width: 100%;\r\n padding: 12px;\r\n}\r\n\r\n.visualization-divider {\r\n display: block;\r\n flex: 1 1 100%;\r\n height: 0px;\r\n max-height: 0px;\r\n opacity: 1;\r\n transition: inherit;\r\n border-style: solid;\r\n border-width: thin 0 0 0;\r\n border-color: rgba(0, 0, 0, 0.12);\r\n margin: 0;\r\n}\r\n\r\n.visualization-divider.vertical {\r\n align-self: stretch;\r\n border-width: 0 thin 0 0;\r\n display: inline-flex;\r\n height: inherit;\r\n margin-left: -1px;\r\n max-height: 100%;\r\n max-width: 0px;\r\n vertical-align: text-bottom;\r\n width: 0px;\r\n}\r\n\r\n.visualization-card {\r\n flex-basis: 0;\r\n flex-grow: 1;\r\n max-width: 100%;\r\n padding: 12px;\r\n width: 100%;\r\n transition-property: box-shadow, opacity, -webkit-box-shadow;\r\n overflow-wrap: break-word;\r\n /*box-shadow: 0 3px 1px -2px rgba(0, 0, 0, 0.2), 0 2px 2px 0 rgba(0, 0, 0, 0.14),\r\n 0 1px 5px 0 rgba(0, 0, 0, 0.12);*/\r\n}\r\n\r\n.visualization-justify-center,\r\n/deep/ .visualization-justify-center {\r\n justify-content: center;\r\n}\r\n\r\n.visualization-align-center {\r\n align-items: center;\r\n}\r\n\r\n#visualization-container {\r\n max-width: 100% !important;\r\n margin: 0 auto !important;\r\n height: 100%;\r\n border-bottom: none;\r\n}\r\n#visualization-container > .card {\r\n border-radius: 0 !important;\r\n font-size: 12px;\r\n width: 100%;\r\n box-shadow: none;\r\n height: 100%;\r\n}\r\n\r\n#command-bar,\r\n#info-bar {\r\n background-color: #f5f5f5;\r\n box-shadow: 0 3px 1px -2px rgba(0, 0, 0, 0.2), 0 2px 2px 0 rgba(0, 0, 0, 0.14),\r\n 0 1px 5px 0 rgba(0, 0, 0, 0.12);\r\n}\r\n#command-bar button {\r\n width: 42px;\r\n height: 36px;\r\n border: none;\r\n background: none;\r\n}\r\n\r\n#command-bar button:hover {\r\n cursor: pointer;\r\n background: rgba(0, 0, 0, 0.12);\r\n}\r\n\r\n#command-bar svg {\r\n font-size: 16px;\r\n}\r\n\r\n#command-bar {\r\n padding: 0 !important;\r\n}\r\n\r\n#info-bar {\r\n padding: 4px;\r\n font-size: 14px;\r\n position: relative;\r\n}\r\n\r\n.settings-container {\r\n position: absolute;\r\n right: 14px;\r\n top: 50%;\r\n transform: translateY(-50%);\r\n}\r\n\r\n.settings-container > * {\r\n margin: 0 2px;\r\n cursor: pointer;\r\n}\r\n\r\n#info-bar svg {\r\n font-size: 16px;\r\n}\r\n\r\n#info-bar .divider {\r\n margin: 0 8px;\r\n}\r\n\r\nsvg:focus {\r\n border: none;\r\n}\r\n\r\n.visualization-card {\r\n border-left: 8px solid #eee;\r\n}\r\n\r\n.active-tab {\r\n border-left: 8px solid var(--visualization-primary) !important;\r\n border-image-slice: 1;\r\n}\r\n\r\n[id^='frame-'] {\r\n padding: 1px;\r\n display: flex;\r\n flex-flow: column;\r\n}\r\n\r\n.tooltip {\r\n display: block !important;\r\n z-index: 10000;\r\n}\r\n\r\n.tooltip .tooltip-inner {\r\n background: var(--visualization-primary);\r\n color: white;\r\n border-radius: 16px;\r\n padding: 5px 10px 4px;\r\n}\r\n\r\n.tooltip .tooltip-arrow {\r\n width: 0;\r\n height: 0;\r\n border-style: solid;\r\n position: absolute;\r\n margin: 5px;\r\n border-color: var(--visualization-primary);\r\n z-index: 1;\r\n}\r\n\r\n.tooltip[x-placement^='top'] {\r\n margin-bottom: 5px;\r\n}\r\n\r\n.tooltip[x-placement^='top'] .tooltip-arrow {\r\n border-width: 5px 5px 0 5px;\r\n border-left-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n bottom: -5px;\r\n left: calc(50% - 5px);\r\n margin-top: 0;\r\n margin-bottom: 0;\r\n}\r\n\r\n.tooltip[x-placement^='bottom'] {\r\n margin-top: 5px;\r\n}\r\n\r\n.tooltip[x-placement^='bottom'] .tooltip-arrow {\r\n border-width: 0 5px 5px 5px;\r\n border-left-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-top-color: transparent !important;\r\n top: -5px;\r\n left: calc(50% - 5px);\r\n margin-top: 0;\r\n margin-bottom: 0;\r\n}\r\n\r\n.tooltip[x-placement^='right'] {\r\n margin-left: 5px;\r\n}\r\n\r\n.tooltip[x-placement^='right'] .tooltip-arrow {\r\n border-width: 5px 5px 5px 0;\r\n border-left-color: transparent !important;\r\n border-top-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n left: -5px;\r\n top: calc(50% - 5px);\r\n margin-left: 0;\r\n margin-right: 0;\r\n}\r\n\r\n.tooltip[x-placement^='left'] {\r\n margin-right: 5px;\r\n}\r\n\r\n.tooltip[x-placement^='left'] .tooltip-arrow {\r\n border-width: 5px 0 5px 5px;\r\n border-top-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n right: -5px;\r\n top: calc(50% - 5px);\r\n margin-left: 0;\r\n margin-right: 0;\r\n}\r\n\r\n.tooltip.popover .popover-inner {\r\n background: #f9f9f9;\r\n color: black;\r\n padding: 24px;\r\n border-radius: 5px;\r\n box-shadow: 0 5px 30px rgba(black, 0.1);\r\n}\r\n\r\n.tooltip.popover .popover-arrow {\r\n border-color: #f9f9f9;\r\n}\r\n\r\n.tooltip[aria-hidden='true'] {\r\n visibility: hidden;\r\n opacity: 0;\r\n transition: opacity 0.15s, visibility 0.15s;\r\n}\r\n\r\n.tooltip[aria-hidden='false'] {\r\n visibility: visible;\r\n opacity: 1;\r\n transition: opacity 0.15s;\r\n}\r\n</style>\r\n"]}, media: undefined });
4685
+ inject("data-v-08eea866_0", { source: "\n.visualization-row[data-v-08eea866] {\r\n display: flex;\r\n flex-wrap: wrap;\r\n flex: 1 1 auto;\n}\n.visualization-col[data-v-08eea866] {\r\n flex-basis: 0;\r\n flex-grow: 1;\r\n max-width: 100%;\r\n padding: 12px;\n}\n.visualization-divider[data-v-08eea866] {\r\n display: block;\r\n flex: 1 1 100%;\r\n height: 0px;\r\n max-height: 0px;\r\n opacity: 1;\r\n transition: inherit;\r\n border-style: solid;\r\n border-width: thin 0 0 0;\r\n border-color: rgba(0, 0, 0, 0.12);\r\n margin: 0;\n}\n.visualization-divider.vertical[data-v-08eea866] {\r\n align-self: stretch;\r\n border-width: 0 thin 0 0;\r\n display: inline-flex;\r\n height: inherit;\r\n margin-left: -1px;\r\n max-height: 100%;\r\n max-width: 0px;\r\n vertical-align: text-bottom;\r\n width: 0px;\n}\n.visualization-card[data-v-08eea866] {\r\n flex-basis: 0;\r\n flex-grow: 1;\r\n max-width: 100%;\r\n padding: 12px;\r\n width: 100%;\r\n transition-property: box-shadow, opacity, -webkit-box-shadow;\r\n overflow-wrap: break-word;\r\n /*box-shadow: 0 3px 1px -2px rgba(0, 0, 0, 0.2), 0 2px 2px 0 rgba(0, 0, 0, 0.14),\r\n 0 1px 5px 0 rgba(0, 0, 0, 0.12);*/\n}\n.visualization-justify-center[data-v-08eea866],[data-v-08eea866] .visualization-justify-center {\r\n justify-content: center;\n}\n.visualization-align-center[data-v-08eea866] {\r\n align-items: center;\n}\n#visualization-container[data-v-08eea866] {\r\n max-width: 100% !important;\r\n margin: 0 auto !important;\r\n height: 100%;\r\n border-bottom: none;\n}\n#visualization-container > .card[data-v-08eea866] {\r\n border-radius: 0 !important;\r\n font-size: 12px;\r\n width: 100%;\r\n box-shadow: none;\r\n height: 100%;\n}\n#command-bar[data-v-08eea866],\r\n#info-bar[data-v-08eea866] {\r\n background-color: #f5f5f5;\r\n box-shadow: 0 3px 1px -2px rgba(0, 0, 0, 0.2), 0 2px 2px 0 rgba(0, 0, 0, 0.14),\r\n 0 1px 5px 0 rgba(0, 0, 0, 0.12);\n}\n#command-bar button[data-v-08eea866] {\r\n width: 42px;\r\n height: 36px;\r\n border: none;\r\n background: none;\n}\n#command-bar button[data-v-08eea866]:hover {\r\n cursor: pointer;\r\n background: rgba(0, 0, 0, 0.12);\n}\n#command-bar svg[data-v-08eea866] {\r\n font-size: 16px;\n}\n#command-bar[data-v-08eea866] {\r\n padding: 0 !important;\n}\n#info-bar[data-v-08eea866] {\r\n padding: 4px;\r\n font-size: 14px;\r\n position: relative;\n}\n.settings-container[data-v-08eea866] {\r\n position: absolute;\r\n right: 14px;\r\n top: 50%;\r\n transform: translateY(-50%);\n}\n.settings-container > *[data-v-08eea866] {\r\n margin: 0 2px;\r\n cursor: pointer;\n}\n#info-bar svg[data-v-08eea866] {\r\n font-size: 16px;\n}\n#info-bar .divider[data-v-08eea866] {\r\n margin: 0 8px;\n}\nsvg[data-v-08eea866]:focus {\r\n border: none;\n}\n.visualization-card[data-v-08eea866] {\r\n border-left: 8px solid #eee;\n}\n.active-tab[data-v-08eea866] {\r\n border-left: 8px solid var(--visualization-primary) !important;\r\n border-image-slice: 1;\n}\n[id^='frame-'][data-v-08eea866] {\r\n padding: 1px;\r\n display: flex;\r\n flex-flow: column;\n}\n.tooltip[data-v-08eea866] {\r\n display: block !important;\r\n z-index: 10000;\n}\n.tooltip .tooltip-inner[data-v-08eea866] {\r\n background: var(--visualization-primary);\r\n color: white;\r\n border-radius: 16px;\r\n padding: 5px 10px 4px;\n}\n.tooltip .tooltip-arrow[data-v-08eea866] {\r\n width: 0;\r\n height: 0;\r\n border-style: solid;\r\n position: absolute;\r\n margin: 5px;\r\n border-color: var(--visualization-primary);\r\n z-index: 1;\n}\n.tooltip[x-placement^='top'][data-v-08eea866] {\r\n margin-bottom: 5px;\n}\n.tooltip[x-placement^='top'] .tooltip-arrow[data-v-08eea866] {\r\n border-width: 5px 5px 0 5px;\r\n border-left-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n bottom: -5px;\r\n left: calc(50% - 5px);\r\n margin-top: 0;\r\n margin-bottom: 0;\n}\n.tooltip[x-placement^='bottom'][data-v-08eea866] {\r\n margin-top: 5px;\n}\n.tooltip[x-placement^='bottom'] .tooltip-arrow[data-v-08eea866] {\r\n border-width: 0 5px 5px 5px;\r\n border-left-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-top-color: transparent !important;\r\n top: -5px;\r\n left: calc(50% - 5px);\r\n margin-top: 0;\r\n margin-bottom: 0;\n}\n.tooltip[x-placement^='right'][data-v-08eea866] {\r\n margin-left: 5px;\n}\n.tooltip[x-placement^='right'] .tooltip-arrow[data-v-08eea866] {\r\n border-width: 5px 5px 5px 0;\r\n border-left-color: transparent !important;\r\n border-top-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n left: -5px;\r\n top: calc(50% - 5px);\r\n margin-left: 0;\r\n margin-right: 0;\n}\n.tooltip[x-placement^='left'][data-v-08eea866] {\r\n margin-right: 5px;\n}\n.tooltip[x-placement^='left'] .tooltip-arrow[data-v-08eea866] {\r\n border-width: 5px 0 5px 5px;\r\n border-top-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n right: -5px;\r\n top: calc(50% - 5px);\r\n margin-left: 0;\r\n margin-right: 0;\n}\n.tooltip.popover .popover-inner[data-v-08eea866] {\r\n background: #f9f9f9;\r\n color: black;\r\n padding: 24px;\r\n border-radius: 5px;\r\n box-shadow: 0 5px 30px rgba(black, 0.1);\n}\n.tooltip.popover .popover-arrow[data-v-08eea866] {\r\n border-color: #f9f9f9;\n}\n.tooltip[aria-hidden='true'][data-v-08eea866] {\r\n visibility: hidden;\r\n opacity: 0;\r\n transition: opacity 0.15s, visibility 0.15s;\n}\n.tooltip[aria-hidden='false'][data-v-08eea866] {\r\n visibility: visible;\r\n opacity: 1;\r\n transition: opacity 0.15s;\n}\r\n", map: {"version":3,"sources":["C:\\workspace\\visualization\\src\\Visualization.vue"],"names":[],"mappings":";AA8qCA;EACA,aAAA;EACA,eAAA;EACA,cAAA;AACA;AAEA;EACA,aAAA;EACA,YAAA;EACA,eAAA;EACA,aAAA;AACA;AAEA;EACA,cAAA;EACA,cAAA;EACA,WAAA;EACA,eAAA;EACA,UAAA;EACA,mBAAA;EACA,mBAAA;EACA,wBAAA;EACA,iCAAA;EACA,SAAA;AACA;AAEA;EACA,mBAAA;EACA,wBAAA;EACA,oBAAA;EACA,eAAA;EACA,iBAAA;EACA,gBAAA;EACA,cAAA;EACA,2BAAA;EACA,UAAA;AACA;AAEA;EACA,aAAA;EACA,YAAA;EACA,eAAA;EACA,aAAA;EACA,WAAA;EACA,4DAAA;EACA,yBAAA;EACA;qCACA;AACA;AAEA;EAEA,uBAAA;AACA;AAEA;EACA,mBAAA;AACA;AAEA;EACA,0BAAA;EACA,yBAAA;EACA,YAAA;EACA,mBAAA;AACA;AACA;EACA,2BAAA;EACA,eAAA;EACA,WAAA;EACA,gBAAA;EACA,YAAA;AACA;AAEA;;EAEA,yBAAA;EACA;mCACA;AACA;AACA;EACA,WAAA;EACA,YAAA;EACA,YAAA;EACA,gBAAA;AACA;AAEA;EACA,eAAA;EACA,+BAAA;AACA;AAEA;EACA,eAAA;AACA;AAEA;EACA,qBAAA;AACA;AAEA;EACA,YAAA;EACA,eAAA;EACA,kBAAA;AACA;AAEA;EACA,kBAAA;EACA,WAAA;EACA,QAAA;EACA,2BAAA;AACA;AAEA;EACA,aAAA;EACA,eAAA;AACA;AAEA;EACA,eAAA;AACA;AAEA;EACA,aAAA;AACA;AAEA;EACA,YAAA;AACA;AAEA;EACA,2BAAA;AACA;AAEA;EACA,8DAAA;EACA,qBAAA;AACA;AAEA;EACA,YAAA;EACA,aAAA;EACA,iBAAA;AACA;AAEA;EACA,yBAAA;EACA,cAAA;AACA;AAEA;EACA,wCAAA;EACA,YAAA;EACA,mBAAA;EACA,qBAAA;AACA;AAEA;EACA,QAAA;EACA,SAAA;EACA,mBAAA;EACA,kBAAA;EACA,WAAA;EACA,0CAAA;EACA,UAAA;AACA;AAEA;EACA,kBAAA;AACA;AAEA;EACA,2BAAA;EACA,yCAAA;EACA,0CAAA;EACA,2CAAA;EACA,YAAA;EACA,qBAAA;EACA,aAAA;EACA,gBAAA;AACA;AAEA;EACA,eAAA;AACA;AAEA;EACA,2BAAA;EACA,yCAAA;EACA,0CAAA;EACA,wCAAA;EACA,SAAA;EACA,qBAAA;EACA,aAAA;EACA,gBAAA;AACA;AAEA;EACA,gBAAA;AACA;AAEA;EACA,2BAAA;EACA,yCAAA;EACA,wCAAA;EACA,2CAAA;EACA,UAAA;EACA,oBAAA;EACA,cAAA;EACA,eAAA;AACA;AAEA;EACA,iBAAA;AACA;AAEA;EACA,2BAAA;EACA,wCAAA;EACA,0CAAA;EACA,2CAAA;EACA,WAAA;EACA,oBAAA;EACA,cAAA;EACA,eAAA;AACA;AAEA;EACA,mBAAA;EACA,YAAA;EACA,aAAA;EACA,kBAAA;EACA,uCAAA;AACA;AAEA;EACA,qBAAA;AACA;AAEA;EACA,kBAAA;EACA,UAAA;EACA,2CAAA;AACA;AAEA;EACA,mBAAA;EACA,UAAA;EACA,yBAAA;AACA","file":"Visualization.vue","sourcesContent":["<template>\r\n <div\r\n class=\"visualization-row\"\r\n id=\"visualization-container\"\r\n @click=\"framesClicked\"\r\n >\r\n <GlobalEvents\r\n v-if=\"!readOnly && canInsertTime && settingsClosed\"\r\n @keydown.45=\"insertTime\"\r\n />\r\n <GlobalEvents\r\n v-if=\"!readOnly && active && settingsClosed\"\r\n @keydown.83.prevent=\"setHourIni\"\r\n @keydown.69.prevent=\"setHourEnd\"\r\n />\r\n <GlobalEvents\r\n v-if=\"active && settingsClosed\"\r\n @keydown.left.prevent=\"arrowLeft\"\r\n @keydown.right.prevent=\"arrowRight\"\r\n @keydown.up.prevent=\"arrowUp\"\r\n @keydown.down.prevent=\"arrowDown\"\r\n @keydown.shift.page-down.prevent=\"nextLoopActivate\"\r\n @keydown.page-down.prevent=\"() => next()\"\r\n @keydown.page-up.prevent=\"() => prev()\"\r\n @keydown.shift.page-up.prevent=\"prevLoopActivate\"\r\n @keydown.36.prevent=\"goToFirstFrame\"\r\n @keydown.35.prevent=\"goToLastFrame\"\r\n @keydown.71.prevent=\"dialogs.goTo = true\"\r\n @keydown.73.prevent=\"dialogs.secondsPerFrame = true\"\r\n @keydown.76.prevent=\"dialogs.frames = true\"\r\n @keydown.49.97=\"() => (secondsPerFrame = 1)\"\r\n @keydown.50.98=\"() => (secondsPerFrame = 2)\"\r\n @keydown.51.99=\"() => (secondsPerFrame = 3)\"\r\n @keydown.52.100=\"() => (secondsPerFrame = 4)\"\r\n @keydown.53.101=\"() => (secondsPerFrame = 5)\"\r\n />\r\n <GlobalEvents\r\n v-if=\"prevLoop || nextLoop\"\r\n @keydown=\"breakLoop\"\r\n v-on:click=\"breakLoop\"\r\n />\r\n <settings\r\n v-if=\"active\"\r\n :dialogs-visibility=\"dialogs\"\r\n :playback-rate=\"playbackRate\"\r\n :seconds-per-frame=\"secondsPerFrame\"\r\n :frames-per-row=\"framesPerRow\"\r\n :number-of-rows=\"numberOfRows\"\r\n @change-playback-rate=\"(value) => (playbackRate = value)\"\r\n @change-go-to=\"changeHour\"\r\n @change-seconds-per-frame=\"(value) => (secondsPerFrame = value)\"\r\n @set-frames-selection=\"setFrameSelection\"\r\n @close=\"(dialog) => (dialogs[dialog] = false)\"\r\n />\r\n <div\r\n :class=\"{ 'visualization-card': true, 'active-tab': active }\"\r\n style=\"width: 100%; padding: 0\"\r\n >\r\n <command-bar\r\n v-show=\"commandBarShow\"\r\n :read-only=\"readOnly\"\r\n :video-playing=\"videoPlaying\"\r\n :video-paused=\"paused\"\r\n :insert-time=\"canInsertTime\"\r\n :hour-ini-selected=\"!!hourIniSelected\"\r\n :hour-end-selected=\"!!hourEndSelected\"\r\n @prev-loop-activate=\"prevLoopActivate\"\r\n @next-loop-activate=\"nextLoopActivate\"\r\n @prev=\"prev\"\r\n @next=\"next\"\r\n @go-to=\"dialogs.goTo = true\"\r\n @open-frame-selection=\"dialogs.frames = true\"\r\n @open-frames-per-second=\"dialogs.secondsPerFrame = true\"\r\n @open-blocks=\"openBlocks\"\r\n @open-playback-rate=\"dialogs.playbackRate = true\"\r\n @play-or-pause=\"playOrPause\"\r\n @stop-playing=\"stopPlayingBar\"\r\n @set-hour-ini=\"setHourIni\"\r\n @set-hour-end=\"setHourEnd\"\r\n @insert-time=\"insertTime\"\r\n />\r\n <video-progress\r\n v-if=\"videoProgressBar\"\r\n v-show=\"videoPlaying\"\r\n :video-time=\"videoTime\"\r\n />\r\n <info-bar\r\n :playback-rate=\"playbackRate\"\r\n :seconds-per-frame=\"secondsPerFrame\"\r\n :commands-show=\"commandBarShow\"\r\n :cache=\"useCache\"\r\n :block-start-time=\"blockStartTime\"\r\n :video-total-duration=\"videoSliderTotalDuration\"\r\n :alternative-server=\"alternativeServer\"\r\n :frames-per-row=\"framesPerRow\"\r\n :number-of-rows=\"numberOfRows\"\r\n :hour-ini=\"hourIniSelected\"\r\n :hour-end=\"hourEndSelected\"\r\n @toogle-commands-visibility=\"toogleCommandsVisibility\"\r\n @toogle-cache=\"useCache = !useCache\"\r\n @change-server=\"changeServerClick\"\r\n />\r\n <div\r\n class=\"visualization-row\"\r\n v-for=\"rowNumber in numberOfRows\"\r\n :id=\"'row-' + rowNumber\"\r\n :key=\"'row-' + rowNumber\"\r\n style=\"padding: 2px 12px\"\r\n >\r\n <div\r\n v-for=\"(frame, frameNumber) in previousFrames\"\r\n :key=\"\r\n numberOfRows +\r\n '-' +\r\n framesPerRow +\r\n '-' +\r\n getIndex(rowNumber, frameNumber, Positions.previous)\r\n \"\r\n style=\"display: none\"\r\n >\r\n <span v-html=\"frame.img\" />\r\n </div>\r\n <div\r\n v-for=\"(frame, frameNumber) in nextFrames\"\r\n :key=\"\r\n numberOfRows +\r\n '-' +\r\n framesPerRow +\r\n '-' +\r\n getIndex(rowNumber, frameNumber, Positions.next)\r\n \"\r\n style=\"display: none\"\r\n >\r\n <span v-html=\"frame.img\" />\r\n </div>\r\n <div\r\n class=\"visualization-col\"\r\n v-for=\"(frame, frameNumber) in frames.slice(\r\n framesPerRow * (rowNumber - 1),\r\n framesPerRow * rowNumber\r\n )\"\r\n :key=\"'row-' + rowNumber + '-frame-' + frameNumber\"\r\n :id=\"`frame-${getIndex(rowNumber, frameNumber, Positions.current)}`\"\r\n :class=\"{ loaderImg: !!frame.img }\"\r\n @click=\"\r\n frame.time\r\n ? selectFrame(\r\n getIndex(rowNumber, frameNumber, Positions.current),\r\n frame\r\n )\r\n : null\r\n \"\r\n >\r\n <span :id=\"activeFrame ? 'aa' : 0\" style=\"text-align: center\">\r\n <b>\r\n {{\r\n getAudienceTime(\r\n frame.time,\r\n rowNumber,\r\n frameNumber,\r\n Positions.current\r\n )\r\n }}\r\n </b>\r\n </span>\r\n\r\n <frame\r\n ref=\"frames\"\r\n :frame=\"frame\"\r\n :index=\"getIndex(rowNumber, frameNumber, Positions.current)\"\r\n :grid-settings=\"{ numberOfRows, framesPerRow }\"\r\n :initialTime=\"frame.time === hourIniSelected\"\r\n :endTime=\"frame.time === hourEndSelected\"\r\n :betweenTime=\"\r\n frame.time > hourIniSelected && frame.time < hourEndSelected\r\n \"\r\n :active=\"\r\n getIndex(rowNumber, frameNumber, Positions.current) ===\r\n activeFrame\r\n \"\r\n :activeTab=\"active\"\r\n :videoUrl=\"fInterface ? fInterface.getVideoUrl(frame) : ''\"\r\n :videoControls=\"videoControls\"\r\n @startPlaying=\"startPlaying\"\r\n @stopPlaying=\"stopPlaying\"\r\n @playPauseStatus=\"changePlayPause\"\r\n @updateSlider=\"updateSlider\"\r\n :playback-rate=\"playbackRate\"\r\n style=\"margin: 0 auto\"\r\n ></frame>\r\n </div>\r\n </div>\r\n </div>\r\n <!-- <settings\r\n ref=\"settings2\"\r\n :active=\"active\"\r\n @goToTime=\"changeHour\"\r\n @goToBlockInterval=\"changeBlockInterval\"\r\n @setSplitTime=\"setSplitTime\"\r\n @setFrameSelection=\"setFrameSelection\"\r\n @setPlaybackRate=\"\r\n (rate) => {\r\n playbackRate = rate\r\n }\r\n \"\r\n >\r\n </settings> -->\r\n <!-- <v-dialog v-model=\"dialog\" width=\"500\">\r\n <div class=\"card\">\r\n <div class=\"card\"-title class=\"text-h5 grey lighten-2\">\r\n {{ ' Último bloco disponível até: ' }}\r\n <v-btn\r\n @click=\"goToStartBlock\"\r\n class=\"ml-2\"\r\n dark\r\n color=\"success\"\r\n depressed\r\n >\r\n <v-icon left> fa-clock </v-icon>\r\n {{ timeLastBlock }}\r\n </v-btn>\r\n <v-spacer></v-spacer>\r\n <v-btn color=\"error\" fab small class=\"ml-5\" @click=\"dialog = false\">\r\n <v-icon dark> fa fa-xmark </v-icon>\r\n </v-btn>\r\n </div-title>\r\n </div>\r\n </v-dialog>\r\n <Help :media=\"media\" @close=\"media = null\" />\r\n <v-dialog\r\n v-if=\"userMultiTabsGrid\"\r\n v-model=\"userMultiTabsGridsModel\"\r\n persistent\r\n width=\"60%\"\r\n >\r\n <div class=\"card\">\r\n <div class=\"card\"-title class=\"warning text-h5\" primary-title>\r\n <div class=\"row\" class=\"ma-0\" justify=\"center\" align=\"center\">\r\n <v-icon dark left style=\"font-size: 24px !important\">\r\n fa fa-exclamation-triangle\r\n </v-icon>\r\n <div style=\"color: white\">{{ $t('form.alert') }}</div>\r\n </div>\r\n </div-title>\r\n <div class=\"card\"-text class=\"justify-center pa-6 grey lighten-2\">\r\n <h3>\r\n {{ $t('alerts.userMultiTabsGrid') }}\r\n </h3>\r\n </div-text>\r\n <hr class=\"divider\" class=\"grey lighten-1\"></span>\r\n <div class=\"card\"-actions class=\"grey lighten-2 justify-center\">\r\n <v-btn color=\"error\" ml-5 @click=\"userMultiTabsGrid = false\">\r\n <v-icon left color=\"white\">fa fa-times</v-icon>\r\n {{ $t('form.close') }}\r\n </v-btn>\r\n </div-actions>\r\n </div>\r\n </v-dialog> -->\r\n </div>\r\n</template>\r\n<script>\r\nimport Frame from './components/Frame.vue'\r\nimport FramesInterface from './utils/FramesInterface.js'\r\nimport FramesService from './services/FramesService.js'\r\n\r\nimport Commands from './components/Commands.vue'\r\nimport Infos from './components/Infos.vue'\r\nimport VideoProgress from './components/VideoProgress.vue'\r\nimport Settings from './components/Settings.vue'\r\n\r\nconst Positions = Object.freeze({\r\n previous: 0,\r\n current: 1,\r\n next: 2,\r\n})\r\n\r\nexport default {\r\n name: 'visualization-container',\r\n props: {\r\n value: {\r\n type: Boolean,\r\n required: true,\r\n },\r\n date: {\r\n type: String,\r\n required: true,\r\n },\r\n channel: {\r\n type: Number,\r\n required: true,\r\n },\r\n startAudienceTime: {\r\n type: String,\r\n required: true,\r\n },\r\n endAudienceTime: {\r\n type: String,\r\n required: true,\r\n },\r\n videoProgressBar: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n jumpOnInsert: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n removeSelectionOnInsert: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n framesFormat: {\r\n type: [Number, String],\r\n default: 7,\r\n },\r\n maxSize: {\r\n type: Number,\r\n },\r\n videoControls: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n readOnly: {\r\n type: Boolean,\r\n default: false,\r\n },\r\n },\r\n components: {\r\n Frame,\r\n CommandBar: Commands,\r\n InfoBar: Infos,\r\n VideoProgress,\r\n Settings,\r\n // Help,\r\n },\r\n data() {\r\n return {\r\n Positions,\r\n updatingChannel: null,\r\n dialog: false,\r\n timeLastBlock: null,\r\n alternativeServer: false,\r\n useCache: true,\r\n numberOfRows: 1,\r\n framesPerRow: 5,\r\n secondsPerFrame: 1,\r\n fInterface: null,\r\n velocity: 1,\r\n frames: [],\r\n previousFrames: [],\r\n nextFrames: [],\r\n channelCode: 0,\r\n videoPlaying: false,\r\n activeFrame: null,\r\n activeVideo: null,\r\n videoTime: 0,\r\n videoTotalTime: null,\r\n progressVideoDrag: false,\r\n hourIniSelected: false,\r\n hourEndSelected: false,\r\n canInsertTime: false,\r\n lastHeight: 0,\r\n loopInterval: null,\r\n nextLoop: false,\r\n prevLoop: false,\r\n videoSliderTotalDuration: 900,\r\n blockStartTime: null,\r\n media: null,\r\n changeServer: false,\r\n userMultiTabsGrid: false,\r\n userMultiTabsGridsModel: true,\r\n playbackRate: 1,\r\n paused: false,\r\n commandBarShow: true,\r\n dialogs: {\r\n playbackRate: false,\r\n goTo: false,\r\n secondsPerFrame: false,\r\n frames: false,\r\n },\r\n lastNext: 0,\r\n lastPrev: 0,\r\n }\r\n },\r\n async created() {\r\n this.changeServer = this.serverOfFrames === 'alternative'\r\n this.alternativeServer = this.serverOfFrames === 'alternative'\r\n\r\n const settings = [\r\n {\r\n framesPerRow: 1,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 2,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 3,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 3,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 4,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 4,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 5,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 5,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 6,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 6,\r\n numberOfRows: 2,\r\n },\r\n ]\r\n\r\n const storedOnDb = settings[parseInt(this.framesFormat) - 1]\r\n this.framesPerRow = storedOnDb.framesPerRow\r\n this.numberOfRows = storedOnDb.numberOfRows\r\n\r\n await this.createFramesInterface()\r\n // if (this.maxSize) {\r\n // this.resize(this.maxSize)\r\n // }\r\n },\r\n methods: {\r\n stopVideoPlaying(array) {\r\n for (const frame of array || this.$refs.frames) {\r\n if (\r\n frame.videoStatus === frame.Status.playing ||\r\n frame.videoStatus === frame.Status.paused\r\n ) {\r\n frame.stop(false)\r\n }\r\n }\r\n this.activeVideo = null\r\n },\r\n toogleCommandsVisibility() {\r\n this.commandBarShow = !this.commandBarShow\r\n setTimeout(this.resize, 0)\r\n },\r\n framesClicked(e) {\r\n if (e.target.parentNode.id != 'insert') {\r\n this.active = true\r\n }\r\n },\r\n async goToStartBlock() {\r\n try {\r\n const d = new Date()\r\n let timestamp = Date.UTC(\r\n d.getFullYear(),\r\n d.getMonth(),\r\n d.getDate(),\r\n d.getHours(),\r\n d.getMinutes(),\r\n d.getSeconds()\r\n )\r\n\r\n const response = (\r\n await FramesService.getNextAvailableBlock({\r\n channel: this.channel,\r\n time: timestamp / 1000,\r\n })\r\n ).data\r\n\r\n this.dialog = false\r\n this.changeHour(this.convertToAudienceTime(response.data.start, ':'))\r\n } catch (err) {\r\n console.error(err)\r\n }\r\n },\r\n async checkAvailableBlock() {\r\n try {\r\n const d = new Date()\r\n let timestamp = Date.UTC(\r\n d.getFullYear(),\r\n d.getMonth(),\r\n d.getDate(),\r\n d.getHours(),\r\n d.getMinutes(),\r\n d.getSeconds()\r\n )\r\n\r\n const response = (\r\n await FramesService.getNextAvailableBlock({\r\n channel: this.channel,\r\n time: timestamp / 1000,\r\n })\r\n ).data\r\n\r\n this.timeLastBlock = this.convertToAudienceTime(response.data.end, ':')\r\n this.dialog = true\r\n if (!response.status) {\r\n this.timeLastBlock = 'N/D'\r\n }\r\n } catch (err) {\r\n console.error(err)\r\n }\r\n },\r\n updateSlider(videoStartTime, time) {\r\n // * atualizar slider se estiver fora do range definido previamente\r\n if (\r\n time < this.blockStartTime ||\r\n time > this.blockStartTime ||\r\n videoStartTime > this.blockStartTime + this.videoSliderTotalDuration\r\n ) {\r\n this.blockStartTime = videoStartTime\r\n this.videoSliderTotalDuration = 900\r\n }\r\n },\r\n nextLoopActivate() {\r\n this.breakLoop()\r\n this.loopInterval = setInterval(\r\n () => this.next({ ignoreTime: true }),\r\n this.swapImagesDelay\r\n )\r\n setTimeout(() => {\r\n this.nextLoop = true\r\n }, 0)\r\n },\r\n prevLoopActivate() {\r\n this.breakLoop()\r\n this.loopInterval = setInterval(\r\n () => this.prev({ ignoreTime: true }),\r\n this.swapImagesDelay\r\n )\r\n setTimeout(() => {\r\n this.prevLoop = true\r\n }, 0)\r\n },\r\n breakLoop() {\r\n clearInterval(this.loopInterval)\r\n this.loopInterval = null\r\n this.nextLoop = false\r\n this.prevLoop = false\r\n },\r\n changePlayPause(status) {\r\n this.paused = !status\r\n },\r\n resize(height = this.lastHeight) {\r\n this.lastHeight = height\r\n if (this.$refs.frames) {\r\n for (let frame of this.$refs.frames) {\r\n frame.resize(height)\r\n }\r\n }\r\n this.$emit('resized')\r\n },\r\n async goToFirstFrame() {\r\n let frames = this.$refs.frames\r\n\r\n let audienceTime = null\r\n if (frames.length > 0) {\r\n let frame = frames[0].frame\r\n audienceTime = this.getAudienceTime(frame.time, 0, 0, 0)\r\n }\r\n if (audienceTime) {\r\n const [hours, minutes, seconds] = audienceTime.split(':')\r\n const totalSeconds =\r\n parseInt(hours) * 3600 + parseInt(minutes) * 60 + parseInt(seconds)\r\n if (totalSeconds >= 9000)\r\n this.changeHour(this.getLastFirtsBlockTime(audienceTime, true))\r\n else this.changeHour(this.getLastFirtsBlockTime('02:30:00', true))\r\n }\r\n },\r\n async goToLastFrame() {\r\n let frames = this.$refs.frames\r\n let audienceTime = null\r\n if (frames.length > 0) {\r\n let frame = frames[0].frame\r\n\r\n audienceTime = this.getAudienceTime(frame.time, 0, 0, 0)\r\n }\r\n if (audienceTime) {\r\n this.changeHour(this.getLastFirtsBlockTime(audienceTime))\r\n }\r\n },\r\n getLastFirtsBlockTime(time, first = false) {\r\n if (time.indexOf(':') !== -1) {\r\n time = time.replace(/:/g, '')\r\n }\r\n let h, m, newTime\r\n const t = time.match(/.{1,2}/g)\r\n if (t[0] && t[1]) {\r\n h = parseInt(t[0])\r\n m = parseInt(t[1])\r\n }\r\n if (h < 26) {\r\n if (m < 15)\r\n if (first) newTime = t[0] + ':00:00'\r\n else newTime = t[0] + ':14:59'\r\n else if (m < 30)\r\n if (first) newTime = t[0] + ':15:00'\r\n else newTime = t[0] + ':29:59'\r\n else if (m < 45)\r\n if (first) newTime = t[0] + ':30:00'\r\n else newTime = t[0] + ':44:59'\r\n else if (first) newTime = t[0] + ':45:00'\r\n else newTime = t[0] + ':59:59'\r\n } else {\r\n if (m < 15)\r\n if (first) newTime = '26:00:00'\r\n else newTime = '26:14:59'\r\n else {\r\n if (first) newTime = '26:15:00'\r\n else newTime = '26:29:59'\r\n }\r\n }\r\n return newTime\r\n },\r\n openBlocks() {\r\n this.$refs.settings2?.openBlocks()\r\n },\r\n playOrPause() {\r\n const array = this.$refs.frames.filter((fc) => !!fc.active)\r\n if (array.length === 1) {\r\n const frame = array[0]\r\n frame.playOrPause(this.playbackRate)\r\n }\r\n },\r\n stopPlayingBar() {\r\n for (let ref of this.$refs.frames) {\r\n if (\r\n ref.videoStatus === ref.Status.playing ||\r\n ref.videoStatus === ref.Status.paused\r\n ) {\r\n ref.stop(false)\r\n }\r\n }\r\n },\r\n async setFrameSelection(selected) {\r\n this.frames = this.loadingArray\r\n const settings = [\r\n {\r\n framesPerRow: 1,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 2,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 3,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 3,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 4,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 4,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 5,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 5,\r\n numberOfRows: 2,\r\n },\r\n {\r\n framesPerRow: 6,\r\n numberOfRows: 1,\r\n },\r\n {\r\n framesPerRow: 6,\r\n numberOfRows: 2,\r\n },\r\n ]\r\n\r\n const formatSelected = settings[selected - 1]\r\n this.framesPerRow = formatSelected.framesPerRow\r\n this.numberOfRows = formatSelected.numberOfRows\r\n\r\n await this.fInterface.changeSize(this.numberOfRows, this.framesPerRow)\r\n this.getFramesArray()\r\n setTimeout(() => {\r\n for (let ref of this.$refs.frames) {\r\n ref?.resize(this.lastHeight)\r\n }\r\n }, 150)\r\n this.$emit('frames-format-changed', selected)\r\n },\r\n getFramesArray() {\r\n this.frames = this.fInterface.getFrames(Positions.current)\r\n this.nextFrames = this.fInterface.getFrames(Positions.next)\r\n this.previousFrames = this.fInterface.getFrames(Positions.previous)\r\n },\r\n async createFramesInterface() {\r\n this.frames = this.loadingArray\r\n // let ch = this.channel\r\n // let associationTMP = {\r\n // 1735073: 1,\r\n // 1735074: 139,\r\n // 1735075: 3,\r\n // 1735076: 132,\r\n // }\r\n // //\r\n // this.channelCode = associationTMP[ch] ? associationTMP[ch] : ch\r\n\r\n const t = this.startAudienceTime.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const time = Date.UTC(d.year, d.month, d.day, t[0], t[1], t[2]) / 1000\r\n // * iniciar slider\r\n this.blockStartTime = time\r\n this.fInterface = await new FramesInterface(\r\n this.channel,\r\n this.numberOfRows,\r\n this.framesPerRow,\r\n time,\r\n this.startAudienceTime,\r\n this.useCache\r\n )\r\n await this.fInterface.init()\r\n\r\n this.getFramesArray()\r\n\r\n this.activeFrame = this.getIndex(1, 0, Positions.current)\r\n\r\n this.activeVideo = null\r\n },\r\n getIndex(rowNumber, frameIndex, position) {\r\n let from = this.framesPerRow * this.numberOfRows * position\r\n let till = this.framesPerRow * this.numberOfRows * (position + 1)\r\n\r\n return (from + till * (rowNumber - 1)) / rowNumber + frameIndex\r\n },\r\n getAudienceTime(frameTime, rowNumber, frameNumber, position) {\r\n if (!frameTime) {\r\n return 'Loading...'\r\n } else if (\r\n this.getIndex(rowNumber, frameNumber, position) === this.activeVideo\r\n ) {\r\n return this.convertToAudienceTime(this.videoTime)\r\n } else {\r\n return this.convertToAudienceTime(frameTime)\r\n }\r\n },\r\n dateInUtc(miliSeconds) {\r\n var date = new Date(miliSeconds)\r\n var utc = new Date(\r\n date.getUTCFullYear(),\r\n date.getUTCMonth(),\r\n date.getUTCDate(),\r\n date.getUTCHours(),\r\n date.getUTCMinutes(),\r\n date.getUTCSeconds()\r\n )\r\n return utc\r\n },\r\n convertToAudienceTime(time, separator = ':') {\r\n const d = this.getDateParts()\r\n const limit = Date.UTC(d.year, d.month, d.day, 23, 59, 59) / 1000\r\n\r\n let hour = this.dateInUtc(time * 1000)\r\n .toTimeString()\r\n .split(' ')[0]\r\n .split(':')\r\n .map(Number)\r\n\r\n if (time > limit && time <= limit + this.startAudienceSeconds) {\r\n hour[0] = 24 + hour[0]\r\n }\r\n return hour\r\n .map((part) => (part > 9 ? part.toString() : '0' + part))\r\n .join(separator)\r\n },\r\n getDateParts(date = this.date) {\r\n const d = new Date(date)\r\n return {\r\n year: d.getFullYear(),\r\n month: d.getMonth(),\r\n day: d.getDate(),\r\n }\r\n },\r\n selectFrame(index, frame) {\r\n const d = this.getDateParts()\r\n const limit = Date.UTC(d.year, d.month, d.day, 23, 59, 59) / 1000\r\n const frameTime = frame?.time\r\n\r\n if (frameTime - (this.startAudienceSeconds + limit) <= 0) {\r\n if (this.hourIniSelected === true) {\r\n this.hourIniSelected = frameTime\r\n\r\n if (\r\n this.hourEndSelected &&\r\n this.hourIniSelected > this.hourEndSelected\r\n ) {\r\n this.hourEndSelected = false\r\n }\r\n } else if (this.hourEndSelected === true) {\r\n if (frameTime > this.hourIniSelected) {\r\n this.hourEndSelected = frameTime\r\n this.canInsertTime = true\r\n } else {\r\n this.hourEndSelected = false\r\n }\r\n }\r\n }\r\n\r\n if (this.activeFrame !== index) {\r\n // ? Se clicar no frame diferente de onde está a dar play, faz pausa\r\n const array = this.$refs.frames.filter(\r\n (fc) => fc.videoStatus === fc.Status.playing\r\n )\r\n if (array.length === 1) {\r\n const frame = array[0]\r\n frame.playOrPause()\r\n }\r\n this.activeVideo = null\r\n this.activeFrame = index\r\n }\r\n },\r\n setHourIni() {\r\n this.canInsertTime = true\r\n this.hourIniSelected = true\r\n document.getElementById(`frame-${this.activeFrame}`).click()\r\n this.$emit('setHourIni', {\r\n hour_ini: this.hourIniSelected\r\n ? this.convertToAudienceTime(this.hourIniSelected, '')\r\n : null,\r\n })\r\n },\r\n setHourEnd() {\r\n this.canInsertTime = true\r\n this.hourEndSelected = true\r\n document.getElementById(`frame-${this.activeFrame}`).click()\r\n },\r\n //* Navegação\r\n arrowRight() {\r\n if (this.checkLimitRight(false)) {\r\n if (\r\n this.activeFrame ===\r\n this.numberOfRows * this.framesPerRow * 2 - 1\r\n ) {\r\n this.next()\r\n } else {\r\n this.activeFrame++\r\n }\r\n }\r\n },\r\n arrowLeft() {\r\n if (this.checkLimitLeft(false)) {\r\n if (this.activeFrame === this.numberOfRows * this.framesPerRow) {\r\n this.prev({ stayOnLast: true })\r\n } else {\r\n this.activeFrame--\r\n }\r\n }\r\n },\r\n arrowUp() {\r\n if (\r\n this.activeFrame - this.numberOfRows * this.framesPerRow >=\r\n Math.round((this.numberOfRows * this.framesPerRow) / 2)\r\n ) {\r\n this.activeFrame -= this.framesPerRow\r\n }\r\n },\r\n arrowDown() {\r\n if (\r\n this.activeFrame - this.numberOfRows * this.framesPerRow <\r\n Math.round((this.numberOfRows * this.framesPerRow) / 2)\r\n ) {\r\n this.activeFrame += this.framesPerRow\r\n }\r\n },\r\n checkLimitRight(value) {\r\n const hours = this.endAudienceTime.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const high = Date.UTC(\r\n d.year,\r\n d.month,\r\n d.day,\r\n hours[0],\r\n parseInt(hours[1]) + 30,\r\n hours[2]\r\n )\r\n\r\n if (value) {\r\n return (\r\n high >\r\n (this.fInterface.getCurrentTime() +\r\n this.numberOfRows * this.framesPerRow -\r\n 1) *\r\n 1000 && this.nextFrames[0].title !== -1\r\n )\r\n } else {\r\n // return high > (this.fInterface.getCurrentTime() + this.activeFrame) * 1000\r\n return high > this.fInterface.getCurrentTime() * 1000\r\n }\r\n },\r\n checkLimitLeft(value) {\r\n const hours = this.startAudienceTime.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const low = Date.UTC(d.year, d.month, d.day, hours[0], hours[1], hours[2])\r\n\r\n if (value) {\r\n return low <= (this.fInterface.getCurrentTime() - 1) * 1000\r\n } else {\r\n return (\r\n low <\r\n (this.fInterface.getCurrentTime() +\r\n this.activeFrame -\r\n this.numberOfRows * this.framesPerRow) *\r\n 1000\r\n )\r\n }\r\n },\r\n async next(config = {}) {\r\n if (\r\n (config.ignoreTime ||\r\n Date.now() - this.lastNext > this.swapImagesDelay) &&\r\n this.checkLimitRight(true) &&\r\n !this.navigationPending\r\n ) {\r\n this.navigationPending = true\r\n this.stopVideoPlaying()\r\n\r\n this.navigationPending = await new Promise((resolve) => {\r\n this.fInterface.loadNextFrames().then(() => {\r\n this.activeFrame = this.getIndex(1, 0, Positions.current)\r\n\r\n this.getFramesArray()\r\n this.lastNext = Date.now()\r\n resolve(false)\r\n })\r\n })\r\n } else {\r\n console.error('next blocked')\r\n }\r\n },\r\n async prev(config = {}) {\r\n if (\r\n (config.ignoreTime ||\r\n Date.now() - this.lastPrev > this.swapImagesDelay) &&\r\n this.checkLimitLeft(true) &&\r\n !this.navigationPending\r\n ) {\r\n this.navigationPending = true\r\n this.stopVideoPlaying()\r\n\r\n this.navigationPending = await new Promise((resolve) => {\r\n this.fInterface.loadPrevFrames().then(() => {\r\n if (config.stayOnLast) {\r\n this.activeFrame = this.getIndex(\r\n this.numberOfRows,\r\n this.framesPerRow - 1,\r\n Positions.current\r\n )\r\n } else {\r\n this.activeFrame = this.getIndex(1, 0, Positions.current)\r\n }\r\n\r\n this.getFramesArray()\r\n this.lastPrev = Date.now()\r\n resolve(false)\r\n })\r\n })\r\n } else {\r\n console.error('prev blocked')\r\n }\r\n },\r\n async setStartTime(time) {\r\n if (time.indexOf(':') !== -1) {\r\n time = time.replace(/:/g, '')\r\n }\r\n const t = time.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const setTime = Date.UTC(d.year, d.month, d.day, t[0], t[1], t[2]) / 1000\r\n // this.frames = this.loadingArray\r\n\r\n await this.fInterface.changeTime(setTime)\r\n\r\n this.getFramesArray()\r\n\r\n this.activeFrame = this.getIndex(1, 0, Positions.current)\r\n\r\n this.activeVideo = null\r\n\r\n return true\r\n },\r\n hourToTimeStamp(time) {\r\n if (time.indexOf(':') !== -1) {\r\n time = time.replace(/:/g, '')\r\n }\r\n const t = time.match(/.{1,2}/g)\r\n const d = this.getDateParts()\r\n const setTime = Date.UTC(d.year, d.month, d.day, t[0], t[1], t[2]) / 1000\r\n\r\n return setTime\r\n },\r\n changeHour(value) {\r\n if (value) {\r\n return new Promise((resolve) => {\r\n setTimeout(async () => {\r\n this.stopVideoPlaying()\r\n\r\n await this.setStartTime(value, true)\r\n resolve()\r\n }, 0)\r\n })\r\n }\r\n },\r\n changeBlockInterval(value) {\r\n this.changeHour(value.ini)\r\n let time_ini, time_end\r\n time_ini = this.hourToTimeStamp(value.ini)\r\n time_end = this.hourToTimeStamp(value.end)\r\n this.videoSliderTotalDuration = time_end - time_ini\r\n this.$refs.frames[0].changeSettings(time_ini)\r\n this.blockStartTime = time_ini\r\n },\r\n //eslint-disable-next-line\r\n async updateVideoTime(index, videoTime) {\r\n this.activeVideo = index\r\n this.videoTime = videoTime\r\n },\r\n //eslint-disable-next-line\r\n updateVideoStatus(currentTime) {\r\n if (!this.progressVideoDrag) {\r\n // ESTA FUNÇÃO PASSOU PARA DENTRO DOS COMMANDS\r\n // this.updateProgress(null, currentTime)\r\n }\r\n },\r\n async startPlaying(frame, totalTime) {\r\n const array = this.$refs.frames.filter(\r\n (fc) => fc.frame.time !== frame.time\r\n )\r\n this.stopVideoPlaying(array)\r\n\r\n this.videoTotalTime = totalTime\r\n this.videoPlaying = true\r\n },\r\n stopPlaying() {\r\n this.videoTotalTime = null\r\n this.videoPlaying = false\r\n this.paused = false\r\n },\r\n insertTime() {\r\n this.$emit('timeToInsert', {\r\n channel: this.channel,\r\n hour_ini: this.hourIniSelected\r\n ? this.convertToAudienceTime(this.hourIniSelected, '')\r\n : null,\r\n hour_end: this.hourEndSelected\r\n ? this.convertToAudienceTime(this.hourEndSelected, '')\r\n : null,\r\n force: false,\r\n })\r\n\r\n if (this.jumpOnInsert) {\r\n this.changeHour(\r\n this.convertToAudienceTime(\r\n this.hourEndSelected || this.hourIniSelected\r\n )\r\n ).then(() => {\r\n this.activeFrame = this.getIndex(1, 1, Positions.current)\r\n })\r\n }\r\n\r\n if (this.removeSelectionOnInsert) {\r\n this.hourIniSelected = null\r\n this.hourEndSelected = null\r\n this.canInsertTime = false\r\n }\r\n },\r\n insertTimeForce() {\r\n this.$emit('timeToInsert', {\r\n channel: this.channel,\r\n hour_ini: this.hourIniSelected\r\n ? this.convertToAudienceTime(this.hourIniSelected, '')\r\n : null,\r\n hour_end: this.hourEndSelected\r\n ? this.convertToAudienceTime(this.hourEndSelected, '')\r\n : null,\r\n force: true,\r\n })\r\n\r\n if (this.removeSelectionOnInsert) {\r\n this.hourIniSelected = null\r\n this.hourEndSelected = null\r\n this.canInsertTime = false\r\n }\r\n },\r\n async getChannelMedia() {\r\n // this.media = (await ChannelService.show(this.channel)).data.MEDIA\r\n },\r\n async changeServerClick() {\r\n this.changeServer = !this.changeServer\r\n sessionStorage.setItem(\r\n 'server',\r\n this.changeServer ? 'alternative' : 'default'\r\n )\r\n\r\n location.reload()\r\n },\r\n },\r\n computed: {\r\n swapImagesDelay() {\r\n return 0\r\n // return this.numberOfRows * this.framesPerRow * 15\r\n },\r\n active: {\r\n get() {\r\n return this.value\r\n },\r\n set(value) {\r\n this.$emit('input', value)\r\n },\r\n },\r\n settingsClosed() {\r\n return !Object.values(this.dialogs).find((v) => v)\r\n },\r\n startAudienceSeconds() {\r\n const t = this.startAudienceTime.match(/.{1,2}/g)\r\n return parseInt(t[0] * 3600 + t[1] * 60 + t[2])\r\n },\r\n loadingArray() {\r\n return Array.from(Array(this.numberOfRows * this.framesPerRow).keys())\r\n },\r\n serverOfFrames() {\r\n return sessionStorage.getItem('server')\r\n },\r\n },\r\n watch: {\r\n async secondsPerFrame(value) {\r\n const activeF =\r\n this.frames[this.activeFrame - this.numberOfRows * this.framesPerRow]\r\n\r\n if (activeF) {\r\n this.changeHour(this.getAudienceTime(activeF.time, 0, 0, 0))\r\n this.fInterface.setCurrentStep(this.secondsPerFrame)\r\n await this.fInterface.loadFrames()\r\n this.getFramesArray()\r\n }\r\n },\r\n framesFormat(value) {\r\n this.setFrameSelection(value)\r\n },\r\n active() {\r\n // ? sempre que trocamos de tabs dar reset as horas selected\r\n if (this.removeSelectionOnInsert) {\r\n this.hourIniSelected = false\r\n this.hourEndSelected = false\r\n }\r\n },\r\n useCache() {\r\n this.createFramesInterface()\r\n },\r\n hourIniSelected(value) {\r\n if (value) {\r\n sessionStorage.setItem(\r\n 'currentTimeFrames',\r\n this.convertToAudienceTime(this.hourIniSelected, '')\r\n )\r\n } else {\r\n sessionStorage.removeItem('currentTimeFrames')\r\n }\r\n },\r\n activeFrame(value) {\r\n if (value) {\r\n this.stopPlayingBar()\r\n }\r\n },\r\n channel() {\r\n this.updatingChannel = new Promise((resolve, reject) => {\r\n try {\r\n this.createFramesInterface()\r\n resolve(true)\r\n } catch (err) {\r\n reject(err)\r\n }\r\n })\r\n },\r\n },\r\n}\r\n</script>\r\n<style scoped>\r\n.visualization-row {\r\n display: flex;\r\n flex-wrap: wrap;\r\n flex: 1 1 auto;\r\n}\r\n\r\n.visualization-col {\r\n flex-basis: 0;\r\n flex-grow: 1;\r\n max-width: 100%;\r\n padding: 12px;\r\n}\r\n\r\n.visualization-divider {\r\n display: block;\r\n flex: 1 1 100%;\r\n height: 0px;\r\n max-height: 0px;\r\n opacity: 1;\r\n transition: inherit;\r\n border-style: solid;\r\n border-width: thin 0 0 0;\r\n border-color: rgba(0, 0, 0, 0.12);\r\n margin: 0;\r\n}\r\n\r\n.visualization-divider.vertical {\r\n align-self: stretch;\r\n border-width: 0 thin 0 0;\r\n display: inline-flex;\r\n height: inherit;\r\n margin-left: -1px;\r\n max-height: 100%;\r\n max-width: 0px;\r\n vertical-align: text-bottom;\r\n width: 0px;\r\n}\r\n\r\n.visualization-card {\r\n flex-basis: 0;\r\n flex-grow: 1;\r\n max-width: 100%;\r\n padding: 12px;\r\n width: 100%;\r\n transition-property: box-shadow, opacity, -webkit-box-shadow;\r\n overflow-wrap: break-word;\r\n /*box-shadow: 0 3px 1px -2px rgba(0, 0, 0, 0.2), 0 2px 2px 0 rgba(0, 0, 0, 0.14),\r\n 0 1px 5px 0 rgba(0, 0, 0, 0.12);*/\r\n}\r\n\r\n.visualization-justify-center,\r\n/deep/ .visualization-justify-center {\r\n justify-content: center;\r\n}\r\n\r\n.visualization-align-center {\r\n align-items: center;\r\n}\r\n\r\n#visualization-container {\r\n max-width: 100% !important;\r\n margin: 0 auto !important;\r\n height: 100%;\r\n border-bottom: none;\r\n}\r\n#visualization-container > .card {\r\n border-radius: 0 !important;\r\n font-size: 12px;\r\n width: 100%;\r\n box-shadow: none;\r\n height: 100%;\r\n}\r\n\r\n#command-bar,\r\n#info-bar {\r\n background-color: #f5f5f5;\r\n box-shadow: 0 3px 1px -2px rgba(0, 0, 0, 0.2), 0 2px 2px 0 rgba(0, 0, 0, 0.14),\r\n 0 1px 5px 0 rgba(0, 0, 0, 0.12);\r\n}\r\n#command-bar button {\r\n width: 42px;\r\n height: 36px;\r\n border: none;\r\n background: none;\r\n}\r\n\r\n#command-bar button:hover {\r\n cursor: pointer;\r\n background: rgba(0, 0, 0, 0.12);\r\n}\r\n\r\n#command-bar svg {\r\n font-size: 16px;\r\n}\r\n\r\n#command-bar {\r\n padding: 0 !important;\r\n}\r\n\r\n#info-bar {\r\n padding: 4px;\r\n font-size: 14px;\r\n position: relative;\r\n}\r\n\r\n.settings-container {\r\n position: absolute;\r\n right: 14px;\r\n top: 50%;\r\n transform: translateY(-50%);\r\n}\r\n\r\n.settings-container > * {\r\n margin: 0 2px;\r\n cursor: pointer;\r\n}\r\n\r\n#info-bar svg {\r\n font-size: 16px;\r\n}\r\n\r\n#info-bar .divider {\r\n margin: 0 8px;\r\n}\r\n\r\nsvg:focus {\r\n border: none;\r\n}\r\n\r\n.visualization-card {\r\n border-left: 8px solid #eee;\r\n}\r\n\r\n.active-tab {\r\n border-left: 8px solid var(--visualization-primary) !important;\r\n border-image-slice: 1;\r\n}\r\n\r\n[id^='frame-'] {\r\n padding: 1px;\r\n display: flex;\r\n flex-flow: column;\r\n}\r\n\r\n.tooltip {\r\n display: block !important;\r\n z-index: 10000;\r\n}\r\n\r\n.tooltip .tooltip-inner {\r\n background: var(--visualization-primary);\r\n color: white;\r\n border-radius: 16px;\r\n padding: 5px 10px 4px;\r\n}\r\n\r\n.tooltip .tooltip-arrow {\r\n width: 0;\r\n height: 0;\r\n border-style: solid;\r\n position: absolute;\r\n margin: 5px;\r\n border-color: var(--visualization-primary);\r\n z-index: 1;\r\n}\r\n\r\n.tooltip[x-placement^='top'] {\r\n margin-bottom: 5px;\r\n}\r\n\r\n.tooltip[x-placement^='top'] .tooltip-arrow {\r\n border-width: 5px 5px 0 5px;\r\n border-left-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n bottom: -5px;\r\n left: calc(50% - 5px);\r\n margin-top: 0;\r\n margin-bottom: 0;\r\n}\r\n\r\n.tooltip[x-placement^='bottom'] {\r\n margin-top: 5px;\r\n}\r\n\r\n.tooltip[x-placement^='bottom'] .tooltip-arrow {\r\n border-width: 0 5px 5px 5px;\r\n border-left-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-top-color: transparent !important;\r\n top: -5px;\r\n left: calc(50% - 5px);\r\n margin-top: 0;\r\n margin-bottom: 0;\r\n}\r\n\r\n.tooltip[x-placement^='right'] {\r\n margin-left: 5px;\r\n}\r\n\r\n.tooltip[x-placement^='right'] .tooltip-arrow {\r\n border-width: 5px 5px 5px 0;\r\n border-left-color: transparent !important;\r\n border-top-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n left: -5px;\r\n top: calc(50% - 5px);\r\n margin-left: 0;\r\n margin-right: 0;\r\n}\r\n\r\n.tooltip[x-placement^='left'] {\r\n margin-right: 5px;\r\n}\r\n\r\n.tooltip[x-placement^='left'] .tooltip-arrow {\r\n border-width: 5px 0 5px 5px;\r\n border-top-color: transparent !important;\r\n border-right-color: transparent !important;\r\n border-bottom-color: transparent !important;\r\n right: -5px;\r\n top: calc(50% - 5px);\r\n margin-left: 0;\r\n margin-right: 0;\r\n}\r\n\r\n.tooltip.popover .popover-inner {\r\n background: #f9f9f9;\r\n color: black;\r\n padding: 24px;\r\n border-radius: 5px;\r\n box-shadow: 0 5px 30px rgba(black, 0.1);\r\n}\r\n\r\n.tooltip.popover .popover-arrow {\r\n border-color: #f9f9f9;\r\n}\r\n\r\n.tooltip[aria-hidden='true'] {\r\n visibility: hidden;\r\n opacity: 0;\r\n transition: opacity 0.15s, visibility 0.15s;\r\n}\r\n\r\n.tooltip[aria-hidden='false'] {\r\n visibility: visible;\r\n opacity: 1;\r\n transition: opacity 0.15s;\r\n}\r\n</style>\r\n"]}, media: undefined });
4684
4686
 
4685
4687
  };
4686
4688
  /* scoped */
4687
- const __vue_scope_id__ = "data-v-11249812";
4689
+ const __vue_scope_id__ = "data-v-08eea866";
4688
4690
  /* module identifier */
4689
4691
  const __vue_module_identifier__ = undefined;
4690
4692
  /* functional template */
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@twab/visualization",
3
- "version": "1.4.3",
3
+ "version": "1.4.5",
4
4
  "main": "dist/visualization.js",
5
5
  "files": [
6
6
  "dist"