@thoughtspot/visual-embed-sdk 1.39.3 → 1.40.1-alpha.1

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 (93) hide show
  1. package/cjs/src/embed/app.d.ts +56 -0
  2. package/cjs/src/embed/app.d.ts.map +1 -1
  3. package/cjs/src/embed/app.js +47 -8
  4. package/cjs/src/embed/app.js.map +1 -1
  5. package/cjs/src/embed/app.spec.js +322 -7
  6. package/cjs/src/embed/app.spec.js.map +1 -1
  7. package/cjs/src/embed/liveboard.d.ts +58 -1
  8. package/cjs/src/embed/liveboard.d.ts.map +1 -1
  9. package/cjs/src/embed/liveboard.js +59 -8
  10. package/cjs/src/embed/liveboard.js.map +1 -1
  11. package/cjs/src/embed/liveboard.spec.js +206 -0
  12. package/cjs/src/embed/liveboard.spec.js.map +1 -1
  13. package/cjs/src/embed/ts-embed.d.ts +7 -0
  14. package/cjs/src/embed/ts-embed.d.ts.map +1 -1
  15. package/cjs/src/embed/ts-embed.js +61 -7
  16. package/cjs/src/embed/ts-embed.js.map +1 -1
  17. package/cjs/src/types.d.ts +37 -6
  18. package/cjs/src/types.d.ts.map +1 -1
  19. package/cjs/src/types.js +35 -4
  20. package/cjs/src/types.js.map +1 -1
  21. package/cjs/src/utils/processTrigger.js +2 -1
  22. package/cjs/src/utils/processTrigger.js.map +1 -1
  23. package/cjs/src/utils.d.ts +6 -0
  24. package/cjs/src/utils.d.ts.map +1 -1
  25. package/cjs/src/utils.js +23 -3
  26. package/cjs/src/utils.js.map +1 -1
  27. package/cjs/src/utils.spec.js +212 -1
  28. package/cjs/src/utils.spec.js.map +1 -1
  29. package/dist/{index-ZrE8YYq8.js → index-CmEQfuE3.js} +1 -1
  30. package/dist/index-D1pyb7RG.js +7371 -0
  31. package/dist/index-DeFzsyFF.js +7371 -0
  32. package/dist/index-Dpf0rd6w.js +7371 -0
  33. package/dist/index-UuEbsISo.js +7447 -0
  34. package/dist/index-e3Uw3YFO.js +7371 -0
  35. package/dist/src/embed/app.d.ts +56 -0
  36. package/dist/src/embed/app.d.ts.map +1 -1
  37. package/dist/src/embed/bodyless-conversation.d.ts +0 -4
  38. package/dist/src/embed/bodyless-conversation.d.ts.map +1 -1
  39. package/dist/src/embed/liveboard.d.ts +56 -0
  40. package/dist/src/embed/liveboard.d.ts.map +1 -1
  41. package/dist/src/react/index.d.ts +0 -2
  42. package/dist/src/react/index.d.ts.map +1 -1
  43. package/dist/src/types.d.ts +16 -198
  44. package/dist/src/types.d.ts.map +1 -1
  45. package/dist/src/utils/graphql/nlsService/conversation-service.d.ts.map +1 -1
  46. package/dist/src/utils.d.ts +6 -0
  47. package/dist/src/utils.d.ts.map +1 -1
  48. package/dist/tsembed-react.es.js +137 -224
  49. package/dist/tsembed-react.js +136 -223
  50. package/dist/tsembed.es.js +137 -224
  51. package/dist/tsembed.js +136 -223
  52. package/dist/visual-embed-sdk-react-full.d.ts +106 -204
  53. package/dist/visual-embed-sdk-react.d.ts +106 -204
  54. package/dist/visual-embed-sdk.d.ts +106 -202
  55. package/lib/src/embed/app.d.ts +56 -0
  56. package/lib/src/embed/app.d.ts.map +1 -1
  57. package/lib/src/embed/app.js +48 -9
  58. package/lib/src/embed/app.js.map +1 -1
  59. package/lib/src/embed/app.spec.js +322 -7
  60. package/lib/src/embed/app.spec.js.map +1 -1
  61. package/lib/src/embed/liveboard.d.ts +58 -1
  62. package/lib/src/embed/liveboard.d.ts.map +1 -1
  63. package/lib/src/embed/liveboard.js +60 -9
  64. package/lib/src/embed/liveboard.js.map +1 -1
  65. package/lib/src/embed/liveboard.spec.js +206 -0
  66. package/lib/src/embed/liveboard.spec.js.map +1 -1
  67. package/lib/src/embed/ts-embed.d.ts +7 -0
  68. package/lib/src/embed/ts-embed.d.ts.map +1 -1
  69. package/lib/src/embed/ts-embed.js +61 -7
  70. package/lib/src/embed/ts-embed.js.map +1 -1
  71. package/lib/src/types.d.ts +37 -6
  72. package/lib/src/types.d.ts.map +1 -1
  73. package/lib/src/types.js +35 -4
  74. package/lib/src/types.js.map +1 -1
  75. package/lib/src/utils/processTrigger.js +2 -1
  76. package/lib/src/utils/processTrigger.js.map +1 -1
  77. package/lib/src/utils.d.ts +6 -0
  78. package/lib/src/utils.d.ts.map +1 -1
  79. package/lib/src/utils.js +21 -2
  80. package/lib/src/utils.js.map +1 -1
  81. package/lib/src/utils.spec.js +213 -2
  82. package/lib/src/utils.spec.js.map +1 -1
  83. package/lib/src/visual-embed-sdk.d.ts +106 -202
  84. package/package.json +1 -2
  85. package/src/embed/app.spec.ts +397 -8
  86. package/src/embed/app.ts +106 -12
  87. package/src/embed/liveboard.spec.ts +254 -1
  88. package/src/embed/liveboard.ts +109 -11
  89. package/src/embed/ts-embed.ts +84 -21
  90. package/src/types.ts +36 -5
  91. package/src/utils/processTrigger.ts +1 -1
  92. package/src/utils.spec.ts +250 -2
  93. package/src/utils.ts +28 -2
@@ -786,7 +786,7 @@ describe('Liveboard/viz embed tests', () => {
786
786
  await waitFor(() => !!getIFrameEl());
787
787
 
788
788
  const ts = '__tsEmbed';
789
- expect(document.getElementById(libEmbed.getPreRenderIds().wrapper)[ts]).toEqual(
789
+ expect((document.getElementById(libEmbed.getPreRenderIds().wrapper) as any)[ts]).toEqual(
790
790
  libEmbed,
791
791
  );
792
792
 
@@ -814,6 +814,259 @@ describe('Liveboard/viz embed tests', () => {
814
814
  });
815
815
  });
816
816
 
817
+ describe('LazyLoadingForFullHeight functionality', () => {
818
+ let mockIFrame: HTMLIFrameElement;
819
+
820
+ beforeEach(() => {
821
+ mockIFrame = document.createElement('iframe');
822
+ mockIFrame.getBoundingClientRect = jest.fn().mockReturnValue({
823
+ top: 100,
824
+ left: 150,
825
+ bottom: 600,
826
+ right: 800,
827
+ width: 650,
828
+ height: 500,
829
+ });
830
+ jest.spyOn(document, 'createElement').mockImplementation((tagName) => {
831
+ if (tagName === 'iframe') {
832
+ return mockIFrame;
833
+ }
834
+ return document.createElement(tagName);
835
+ });
836
+ });
837
+
838
+ afterEach(() => {
839
+ jest.restoreAllMocks();
840
+ });
841
+
842
+ test('should set lazyLoadingMargin parameter when provided', async () => {
843
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
844
+ ...defaultViewConfig,
845
+ liveboardId,
846
+ fullHeight: true,
847
+ lazyLoadingForFullHeight: true,
848
+ lazyLoadingMargin: '100px 0px',
849
+ } as LiveboardViewConfig);
850
+
851
+ await liveboardEmbed.render();
852
+
853
+ await executeAfterWait(() => {
854
+ const iframeSrc = getIFrameSrc();
855
+ expect(iframeSrc).toContain('isLazyLoadingForEmbedEnabled=true');
856
+ expect(iframeSrc).toContain('isFullHeightPinboard=true');
857
+ expect(iframeSrc).toContain('rootMarginForLazyLoad=100px%200px');
858
+ }, 100);
859
+ });
860
+
861
+ test('should set isLazyLoadingForEmbedEnabled=true when both fullHeight and lazyLoadingForFullHeight are enabled', async () => {
862
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
863
+ ...defaultViewConfig,
864
+ liveboardId,
865
+ fullHeight: true,
866
+ lazyLoadingForFullHeight: true,
867
+ } as LiveboardViewConfig);
868
+
869
+ await liveboardEmbed.render();
870
+
871
+ await executeAfterWait(() => {
872
+ const iframeSrc = getIFrameSrc();
873
+ expect(iframeSrc).toContain('isLazyLoadingForEmbedEnabled=true');
874
+ expect(iframeSrc).toContain('isFullHeightPinboard=true');
875
+ }, 100);
876
+ });
877
+
878
+ test('should not set lazyLoadingForEmbed when lazyLoadingForFullHeight is enabled but fullHeight is false', async () => {
879
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
880
+ ...defaultViewConfig,
881
+ liveboardId,
882
+ fullHeight: false,
883
+ lazyLoadingForFullHeight: true,
884
+ } as LiveboardViewConfig);
885
+
886
+ await liveboardEmbed.render();
887
+
888
+ await executeAfterWait(() => {
889
+ const iframeSrc = getIFrameSrc();
890
+ expect(iframeSrc).not.toContain('isLazyLoadingForEmbedEnabled=true');
891
+ expect(iframeSrc).not.toContain('isFullHeightPinboard=true');
892
+ }, 100);
893
+ });
894
+
895
+ test('should not set isLazyLoadingForEmbedEnabled when fullHeight is true but lazyLoadingForFullHeight is false', async () => {
896
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
897
+ ...defaultViewConfig,
898
+ liveboardId,
899
+ fullHeight: true,
900
+ lazyLoadingForFullHeight: false,
901
+ } as LiveboardViewConfig);
902
+
903
+ await liveboardEmbed.render();
904
+
905
+ await executeAfterWait(() => {
906
+ const iframeSrc = getIFrameSrc();
907
+ expect(iframeSrc).not.toContain('isLazyLoadingForEmbedEnabled=true');
908
+ expect(iframeSrc).toContain('isFullHeightPinboard=true');
909
+ }, 100);
910
+ });
911
+
912
+ test('should register event handlers to adjust iframe height', async () => {
913
+ const onSpy = jest.spyOn(LiveboardEmbed.prototype, 'on');
914
+
915
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
916
+ ...defaultViewConfig,
917
+ liveboardId,
918
+ fullHeight: true,
919
+ lazyLoadingForFullHeight: true,
920
+ } as LiveboardViewConfig);
921
+
922
+ await liveboardEmbed.render();
923
+
924
+ await executeAfterWait(() => {
925
+ expect(onSpy).toHaveBeenCalledWith(EmbedEvent.EmbedHeight, expect.anything());
926
+ expect(onSpy).toHaveBeenCalledWith(EmbedEvent.RouteChange, expect.anything());
927
+ expect(onSpy).toHaveBeenCalledWith(EmbedEvent.EmbedIframeCenter, expect.anything());
928
+ expect(onSpy).toHaveBeenCalledWith(EmbedEvent.RequestVisibleEmbedCoordinates, expect.anything());
929
+ }, 100);
930
+ });
931
+
932
+ test('should send correct visible data when RequestVisibleEmbedCoordinates is triggered', async () => {
933
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
934
+ ...defaultViewConfig,
935
+ liveboardId,
936
+ fullHeight: true,
937
+ lazyLoadingForFullHeight: true,
938
+ } as LiveboardViewConfig);
939
+
940
+ const mockTrigger = jest.spyOn(liveboardEmbed, 'trigger');
941
+
942
+ await liveboardEmbed.render();
943
+
944
+ // Trigger the lazy load data calculation
945
+ (liveboardEmbed as any).sendFullHeightLazyLoadData();
946
+
947
+ expect(mockTrigger).toHaveBeenCalledWith(HostEvent.VisibleEmbedCoordinates, {
948
+ top: 0,
949
+ height: 500,
950
+ left: 0,
951
+ width: 650,
952
+ });
953
+ });
954
+
955
+ test('should calculate correct visible data for partially visible full height element', async () => {
956
+ mockIFrame.getBoundingClientRect = jest.fn().mockReturnValue({
957
+ top: -50,
958
+ left: -30,
959
+ bottom: 700,
960
+ right: 1024,
961
+ width: 1054,
962
+ height: 750,
963
+ });
964
+
965
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
966
+ ...defaultViewConfig,
967
+ liveboardId,
968
+ fullHeight: true,
969
+ lazyLoadingForFullHeight: true,
970
+ } as LiveboardViewConfig);
971
+
972
+ const mockTrigger = jest.spyOn(liveboardEmbed, 'trigger');
973
+
974
+ await liveboardEmbed.render();
975
+
976
+ // Trigger the lazy load data calculation
977
+ (liveboardEmbed as any).sendFullHeightLazyLoadData();
978
+
979
+ expect(mockTrigger).toHaveBeenCalledWith(HostEvent.VisibleEmbedCoordinates, {
980
+ top: 50,
981
+ height: 700,
982
+ left: 30,
983
+ width: 1024,
984
+ });
985
+ });
986
+
987
+ test('should add window event listeners for resize and scroll when fullHeight and lazyLoadingForFullHeight are enabled', async () => {
988
+ const addEventListenerSpy = jest.spyOn(window, 'addEventListener');
989
+
990
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
991
+ ...defaultViewConfig,
992
+ liveboardId,
993
+ fullHeight: true,
994
+ lazyLoadingForFullHeight: true,
995
+ } as LiveboardViewConfig);
996
+
997
+ await liveboardEmbed.render();
998
+
999
+ // Wait for the post-render events to be registered
1000
+ await executeAfterWait(() => {
1001
+ expect(addEventListenerSpy).toHaveBeenCalledWith('resize', expect.anything());
1002
+ expect(addEventListenerSpy).toHaveBeenCalledWith('scroll', expect.anything(), true);
1003
+ }, 100);
1004
+
1005
+ addEventListenerSpy.mockRestore();
1006
+ });
1007
+
1008
+ test('should remove window event listeners on destroy when fullHeight and lazyLoadingForFullHeight are enabled', async () => {
1009
+ const removeEventListenerSpy = jest.spyOn(window, 'removeEventListener');
1010
+
1011
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
1012
+ ...defaultViewConfig,
1013
+ liveboardId,
1014
+ fullHeight: true,
1015
+ lazyLoadingForFullHeight: true,
1016
+ } as LiveboardViewConfig);
1017
+
1018
+ await liveboardEmbed.render();
1019
+ liveboardEmbed.destroy();
1020
+
1021
+ expect(removeEventListenerSpy).toHaveBeenCalledWith('resize', expect.anything());
1022
+ expect(removeEventListenerSpy).toHaveBeenCalledWith('scroll', expect.anything());
1023
+
1024
+ removeEventListenerSpy.mockRestore();
1025
+ });
1026
+
1027
+ test('should handle RequestVisibleEmbedCoordinates event and respond with correct data', async () => {
1028
+ // Mock the iframe element
1029
+ mockIFrame.getBoundingClientRect = jest.fn().mockReturnValue({
1030
+ top: 100,
1031
+ left: 150,
1032
+ bottom: 600,
1033
+ right: 800,
1034
+ width: 650,
1035
+ height: 500,
1036
+ });
1037
+ Object.defineProperty(mockIFrame, 'scrollHeight', { value: 500 });
1038
+
1039
+ const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
1040
+ ...defaultViewConfig,
1041
+ liveboardId,
1042
+ fullHeight: true,
1043
+ lazyLoadingForFullHeight: true,
1044
+ } as LiveboardViewConfig);
1045
+
1046
+ // Set the iframe before render
1047
+ (liveboardEmbed as any).iFrame = mockIFrame;
1048
+
1049
+ await liveboardEmbed.render();
1050
+
1051
+ // Create a mock responder function
1052
+ const mockResponder = jest.fn();
1053
+
1054
+ // Trigger the handler directly
1055
+ (liveboardEmbed as any).requestVisibleEmbedCoordinatesHandler({}, mockResponder);
1056
+
1057
+ // Verify the responder was called with the correct data
1058
+ expect(mockResponder).toHaveBeenCalledWith({
1059
+ type: EmbedEvent.RequestVisibleEmbedCoordinates,
1060
+ data: {
1061
+ top: 0,
1062
+ height: 500,
1063
+ left: 0,
1064
+ width: 650,
1065
+ },
1066
+ });
1067
+ });
1068
+ });
1069
+
817
1070
  describe('Host events for liveborad', () => {
818
1071
  test('Host event with empty param', async () => {
819
1072
  const mockProcessTrigger = jest.spyOn(tsEmbed.TsEmbed.prototype, 'trigger');
@@ -21,7 +21,7 @@ import {
21
21
  BaseViewConfig,
22
22
  LiveboardAppEmbedViewConfig,
23
23
  } from '../types';
24
- import { getQueryParamString, isUndefined } from '../utils';
24
+ import { calculateVisibleElementData, getQueryParamString, isUndefined } from '../utils';
25
25
  import { getAuthPromise } from './base';
26
26
  import { TsEmbed, V1Embed } from './ts-embed';
27
27
  import { addPreviewStylesIfNotPresent } from '../utils/global-styles';
@@ -324,6 +324,46 @@ export interface LiveboardViewConfig extends BaseViewConfig, LiveboardOtherViewC
324
324
  * ```
325
325
  */
326
326
  isLiveboardStylingAndGroupingEnabled?: boolean;
327
+ /**
328
+ * This flag is used to enable the full height lazy load data.
329
+ *
330
+ * @example
331
+ * ```js
332
+ * const embed = new LiveboardEmbed('#embed-container', {
333
+ * // ...other options
334
+ * fullHeight: true,
335
+ * lazyLoadingForFullHeight: true,
336
+ * })
337
+ * ```
338
+ *
339
+ * @type {boolean}
340
+ * @default false
341
+ * @version SDK: 1.40.0 | ThoughtSpot:10.12.0.cl
342
+ */
343
+ lazyLoadingForFullHeight?: boolean;
344
+ /**
345
+ * The margin to be used for lazy loading.
346
+ *
347
+ * For example, if the margin is set to '10px',
348
+ * the visualization will be loaded 10px before the its top edge is visible in the
349
+ * viewport.
350
+ *
351
+ * The format is similar to CSS margin.
352
+ *
353
+ * @example
354
+ * ```js
355
+ * const embed = new LiveboardEmbed('#embed-container', {
356
+ * // ...other options
357
+ * fullHeight: true,
358
+ * lazyLoadingForFullHeight: true,
359
+ * // Using 0px, the visualization will be only loaded when its visible in the viewport.
360
+ * lazyLoadingMargin: '0px',
361
+ * })
362
+ * ```
363
+ * @type {string}
364
+ * @version SDK: 1.40.0 | ThoughtSpot:10.12.0.cl
365
+ */
366
+ lazyLoadingMargin?: string;
327
367
  }
328
368
 
329
369
  /**
@@ -346,19 +386,20 @@ export class LiveboardEmbed extends V1Embed {
346
386
 
347
387
  private defaultHeight = 500;
348
388
 
349
-
389
+
350
390
  constructor(domSelector: DOMSelector, viewConfig: LiveboardViewConfig) {
351
391
  viewConfig.embedComponentType = 'LiveboardEmbed';
352
392
  super(domSelector, viewConfig);
353
393
  if (this.viewConfig.fullHeight === true) {
354
394
  if (this.viewConfig.vizId) {
355
395
  logger.warn('Full height is currently only supported for Liveboard embeds.' +
356
- 'Using full height with vizId might lead to unexpected behavior.');
396
+ 'Using full height with vizId might lead to unexpected behavior.');
357
397
  }
358
398
 
359
399
  this.on(EmbedEvent.RouteChange, this.setIframeHeightForNonEmbedLiveboard);
360
400
  this.on(EmbedEvent.EmbedHeight, this.updateIFrameHeight);
361
401
  this.on(EmbedEvent.EmbedIframeCenter, this.embedIframeCenter);
402
+ this.on(EmbedEvent.RequestVisibleEmbedCoordinates, this.requestVisibleEmbedCoordinatesHandler);
362
403
  }
363
404
  }
364
405
 
@@ -367,7 +408,7 @@ export class LiveboardEmbed extends V1Embed {
367
408
  * embedded Liveboard or visualization.
368
409
  */
369
410
  protected getEmbedParams() {
370
- let params = {};
411
+ let params: any = {};
371
412
  params = this.getBaseQueryParams(params);
372
413
  const {
373
414
  enableVizTransformations,
@@ -402,6 +443,10 @@ export class LiveboardEmbed extends V1Embed {
402
443
 
403
444
  if (fullHeight === true) {
404
445
  params[Param.fullHeight] = true;
446
+ if (this.viewConfig.lazyLoadingForFullHeight) {
447
+ params[Param.IsLazyLoadingForEmbedEnabled] = true;
448
+ params[Param.RootMarginForLazyLoad] = this.viewConfig.lazyLoadingMargin;
449
+ }
405
450
  }
406
451
  if (defaultHeight) {
407
452
  this.defaultHeight = defaultHeight;
@@ -484,6 +529,23 @@ export class LiveboardEmbed extends V1Embed {
484
529
  return suffix;
485
530
  }
486
531
 
532
+ private sendFullHeightLazyLoadData = () => {
533
+ const data = calculateVisibleElementData(this.iFrame);
534
+ this.trigger(HostEvent.VisibleEmbedCoordinates, data);
535
+ }
536
+
537
+ /**
538
+ * This is a handler for the RequestVisibleEmbedCoordinates event.
539
+ * It is used to send the visible coordinates data to the host application.
540
+ * @param data The event payload
541
+ * @param responder The responder function
542
+ */
543
+ private requestVisibleEmbedCoordinatesHandler = (data: MessagePayload, responder: any) => {
544
+ logger.info('Sending RequestVisibleEmbedCoordinates', data);
545
+ const visibleCoordinatesData = calculateVisibleElementData(this.iFrame);
546
+ responder({ type: EmbedEvent.RequestVisibleEmbedCoordinates, data: visibleCoordinatesData });
547
+ }
548
+
487
549
  /**
488
550
  * Construct the URL of the embedded ThoughtSpot Liveboard or visualization
489
551
  * to be loaded within the iFrame.
@@ -509,6 +571,7 @@ export class LiveboardEmbed extends V1Embed {
509
571
  */
510
572
  private updateIFrameHeight = (data: MessagePayload) => {
511
573
  this.setIFrameHeight(Math.max(data.data, this.defaultHeight));
574
+ this.sendFullHeightLazyLoadData();
512
575
  };
513
576
 
514
577
  private embedIframeCenter = (data: MessagePayload, responder: any) => {
@@ -582,16 +645,20 @@ export class LiveboardEmbed extends V1Embed {
582
645
  }
583
646
 
584
647
  protected beforePrerenderVisible(): void {
585
- const embedObj = this.insertedDomEl?.[this.embedNodeKey] as LiveboardEmbed;
648
+ const embedObj = this.getPreRenderObj<LiveboardEmbed>();
586
649
 
587
650
  if (isUndefined(embedObj)) return;
588
651
 
589
- const showDifferentLib = this.viewConfig.liveboardId
590
- && embedObj.viewConfig.liveboardId !== this.viewConfig.liveboardId;
652
+ const showDifferentLib = this.currentLiveboardId
653
+ && embedObj.currentLiveboardId !== this.currentLiveboardId;
591
654
 
592
655
  if (showDifferentLib) {
593
- const libId = this.viewConfig.liveboardId;
594
- this.navigateToLiveboard(libId);
656
+ console.log('showDifferentLib', this.currentLiveboardId);
657
+ const libId = this.currentLiveboardId;
658
+ this.navigateToLiveboard(libId, null, null, () => {
659
+ console.log('onNavigateCalled', libId);
660
+ embedObj.currentLiveboardId = libId;
661
+ });
595
662
  }
596
663
  }
597
664
 
@@ -622,6 +689,33 @@ export class LiveboardEmbed extends V1Embed {
622
689
  }
623
690
  return super.trigger(messageType, dataWithVizId);
624
691
  }
692
+ /**
693
+ * Destroys the ThoughtSpot embed, and remove any nodes from the DOM.
694
+ * @version SDK: 1.39.0 | ThoughtSpot: 10.10.0.cl
695
+ */
696
+ public destroy() {
697
+ super.destroy();
698
+ this.unregisterLazyLoadEvents();
699
+ }
700
+
701
+ private postRender() {
702
+ this.registerLazyLoadEvents();
703
+ }
704
+
705
+ private registerLazyLoadEvents() {
706
+ if (this.viewConfig.fullHeight && this.viewConfig.lazyLoadingForFullHeight) {
707
+ // TODO: Use passive: true, install modernizr to check for passive
708
+ window.addEventListener('resize', this.sendFullHeightLazyLoadData);
709
+ window.addEventListener('scroll', this.sendFullHeightLazyLoadData, true);
710
+ }
711
+ }
712
+
713
+ private unregisterLazyLoadEvents() {
714
+ if (this.viewConfig.fullHeight && this.viewConfig.lazyLoadingForFullHeight) {
715
+ window.removeEventListener('resize', this.sendFullHeightLazyLoadData);
716
+ window.removeEventListener('scroll', this.sendFullHeightLazyLoadData);
717
+ }
718
+ }
625
719
 
626
720
  /**
627
721
  * Render an embedded ThoughtSpot Liveboard or visualization
@@ -635,16 +729,20 @@ export class LiveboardEmbed extends V1Embed {
635
729
  await this.renderV1Embed(src);
636
730
  this.showPreviewLoader();
637
731
 
732
+ this.postRender();
638
733
  return this;
639
734
  }
640
735
 
641
- public navigateToLiveboard(liveboardId: string, vizId?: string, activeTabId?: string) {
736
+ public currentLiveboardId: string = this.viewConfig.liveboardId;
737
+
738
+ public navigateToLiveboard(liveboardId: string, vizId?: string, activeTabId?: string, onNavigateCalled?: () => void) {
642
739
  const path = this.getIframeSuffixSrc(liveboardId, vizId, activeTabId);
643
740
  this.viewConfig.liveboardId = liveboardId;
644
741
  this.viewConfig.activeTabId = activeTabId;
645
742
  this.viewConfig.vizId = vizId;
646
743
  if (this.isRendered) {
647
- this.trigger(HostEvent.Navigate, path.substring(1));
744
+ console.log('navigating to liveboard', path.substring(1));
745
+ this.triggerAfterLoad(HostEvent.Navigate, path.substring(1), onNavigateCalled);
648
746
  } else if (this.viewConfig.preRenderId) {
649
747
  this.preRender(true);
650
748
  } else {