kamrify commited on
Commit
bd90a81
·
1 Parent(s): 0c90a3d

Confirm on exit popup

Browse files
Files changed (4) hide show
  1. index.html +17 -3
  2. src/driver.ts +15 -6
  3. src/state.ts +3 -5
  4. src/style.css +2 -2
index.html CHANGED
@@ -201,6 +201,7 @@
201
  <button id="basic-tour">Animated Tour</button>
202
  <button id="non-animated-tour">Non-Animated Tour</button>
203
  <button id="async-tour">Asynchronous Tour</button>
 
204
  </div>
205
 
206
  <ul>
@@ -398,15 +399,28 @@ npm install driver.js</pre
398
  driverObj.drive();
399
  });
400
 
401
- document.getElementById("async-tour").addEventListener("click", () => {
402
  const driverObj = driver({
403
  animate: true,
 
404
  opacity: 0.3,
405
- onDestroyStarted: (element, step) => {
406
- if (confirm('Are you sure?')) {
 
 
 
407
  driverObj.destroy();
408
  }
409
  },
 
 
 
 
 
 
 
 
 
410
  steps: [
411
  {
412
  element: ".page-header",
 
201
  <button id="basic-tour">Animated Tour</button>
202
  <button id="non-animated-tour">Non-Animated Tour</button>
203
  <button id="async-tour">Asynchronous Tour</button>
204
+ <button id="confirm-exit-tour">Confirm on Exit</button>
205
  </div>
206
 
207
  <ul>
 
399
  driverObj.drive();
400
  });
401
 
402
+ document.getElementById("confirm-exit-tour").addEventListener("click", () => {
403
  const driverObj = driver({
404
  animate: true,
405
+ backdropColor: "green",
406
  opacity: 0.3,
407
+ steps: basicTourSteps,
408
+ onDestroyStarted: () => {
409
+ if (driverObj.hasNextStep() && confirm("Are you sure?")) {
410
+ driverObj.destroy();
411
+ } else {
412
  driverObj.destroy();
413
  }
414
  },
415
+ });
416
+
417
+ driverObj.drive();
418
+ });
419
+
420
+ document.getElementById("async-tour").addEventListener("click", () => {
421
+ const driverObj = driver({
422
+ animate: true,
423
+ opacity: 0.3,
424
  steps: [
425
  {
426
  element: ".page-header",
src/driver.ts CHANGED
@@ -145,16 +145,15 @@ export function driver(options: Config = {}) {
145
  });
146
  }
147
 
148
- function destroy(withStartHook = true) {
149
  const activeElement = getState("activeElement");
150
  const activeStep = getState("activeStep");
151
 
152
  const onDestroyStarted = getConfig("onDestroyStarted");
153
-
154
  // `onDestroyStarted` is used to confirm the exit of tour. If we trigger
155
  // the hook for when user calls `destroy`, driver will get into infinite loop
156
  // not causing tour to be destroyed.
157
- if (withStartHook && onDestroyStarted) {
158
  onDestroyStarted(activeElement, activeStep!);
159
  return;
160
  }
@@ -186,15 +185,25 @@ export function driver(options: Config = {}) {
186
 
187
  return {
188
  isActive: () => getState("isInitialized") || false,
189
- refresh: () => {
190
- requireRefresh();
191
- },
192
  drive: (stepIndex: number = 0) => {
193
  init();
194
  drive(stepIndex);
195
  },
196
  moveNext,
197
  movePrevious,
 
 
 
 
 
 
 
 
 
 
 
 
198
  highlight: (step: DriveStep) => {
199
  init();
200
  highlight({
 
145
  });
146
  }
147
 
148
+ function destroy(withOnDestroyStartedHook = true) {
149
  const activeElement = getState("activeElement");
150
  const activeStep = getState("activeStep");
151
 
152
  const onDestroyStarted = getConfig("onDestroyStarted");
 
153
  // `onDestroyStarted` is used to confirm the exit of tour. If we trigger
154
  // the hook for when user calls `destroy`, driver will get into infinite loop
155
  // not causing tour to be destroyed.
156
+ if (withOnDestroyStartedHook && onDestroyStarted) {
157
  onDestroyStarted(activeElement, activeStep!);
158
  return;
159
  }
 
185
 
186
  return {
187
  isActive: () => getState("isInitialized") || false,
188
+ refresh: requireRefresh,
 
 
189
  drive: (stepIndex: number = 0) => {
190
  init();
191
  drive(stepIndex);
192
  },
193
  moveNext,
194
  movePrevious,
195
+ hasNextStep: () => {
196
+ const steps = getConfig("steps") || [];
197
+ const activeIndex = getState("activeIndex");
198
+
199
+ return activeIndex !== undefined && steps[activeIndex + 1];
200
+ },
201
+ hasPreviousStep: () => {
202
+ const steps = getConfig("steps") || [];
203
+ const activeIndex = getState("activeIndex");
204
+
205
+ return activeIndex !== undefined && steps[activeIndex - 1];
206
+ },
207
  highlight: (step: DriveStep) => {
208
  init();
209
  highlight({
src/state.ts CHANGED
@@ -5,19 +5,17 @@ import { DriveStep } from "./driver";
5
  export type State = {
6
  // Whether driver is initialized or not
7
  isInitialized?: boolean;
8
- // Index of the currently active step in driver tour
9
- activeIndex?: number;
10
-
11
  // Used to bounce the resize event
12
  resizeTimeout?: number;
13
 
14
- // Used while transitioning between stages
15
  activeElement?: Element;
16
  activeStep?: DriveStep;
 
17
  previousElement?: Element;
18
  previousStep?: DriveStep;
19
- transitionCallback?: () => void;
20
 
 
21
 
22
  activeStagePosition?: StageDefinition;
23
  stageSvg?: SVGSVGElement;
 
5
  export type State = {
6
  // Whether driver is initialized or not
7
  isInitialized?: boolean;
 
 
 
8
  // Used to bounce the resize event
9
  resizeTimeout?: number;
10
 
11
+ activeIndex?: number;
12
  activeElement?: Element;
13
  activeStep?: DriveStep;
14
+
15
  previousElement?: Element;
16
  previousStep?: DriveStep;
 
17
 
18
+ transitionCallback?: () => void;
19
 
20
  activeStagePosition?: StageDefinition;
21
  stageSvg?: SVGSVGElement;
src/style.css CHANGED
@@ -24,11 +24,11 @@
24
  }
25
 
26
  .driver-fade .driver-stage {
27
- animation: animate-fade-in 100ms ease-in-out;
28
  }
29
 
30
  .driver-fade .driver-popover {
31
- animation: animate-fade-in 100ms;
32
  }
33
 
34
  /* Popover styles */
 
24
  }
25
 
26
  .driver-fade .driver-stage {
27
+ animation: animate-fade-in 300ms ease-in-out;
28
  }
29
 
30
  .driver-fade .driver-popover {
31
+ animation: animate-fade-in 300ms;
32
  }
33
 
34
  /* Popover styles */