config
unknown
typescript
3 years ago
4.4 kB
5
Indexable
import random from "lodash/random"; import { Vue3Instance } from "vue/types/v3-component-public-instance"; import { createDraftSteps } from "./scenarios/base"; import { experimentsSteps } from "./scenarios/experiments"; import { tasksSteps } from "./scenarios/tasks"; export enum Tutorials { "CreateDraft" = "CreateDraft", "Experiments" = "Eperiments", "Tasks" = "Tasks", } // @ts-ignore export const startTutorial = async (tutorial: Tutorials, context: Vue3Instance) => { let steps; context.activeTour = tutorial; context.tour = context?.$shepherd({ useModalOverlay: true, keyboardNavigation: false, exitOnEsc: true, stepsContainer: document.querySelector(".tutorial__wrapper"), modalContainer: document.querySelector(".tutorial__wrapper"), confirmCancel: true, confirmCancelMessage: "Are you sure you want to stop the tutorial?", defaultStepOptions: { classes: "shadow-md bg-purple-dark custom-step", cancelIcon: { enabled: true, }, popperOptions: { modifiers: [{ name: "offset", options: { offset: [0, 50] } }], }, }, }); context.buttonStart = { text: "Start tutorial", classes: "v-btn v-btn--is-elevated v-btn--has-bg theme--light v-size--default primary", action: await context.tour.next, }; context.buttonNext = { text: "Next", classes: "v-btn v-btn--is-elevated v-btn--has-bg theme--light v-size--default primary", action: context.tour.next, }; context.buttonFinish = { text: "Finish", classes: "v-btn v-btn--is-elevated v-btn--has-bg theme--light v-size--default primary", action: context.tour.complete, }; context.buttonNextTutorial = { text: "Next tutorial section", classes: "v-btn v-btn--is-elevated v-btn--has-bg theme--light v-size--default primary", action: () => { context.tour.complete(); switch (context.activeTour) { case "CreateDraft": startTutorial(Tutorials.Experiments, context); break; case "Experiments": startTutorial(Tutorials.Tasks, context); break; default: break; } }, }; switch (tutorial) { case Tutorials.CreateDraft: steps = await createDraftSteps(context); break; case Tutorials.Experiments: steps = await experimentsSteps(context); context.tour.randomSeed = random(); break; case Tutorials.Tasks: steps = await tasksSteps(context); break; default: break; } type Step = { when?: { show?: () => void; cancel?: () => void; complete?: () => void }; }; context.tour.on("start", () => { context.taskCreatorPersistent = true; }); ["cancel", "complete"].forEach((event) => { context.tour.on(event, () => { context.tour = undefined; context.activeTour = undefined; context.taskCreatorPersistent = false; }); }); steps?.forEach((step: Step) => { if (!step.when) { step.when = {}; } const showFunc = step.when.show; step.when.show = () => { addProgressToHeader(context.tour); if (showFunc) { showFunc(); } }; }); context.tour.addSteps(steps); context.tour.start(); }; // @ts-ignore function addProgressToHeader(tour: Shepherd.Tour) { const currentStepElement = tour.getCurrentStep().el; const header = currentStepElement.querySelector(".shepherd-header"); const progress = document.createElement("span"); progress.style.setProperty("margin-right", "315px"); progress.innerText = `${tour.steps.indexOf(tour.getCurrentStep()) + 1}/${tour.steps.length}`; header.insertBefore(progress, currentStepElement.querySelector(".shepherd-cancel-icon")); } export function findDrawflowNodeByName(regex: string | RegExp): Element | undefined { return Array.from(document.querySelectorAll("div.drawflow-node").values()).find( (e: Element) => e.textContent?.match(regex) ?? false ); } export function waitForElement( selector: string, callback: (el: Element) => void, condition?: (el: Element) => boolean, intervalMs = 500 ) { const interval = setInterval(() => { try { const element = document.querySelector(selector); if (element && (!condition || condition(element))) { callback(element); clearInterval(interval); return; } } catch { clearInterval(interval); } }, intervalMs); }
Editor is loading...