├── .gitignore
├── .npmrc
├── .npmignore
├── docs
├── img
│ └── bg.35638fd4.png
├── index.html
├── css
│ └── app.0349591b.css
└── js
│ ├── app.70244b16.js
│ ├── app.70244b16.js.map
│ └── chunk-vendors.ff04be39.js
├── rollup
└── rollup.prod.js
├── rollup.config.js
├── src
├── d.ts
├── utils.ts
└── smartour.ts
├── package.json
├── LICENSE
├── README.zh.md
├── README.md
└── dist
├── index.esm.js
└── index.js
/.gitignore:
--------------------------------------------------------------------------------
1 | node_modules/
2 |
--------------------------------------------------------------------------------
/.npmrc:
--------------------------------------------------------------------------------
1 | package-lock=false
--------------------------------------------------------------------------------
/.npmignore:
--------------------------------------------------------------------------------
1 | docs/
2 | node_modules/
3 | src/
4 | rollup.config.js
--------------------------------------------------------------------------------
/docs/img/bg.35638fd4.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jrainlau/smartour/HEAD/docs/img/bg.35638fd4.png
--------------------------------------------------------------------------------
/rollup/rollup.prod.js:
--------------------------------------------------------------------------------
1 | import typescript from 'rollup-plugin-typescript'
2 |
3 | export default {
4 | input: './src/smartour.ts',
5 | output: {
6 | file: './dist/index.js',
7 | name: 'Smartour',
8 | format: 'umd'
9 | },
10 | plugins: [
11 | typescript()
12 | ]
13 | }
14 |
--------------------------------------------------------------------------------
/rollup.config.js:
--------------------------------------------------------------------------------
1 | import typescript from 'rollup-plugin-typescript'
2 |
3 | export default {
4 | input: './src/smartour.ts',
5 | output: [{
6 | file: './dist/index.js',
7 | name: 'Smartour',
8 | format: 'umd'
9 | }, {
10 | file: './dist/index.esm.js',
11 | format: 'es'
12 | }],
13 | plugins: [
14 | typescript()
15 | ]
16 | }
17 |
--------------------------------------------------------------------------------
/src/d.ts:
--------------------------------------------------------------------------------
1 | export enum SlotPosition {
2 | TOP = 'top',
3 | BOTTOM = 'bottom',
4 | LEFT = 'left',
5 | RIGHT = 'right'
6 | }
7 |
8 | export interface Options {
9 | prefix?: string
10 | padding?: number
11 | maskColor?: string
12 | animate?: boolean
13 | slotPosition?: SlotPosition
14 | layerEvent?: EventListener
15 | }
16 |
17 | export interface HightlightElement {
18 | el: string
19 | slot: string
20 | options: Options
21 | keyNodes: Array
22 | }
23 |
24 | export interface KeyNode {
25 | el: string
26 | event: EventListener
27 | }
28 |
--------------------------------------------------------------------------------
/src/utils.ts:
--------------------------------------------------------------------------------
1 | export const maskStyle = (maskColor: string) => `
2 | position: absolute;
3 | border-radius: 4px;
4 | box-shadow: 0 0 0 9999px ${maskColor};
5 | z-index: 10001 !important;
6 | transition: all .3s;
7 | `
8 |
9 | export const slotStyle = () => `
10 | position: absolute;
11 | z-index: 10002 !important;
12 | transition: all .3s;
13 | `
14 |
15 | export const layerStyle = () => `
16 | position: fixed;
17 | top: 0;
18 | left: 0;
19 | right: 0;
20 | bottom: 0;
21 | z-index: 10000 !important;
22 | `
23 |
24 | export const noop = () => {}
25 |
26 | export const preventDefault = (e: Event) => e.preventDefault
27 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "smartour",
3 | "version": "2.0.0",
4 | "description": "Makes web page touring easier.",
5 | "main": "dist/index.js",
6 | "scripts": {
7 | "build": "rollup -c",
8 | "release": "standard-version"
9 | },
10 | "repository": {
11 | "type": "git",
12 | "url": "git+https://github.com/jrainlau/smartour.git"
13 | },
14 | "keywords": [],
15 | "author": "JRAIN LAU",
16 | "license": "MIT",
17 | "bugs": {
18 | "url": "https://github.com/jrainlau/smartour/issues"
19 | },
20 | "homepage": "https://github.com/jrainlau/smartour#readme",
21 | "devDependencies": {
22 | "rollup": "^1.16.3",
23 | "rollup-plugin-typescript": "^1.0.1",
24 | "standard-version": "^6.0.1",
25 | "tslib": "^1.10.0",
26 | "typescript": "^3.5.2"
27 | }
28 | }
29 |
--------------------------------------------------------------------------------
/docs/index.html:
--------------------------------------------------------------------------------
1 | Smartour | Docs
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2019 JrainLau
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.zh.md:
--------------------------------------------------------------------------------
1 | 在遇到网页内容有着较大调整的时候,往往需要一个导览功能去告诉用户,某某功能已经调整到另外一个位置。比较常规的办法是添加一个蒙层,高亮显示被调整的区域,然后通过文字介绍去完成引导。我们把这个功能称为“导览”,而 **Smartour** 则把这个导览的功能抽离出来,提供了一个开箱即用的解决方案。
2 |
3 |
4 | # Install
5 | **Smartour** 被构建成了 `umd` 和 `es module` 模块,允许用户通过不同的方式引入。
6 |
7 | ```
8 | npm install smartour
9 | ```
10 |
11 | ```
12 | /* ES Modules */
13 | import Smartour from 'smartour/dist/index.esm.js'
14 | /* CommandJS */
15 | const Smartour = require('smartour')
16 | /*
18 | ```
19 |
20 | # 基本用法
21 |
22 | **Smartour** 提供了一个非常简单的 API `focus()`, 这是高亮一个元素最简单的方式。
23 |
24 | ```javascript
25 | let tour = new Smartour()
26 |
27 | tour.focus({
28 | el: '#basic-usage'
29 | })
30 | ```
31 |
32 | # 插槽 Slot
33 |
34 | 插槽 `slot` 是用于为高亮元素提供描述的 html 字符串。
35 |
36 | ## 纯字符串:
37 | ```javascript
38 | let tour = new Smartour()
39 |
40 | tour.focus({
41 | el: '#pure-string',
42 | slot: 'This is a pure string'
43 | })
44 | ```
45 |
46 | ## Html 字符串
47 | ```javascript
48 | let tour = new Smartour()
49 |
50 | tour.focus({
51 | el: '#html-string',
52 | slot: `
53 |
54 |
This is a html string
55 |
56 | `
57 | })
58 | ```
59 |
60 | ## 插槽位置
61 |
62 | 插槽的位置可以选择4个不同的方向: `top`, `right`, `left`, `bottom`.
63 |
64 | 设置 `options.slotPosition` 属性即可覆盖默认的 `top` 位置。
65 |
66 | ```javascript
67 | let tour = new Smartour()
68 |
69 | tour.focus({
70 | el: '#slot-positions',
71 | slot: `top`,
72 | options: {
73 | slotPosition: 'top' // 默认为 `top`
74 | }
75 | })
76 | ```buttonslot-bottom">Bottom
77 |
78 | ## 插槽事件
79 | 插槽所定义的元素也可以绑定事件。我们通过 `keyNodes` 属性来为插槽元素绑定事件。
80 |
81 | `keyNodes` 是内容为一系列 `keyNode` 的数组。 属性 `keyNode.el` 是一个 css 选择器,而 `keyNode.event` 属性则是对应元素所绑定的事件。
82 |
83 | ```javascript
84 | let tour = new Smartour()
85 |
86 | tour.focus({
87 | el: '.slot-events-demo',
88 | options: {
89 | slotPosition: 'right'
90 | },
91 | slot: `
92 |
93 | Click here to occur an alert event
94 |
95 |
96 | Click here to occur an alert event
97 |
98 | `,
99 | keyNodes: [{
100 | el: '.occur-1',
101 | event: () => { alert('Event!!') }
102 | }, {
103 | el: '.occur-2',
104 | event: () => { alert('Another event!!') }
105 | }]
106 | })
107 | ```
108 |
109 | # Queue
110 | 有的时候页面需要不止一个导览。**Smartour** 允许你把一系列的导览通过 `.queue()` 放在一起,然后挨个挨个地展示它们。
111 |
112 | 举个例子:
113 |
114 | ```javascript
115 | let tour = new Smartour()
116 |
117 | tour
118 | .queue([{
119 | el: '.li-1',
120 | options: {
121 | layerEvent: tour.next.bind(tour)
122 | },
123 | slot: 'This is the 1st line.'
124 | }, {
125 | el: '.li-2',
126 | options: {
127 | layerEvent: tour.next.bind(tour)
128 | },
129 | slot: 'This is the 2nd line.'
130 | }, {
131 | el: '.li-3',
132 | options: {
133 | layerEvent: tour.next.bind(tour)
134 | },
135 | slot: 'This is the 3rd line.'
136 | }])
137 | .run() // 别忘了调用 `run()` 方法去展示第一个导览
138 | ```
139 |
140 | # 选项
141 | **Smartour** 是一个构建函数,它接收一个 `options` 参数去覆盖其默认选项
142 |
143 | 让我们看看它的默认选项是什么样子的:
144 |
145 | ```javascript
146 | {
147 | prefix: 'smartour', // class 前缀
148 | padding: 5, // 高亮区域内边距
149 | maskColor: 'rgba(0, 0, 0, .5)', // 带透明值的遮罩层颜色
150 | animate: true, // 是否使用动画
151 | slotPosition: 'top' // 默认的插槽位置
152 | layerEvent: smartour.over // 遮罩层点击事件,默认为结束导览
153 | }
154 | ```
155 |
156 | # APIs
157 | 除了 `.focus()`,`.queue()` 和 `.run()` API 以外,**Smartour** 还提供了另外三个 API 专门用于控制导览的展示。
158 |
159 | - `.next()`:展示下一个导览(只能配合 `.queue()` 使用)。
160 |
161 | - `.prev()`:展示上一个导览(只能配合 `.queue()` 使用)。
162 |
163 | - `.over()`:结束全部导览。
164 |
165 | # Smartour 的原理
166 |
167 | **Smartour** 通过 `element.getBoundingClientRect()` api 来获取目标元素的宽高和位置信息,然后放置一个带着 `box-shadow` 样式的元素在其之上作为高亮区域。
168 |
169 | 由于点击事件无法再 `box-shadow` 的区域里触发,所以 **Smartour** 还放置了一个全屏透明的遮罩层用于绑定 `layerEvent` 事件。
170 |
171 | 高亮区域和插槽都被设置为 `absolute`。当页面滚动时,`document.documentElement.scrollTop` 或者 `document.documentElement.scrollLeft` 的值就会变化,然后 **Smartour** 会实时修正它的位置信息。
172 |
173 | # 证书
174 | MIT
--------------------------------------------------------------------------------
/docs/css/app.0349591b.css:
--------------------------------------------------------------------------------
1 | .intro[data-v-4cefd0c2]{position:relative;display:-webkit-box;display:-ms-flexbox;display:flex;-webkit-box-orient:vertical;-webkit-box-direction:normal;-ms-flex-direction:column;flex-direction:column;-webkit-box-pack:center;-ms-flex-pack:center;justify-content:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;background:url(../img/bg.35638fd4.png);background-size:100% 100%;color:#fff;text-shadow:0 0 10px #000}.intro h1[data-v-4cefd0c2]{font-size:4rem;border:none}.intro h3[data-v-4cefd0c2]{font-size:1.3rem}.intro h2[data-v-4cefd0c2]{position:absolute;left:50%;bottom:15px;-webkit-animation:jumping-data-v-4cefd0c2 .8s linear infinite alternate;animation:jumping-data-v-4cefd0c2 .8s linear infinite alternate}@-webkit-keyframes jumping-data-v-4cefd0c2{0%{-webkit-transform:translateX(-50%) translateY(-5px);transform:translateX(-50%) translateY(-5px)}to{-webkit-transform:translateX(-50%) translateY(5px);transform:translateX(-50%) translateY(5px)}}@keyframes jumping-data-v-4cefd0c2{0%{-webkit-transform:translateX(-50%) translateY(-5px);transform:translateX(-50%) translateY(-5px)}to{-webkit-transform:translateX(-50%) translateY(5px);transform:translateX(-50%) translateY(5px)}}.usage-content[data-v-190bd07d]{width:100%;max-width:960px}.footer[data-v-6091108d]{padding:10px 0;background:url(../img/bg.35638fd4.png);background-size:100% 100%}.footer p[data-v-6091108d]{color:#fff;margin:0;text-align:center;text-shadow:0 0 10px #000}.footer p a[data-v-6091108d]{color:#fff}*{-webkit-box-sizing:border-box;box-sizing:border-box;font-family:Helvetica Neue,Helvetica,PingFang SC,Hiragino Sans GB,Microsoft YaHei,SimSun,sans-serif;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}body,html{margin:0;padding:0;font-size:14px}.view{height:100vh;width:100vw;overflow:hidden}.usage{padding:15px;display:-webkit-box;display:-ms-flexbox;display:flex;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-box-orient:vertical;-webkit-box-direction:normal;-ms-flex-direction:column;flex-direction:column}.demo-btn{-webkit-appearance:none;-moz-appearance:none;appearance:none;display:inline-block;border:1px solid #8e24aa;padding:5px 10px;outline:none;color:#8e24aa;-webkit-transition:.1s;transition:.1s;background:#fff;min-width:60px;margin-right:15px}.demo-btn:hover{background:#8e24aa;border-color:#8e24aa;color:#fff}.demo-btn:active{background:#5c007a;border-color:#5c007a;color:#fff}.hljs{font-family:monospace}.smartour-slot{position:relative;background:#fff;padding:5px;border-radius:4px;font-size:1rem}.smartour-slot_top{-webkit-transform:translateY(-10px);transform:translateY(-10px)}.smartour-slot_top:after{content:"";position:absolute;bottom:-5px;left:50%;-webkit-transform:translateX(-50%);transform:translateX(-50%);border-left:5px solid transparent;border-right:5px solid transparent;border-top:5px solid #fff}.smartour-slot_bottom{-webkit-transform:translateY(10px);transform:translateY(10px)}.smartour-slot_bottom:after{content:"";position:absolute;top:-5px;left:50%;-webkit-transform:translateX(-50%);transform:translateX(-50%);border-left:5px solid transparent;border-right:5px solid transparent;border-bottom:5px solid #fff}.smartour-slot_right{-webkit-transform:translateX(10px);transform:translateX(10px)}.smartour-slot_right:after{content:"";position:absolute;left:-5px;top:50%;-webkit-transform:translateY(-50%);transform:translateY(-50%);border-bottom:5px solid transparent;border-right:5px solid #fff;border-top:5px solid transparent}.smartour-slot_left{-webkit-transform:translateX(-10px);transform:translateX(-10px)}.smartour-slot_left:after{content:"";position:absolute;right:-5px;top:50%;-webkit-transform:translateY(-50%);transform:translateY(-50%);border-bottom:5px solid transparent;border-left:5px solid #fff;border-top:5px solid transparent}table{border-right:1px solid #ccc;border-bottom:1px solid #ccc;margin:10px}table td,table th{padding:5px 10px;border-left:1px solid #ccc;border-top:1px solid #ccc}h1{margin:0;padding:10px 0;font-size:2rem;border:none;border-bottom:1px solid #ccc}h1,h2{font-weight:400}h2{font-size:1.5rem}code{padding:2px 4px;font-size:90%;font-family:monospace;color:#c7254e;background-color:#f9f2f4;border-radius:4px}pre{display:block;margin:0 0 10px;font-size:13px;font-family:inherit;line-height:1.42857143;color:#333;word-break:break-all;word-wrap:break-word;border:1px solid #ccc;border-radius:4px}pre code{padding:0;font-size:inherit;color:inherit;white-space:pre-wrap;background-color:transparent;border-radius:0}blockquote{padding:10px 20px;margin:0 0 20px;font-size:17.5px;border-left:5px solid #ccc}blockquote p{margin:0}a{color:#009688}li{margin-bottom:10px}hr{margin-top:20px;margin-bottom:20px;border:0;border-top:1px solid #ccc}ul{padding-left:15px}
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Smartour
2 |
3 | 
4 |
5 | Once a website has changed its UI, usually they would set a list of tour guide to tell the visitors, that some modules were moved to the other places. We named it as "tour guide", and Smartour is a solution for making tour guide much easier.
6 |
7 | See live demo here: https://jrainlau.github.io/smartour
8 |
9 | [中文文档](https://github.com/jrainlau/smartour/blob/master/README.zh.md)
10 |
11 | # Install
12 | **Smartour** was built to an `umd` and `es modules` package.
13 |
14 | ```
15 | npm install smartour
16 | ```
17 |
18 | ```
19 | /* ES Modules */
20 | import Smartour from 'smartour/dist/index.esm.js'
21 | /* CommandJS */
22 | const Smartour = require('smartour')
23 | /*
25 | ```
26 |
27 | # Basic usage
28 |
29 | **Smartour** provides a very simple API `focus()`, it's the easist way to highlight an element.
30 |
31 | ```javascript
32 | let tour = new Smartour()
33 |
34 | tour.focus({
35 | el: '#basic-usage'
36 | })
37 | ```
38 |
39 | # Slot
40 |
41 | `slot` is a html string that allows you to add a description to the highlighted element.
42 |
43 | ## Pure string:
44 | ```javascript
45 | let tour = new Smartour()
46 |
47 | tour.focus({
48 | el: '#pure-string',
49 | slot: 'This is a pure string'
50 | })
51 | ```
52 |
53 | ## Html string
54 | ```javascript
55 | let tour = new Smartour()
56 |
57 | tour.focus({
58 | el: '#html-string',
59 | slot: `
60 |
61 |
This is a html string
62 |
63 | `
64 | })
65 | ```
66 |
67 | ## Slot positions
68 |
69 | There are 4 positions to place a slot: `top`, `right`, `left`, `bottom`.
70 |
71 | Set the `options.slotPosition` attribute to overwrite the default `top`.
72 |
73 | ```javascript
74 | let tour = new Smartour()
75 |
76 | tour.focus({
77 | el: '#slot-positions',
78 | slot: `top`,
79 | options: {
80 | slotPosition: 'top' // default is `top`
81 | }
82 | })
83 | ```
84 |
85 | ## Slot events
86 | The slot element could bind events, too. We can use the `keyNodes` attribute to bind events to them.
87 |
88 | `keyNodes` is an array contains with `keyNode`. The attribute `keyNode.el` is a css selector, and the other `keyNode.event` is the binding event.
89 |
90 | ```javascript
91 | let tour = new Smartour()
92 |
93 | tour.focus({
94 | el: '.slot-events-demo',
95 | options: {
96 | slotPosition: 'right'
97 | },
98 | slot: `
99 |
102 |
105 | `,
106 | keyNodes: [{
107 | el: '.occur-1',
108 | event: () => { alert('Event!!') }
109 | }, {
110 | el: '.occur-2',
111 | event: () => { alert('Another event!!') }
112 | }]
113 | })
114 | ```
115 |
116 | # Queue
117 | Sometimes there are more than one tour guide to show. **Smartour** allows you to put the tour guides together as a queue and show them one by one.
118 |
119 | ```javascript
120 | let tour = new Smartour()
121 |
122 | tour
123 | .queue([{
124 | el: '.li-1',
125 | options: {
126 | layerEvent: tour.next.bind(tour)
127 | },
128 | slot: 'This is the 1st line.'
129 | }, {
130 | el: '.li-2',
131 | options: {
132 | layerEvent: tour.next.bind(tour)
133 | },
134 | slot: 'This is the 2nd line.'
135 | }, {
136 | el: '.li-3',
137 | options: {
138 | layerEvent: tour.next.bind(tour)
139 | },
140 | slot: 'This is the 3rd line.'
141 | }])
142 | .run() // don't forget to trigger api `run()` to show the first tour guide
143 | ```
144 |
145 | # Options
146 | **Smartour** is a constructor and receives an `options` parameter to overwrite the default.
147 |
148 | Let's take a look at the default options:
149 |
150 | ```javascript
151 | {
152 | prefix: 'smartour', // class prefix
153 | padding: 5, // padding of the highlight area
154 | maskColor: 'rgba(0, 0, 0, .5)', // maskColor with alpha
155 | animate: true, // use animate while changing tour guides
156 | slotPosition: 'top' // default slot position
157 | layerEvent: smartour.over // events while clicking the layer
158 | }
159 | ```
160 |
161 | # APIs
162 | Besides `.focus()`, `.queue()` and `.run()`, **Smartour** alse privides two apis to handle the tour guide playing.
163 |
164 | - `.next()`: Show the next tour guide. (Only work with `.queue()`)
165 |
166 | - `.prev()`: Show the previous tour guide. (Only work with `.queue()`)
167 |
168 | # Principles of Smartour
169 |
170 | **Smartour** uses api `element.getBoundingClientRect()` to detect the size and position of the target element, than place a rect element with `box-shadow` over it as the highlight area.
171 |
172 | Because click events could not be triigered from the `box-shadow` area, **Smartour** place another transparent layer over the page, and bind `layerEvent()` to it to solve this problem.
173 |
174 | The position of the highlight area and slot are `absolute`. Every time the page scrolled, the value of `document.documentElement.scrollTop` or `document.documentElement.scrollLeft` would be changed, and **Smartour** will use these values to correct the position.
175 |
176 | # License
177 | MIT
178 |
--------------------------------------------------------------------------------
/src/smartour.ts:
--------------------------------------------------------------------------------
1 | import {
2 | SlotPosition,
3 | Options,
4 | HightlightElement,
5 | KeyNode
6 | } from './d'
7 |
8 | import {
9 | maskStyle,
10 | slotStyle,
11 | layerStyle
12 | } from './utils'
13 |
14 | const defaultOptions: Options = {
15 | prefix: 'smartour',
16 | padding: 5,
17 | maskColor: 'rgba(0, 0, 0, .5)',
18 | animate: true,
19 | slotPosition: SlotPosition.TOP
20 | }
21 |
22 | export default class Smartour {
23 | options: Options
24 | mask: HTMLElement
25 | slot: HTMLElement
26 | layer: HTMLElement
27 | tourList: Array
28 | tourListLength: number
29 | tourIndex: number
30 |
31 | constructor (options: Options = {}) {
32 | this.options = {
33 | ...defaultOptions,
34 | layerEvent: this.over.bind(this),
35 | ...options
36 | }
37 |
38 | this.mask = null
39 | this.slot = null
40 | this.layer = null
41 | }
42 |
43 | private _createMask () {
44 | if (!this.mask) {
45 | this.mask = document.createElement('div')
46 | this.mask.setAttribute('class', this.options.prefix + '-mask')
47 | this.mask.setAttribute('style', maskStyle(this.options.maskColor))
48 | document.body.appendChild(this.mask)
49 | }
50 | }
51 |
52 | private _createSlot (html: string) {
53 | if (!this.slot) {
54 | this.slot = document.createElement('div')
55 | this.slot.setAttribute('style', slotStyle())
56 | document.body.appendChild(this.slot)
57 | }
58 | this.slot.setAttribute('class', `${this.options.prefix}-slot ${this.options.prefix}-slot_${this.options.slotPosition}`)
59 | this.slot.innerHTML = html
60 | }
61 |
62 | private _createLayer () {
63 | if (!this.layer) {
64 | this.layer = document.createElement('div')
65 | this.layer.setAttribute('class', this.options.prefix + '-layer')
66 | this.layer.setAttribute('style', layerStyle())
67 | this.layer.addEventListener('click', this.options.layerEvent)
68 | document.body.appendChild(this.layer)
69 | }
70 | }
71 |
72 | private _setPosition (el: HTMLElement, attrs: Array) {
73 | ;['top', 'left', 'width', 'height'].forEach((attr, index) => {
74 | if (attrs[index]) {
75 | if (attr === 'top' || attr === 'left') {
76 | const scrollDirection = `scroll${attr.charAt(0).toUpperCase() + attr.slice(1)}`
77 | let scrollDistance = 0
78 | if (document.documentElement && document.documentElement[scrollDirection]) {
79 | scrollDistance = document.documentElement[scrollDirection]
80 | } else {
81 | scrollDistance = document.body[scrollDirection]
82 | }
83 | el.style[attr] = attrs[index] + scrollDistance + 'px'
84 | } else {
85 | el.style[attr] = attrs[index] + 'px'
86 | }
87 | }
88 | })
89 | }
90 |
91 | private _show (targetSelector: string, slotHtml: string = '', keyNodes: Array = []) {
92 | this._createMask()
93 | this._createSlot(slotHtml)
94 | this._createLayer()
95 |
96 | if (!this.options.animate) {
97 | this.mask.style.transition = null
98 | this.slot.style.transition = null
99 | }
100 |
101 | const target = document.querySelector(targetSelector)
102 | const { top, left, width, height } = target.getBoundingClientRect()
103 | const [maskTop, maskLeft, maskWidth, maskHeight] = [top - this.options.padding, left - this.options.padding, width + 2 * this.options.padding, height + 2 * this.options.padding]
104 |
105 | this._setPosition(this.mask, [maskTop, maskLeft, maskWidth, maskHeight])
106 |
107 | const { width: slotWidth, height: slotHeight } = this.slot.getBoundingClientRect()
108 | const { slotPosition } = this.options
109 | let [slotTop, slotLeft] = [0, 0]
110 |
111 | if (slotPosition === SlotPosition.TOP) {
112 | [slotTop, slotLeft] = [maskTop - slotHeight, maskLeft + maskWidth / 2 - slotWidth / 2]
113 | } else if (slotPosition === SlotPosition.BOTTOM) {
114 | [slotTop, slotLeft] = [maskTop + maskHeight, maskLeft + maskWidth / 2 - slotWidth / 2]
115 | } else if (slotPosition === SlotPosition.LEFT) {
116 | [slotTop, slotLeft] = [maskTop - (slotHeight - maskHeight) / 2, maskLeft - slotWidth]
117 | } else if (slotPosition === SlotPosition.RIGHT) {
118 | [slotTop, slotLeft] = [maskTop - (slotHeight - maskHeight) / 2, maskLeft + maskWidth]
119 | }
120 |
121 | this._setPosition(this.slot, [slotTop, slotLeft])
122 | if (!slotHtml) {
123 | document.body.removeChild(this.slot)
124 | this.slot = null
125 | }
126 |
127 | if (keyNodes.length) {
128 | keyNodes.forEach(({ el, event }) => {
129 | document.querySelector(el).addEventListener('click', event)
130 | })
131 | }
132 | }
133 |
134 | focus (highlightElement: HightlightElement = { el: '', slot: '', keyNodes: [], options: {} }) {
135 | if (highlightElement.options && Object.keys(highlightElement.options).length) {
136 | this.options = { ...this.options, ...highlightElement.options }
137 | }
138 | this._show(highlightElement.el, highlightElement.slot, highlightElement.keyNodes)
139 | }
140 |
141 | queue (tourList: Array) {
142 | this.tourList = tourList
143 | this.tourListLength = tourList.length
144 | this.tourIndex = -1
145 |
146 | return this
147 | }
148 |
149 | run (isNext: boolean = true) {
150 | if (this.tourListLength && this.tourIndex < this.tourListLength - 1) {
151 | isNext ? this.tourIndex++ : this.tourIndex--
152 | const tour = this.tourList[this.tourIndex]
153 | if (tour.options) {
154 | this.options = { ...this.options, ...tour.options }
155 | }
156 | this._show(tour.el, tour.slot, tour.keyNodes)
157 | } else {
158 | this.over()
159 | }
160 | }
161 |
162 | next () {
163 | this.run(true)
164 | }
165 |
166 | prev () {
167 | this.run(false)
168 | }
169 |
170 | over () {
171 | this.mask && document.body.removeChild(this.mask)
172 | this.slot && document.body.removeChild(this.slot)
173 | this.layer && document.body.removeChild(this.layer)
174 |
175 | ;['mask', 'slot', 'layer'].forEach(attr => {
176 | this[attr] = null
177 | })
178 | }
179 | }
180 |
--------------------------------------------------------------------------------
/dist/index.esm.js:
--------------------------------------------------------------------------------
1 | /*! *****************************************************************************
2 | Copyright (c) Microsoft Corporation. All rights reserved.
3 | Licensed under the Apache License, Version 2.0 (the "License"); you may not use
4 | this file except in compliance with the License. You may obtain a copy of the
5 | License at http://www.apache.org/licenses/LICENSE-2.0
6 |
7 | THIS CODE IS PROVIDED ON AN *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
8 | KIND, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION ANY IMPLIED
9 | WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE,
10 | MERCHANTABLITY OR NON-INFRINGEMENT.
11 |
12 | See the Apache Version 2.0 License for specific language governing permissions
13 | and limitations under the License.
14 | ***************************************************************************** */
15 |
16 | var __assign = function() {
17 | __assign = Object.assign || function __assign(t) {
18 | for (var s, i = 1, n = arguments.length; i < n; i++) {
19 | s = arguments[i];
20 | for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p];
21 | }
22 | return t;
23 | };
24 | return __assign.apply(this, arguments);
25 | };
26 |
27 | var SlotPosition;
28 | (function (SlotPosition) {
29 | SlotPosition["TOP"] = "top";
30 | SlotPosition["BOTTOM"] = "bottom";
31 | SlotPosition["LEFT"] = "left";
32 | SlotPosition["RIGHT"] = "right";
33 | })(SlotPosition || (SlotPosition = {}));
34 |
35 | var maskStyle = function (maskColor) { return "\nposition: absolute;\nborder-radius: 4px;\nbox-shadow: 0 0 0 9999px " + maskColor + ";\nz-index: 10001 !important;\ntransition: all .3s;\n"; };
36 | var slotStyle = function () { return "\nposition: absolute;\nz-index: 10002 !important;\ntransition: all .3s;\n"; };
37 | var layerStyle = function () { return "\nposition: fixed;\ntop: 0;\nleft: 0;\nright: 0;\nbottom: 0;\nz-index: 10000 !important;\n"; };
38 |
39 | var defaultOptions = {
40 | prefix: 'smartour',
41 | padding: 5,
42 | maskColor: 'rgba(0, 0, 0, .5)',
43 | animate: true,
44 | slotPosition: SlotPosition.TOP
45 | };
46 | var Smartour = /** @class */ (function () {
47 | function Smartour(options) {
48 | if (options === void 0) { options = {}; }
49 | this.options = __assign({}, defaultOptions, { layerEvent: this.over.bind(this) }, options);
50 | this.mask = null;
51 | this.slot = null;
52 | this.layer = null;
53 | }
54 | Smartour.prototype._createMask = function () {
55 | if (!this.mask) {
56 | this.mask = document.createElement('div');
57 | this.mask.setAttribute('class', this.options.prefix + '-mask');
58 | this.mask.setAttribute('style', maskStyle(this.options.maskColor));
59 | document.body.appendChild(this.mask);
60 | }
61 | };
62 | Smartour.prototype._createSlot = function (html) {
63 | if (!this.slot) {
64 | this.slot = document.createElement('div');
65 | this.slot.setAttribute('style', slotStyle());
66 | document.body.appendChild(this.slot);
67 | }
68 | this.slot.setAttribute('class', this.options.prefix + "-slot " + this.options.prefix + "-slot_" + this.options.slotPosition);
69 | this.slot.innerHTML = html;
70 | };
71 | Smartour.prototype._createLayer = function () {
72 | if (!this.layer) {
73 | this.layer = document.createElement('div');
74 | this.layer.setAttribute('class', this.options.prefix + '-layer');
75 | this.layer.setAttribute('style', layerStyle());
76 | this.layer.addEventListener('click', this.options.layerEvent);
77 | document.body.appendChild(this.layer);
78 | }
79 | };
80 | Smartour.prototype._setPosition = function (el, attrs) {
81 | ['top', 'left', 'width', 'height'].forEach(function (attr, index) {
82 | if (attrs[index]) {
83 | if (attr === 'top' || attr === 'left') {
84 | var scrollDirection = "scroll" + (attr.charAt(0).toUpperCase() + attr.slice(1));
85 | var scrollDistance = 0;
86 | if (document.documentElement && document.documentElement[scrollDirection]) {
87 | scrollDistance = document.documentElement[scrollDirection];
88 | }
89 | else {
90 | scrollDistance = document.body[scrollDirection];
91 | }
92 | el.style[attr] = attrs[index] + scrollDistance + 'px';
93 | }
94 | else {
95 | el.style[attr] = attrs[index] + 'px';
96 | }
97 | }
98 | });
99 | };
100 | Smartour.prototype._show = function (targetSelector, slotHtml, keyNodes) {
101 | var _a, _b, _c, _d;
102 | if (slotHtml === void 0) { slotHtml = ''; }
103 | if (keyNodes === void 0) { keyNodes = []; }
104 | this._createMask();
105 | this._createSlot(slotHtml);
106 | this._createLayer();
107 | if (!this.options.animate) {
108 | this.mask.style.transition = null;
109 | this.slot.style.transition = null;
110 | }
111 | var target = document.querySelector(targetSelector);
112 | var _e = target.getBoundingClientRect(), top = _e.top, left = _e.left, width = _e.width, height = _e.height;
113 | var _f = [top - this.options.padding, left - this.options.padding, width + 2 * this.options.padding, height + 2 * this.options.padding], maskTop = _f[0], maskLeft = _f[1], maskWidth = _f[2], maskHeight = _f[3];
114 | this._setPosition(this.mask, [maskTop, maskLeft, maskWidth, maskHeight]);
115 | var _g = this.slot.getBoundingClientRect(), slotWidth = _g.width, slotHeight = _g.height;
116 | var slotPosition = this.options.slotPosition;
117 | var _h = [0, 0], slotTop = _h[0], slotLeft = _h[1];
118 | if (slotPosition === SlotPosition.TOP) {
119 | _a = [maskTop - slotHeight, maskLeft + maskWidth / 2 - slotWidth / 2], slotTop = _a[0], slotLeft = _a[1];
120 | }
121 | else if (slotPosition === SlotPosition.BOTTOM) {
122 | _b = [maskTop + maskHeight, maskLeft + maskWidth / 2 - slotWidth / 2], slotTop = _b[0], slotLeft = _b[1];
123 | }
124 | else if (slotPosition === SlotPosition.LEFT) {
125 | _c = [maskTop - (slotHeight - maskHeight) / 2, maskLeft - slotWidth], slotTop = _c[0], slotLeft = _c[1];
126 | }
127 | else if (slotPosition === SlotPosition.RIGHT) {
128 | _d = [maskTop - (slotHeight - maskHeight) / 2, maskLeft + maskWidth], slotTop = _d[0], slotLeft = _d[1];
129 | }
130 | this._setPosition(this.slot, [slotTop, slotLeft]);
131 | if (!slotHtml) {
132 | document.body.removeChild(this.slot);
133 | this.slot = null;
134 | }
135 | if (keyNodes.length) {
136 | keyNodes.forEach(function (_a) {
137 | var el = _a.el, event = _a.event;
138 | document.querySelector(el).addEventListener('click', event);
139 | });
140 | }
141 | };
142 | Smartour.prototype.focus = function (highlightElement) {
143 | if (highlightElement === void 0) { highlightElement = { el: '', slot: '', keyNodes: [], options: {} }; }
144 | if (highlightElement.options && Object.keys(highlightElement.options).length) {
145 | this.options = __assign({}, this.options, highlightElement.options);
146 | }
147 | this._show(highlightElement.el, highlightElement.slot, highlightElement.keyNodes);
148 | };
149 | Smartour.prototype.queue = function (tourList) {
150 | this.tourList = tourList;
151 | this.tourListLength = tourList.length;
152 | this.tourIndex = -1;
153 | return this;
154 | };
155 | Smartour.prototype.run = function (isNext) {
156 | if (isNext === void 0) { isNext = true; }
157 | if (this.tourListLength && this.tourIndex < this.tourListLength - 1) {
158 | isNext ? this.tourIndex++ : this.tourIndex--;
159 | var tour = this.tourList[this.tourIndex];
160 | if (tour.options) {
161 | this.options = __assign({}, this.options, tour.options);
162 | }
163 | this._show(tour.el, tour.slot, tour.keyNodes);
164 | }
165 | else {
166 | this.over();
167 | }
168 | };
169 | Smartour.prototype.next = function () {
170 | this.run(true);
171 | };
172 | Smartour.prototype.prev = function () {
173 | this.run(false);
174 | };
175 | Smartour.prototype.over = function () {
176 | var _this = this;
177 | this.mask && document.body.removeChild(this.mask);
178 | this.slot && document.body.removeChild(this.slot);
179 | this.layer && document.body.removeChild(this.layer);
180 | ['mask', 'slot', 'layer'].forEach(function (attr) {
181 | _this[attr] = null;
182 | });
183 | };
184 | return Smartour;
185 | }());
186 |
187 | export default Smartour;
188 |
--------------------------------------------------------------------------------
/dist/index.js:
--------------------------------------------------------------------------------
1 | (function (global, factory) {
2 | typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
3 | typeof define === 'function' && define.amd ? define(factory) :
4 | (global = global || self, global.Smartour = factory());
5 | }(this, function () { 'use strict';
6 |
7 | /*! *****************************************************************************
8 | Copyright (c) Microsoft Corporation. All rights reserved.
9 | Licensed under the Apache License, Version 2.0 (the "License"); you may not use
10 | this file except in compliance with the License. You may obtain a copy of the
11 | License at http://www.apache.org/licenses/LICENSE-2.0
12 |
13 | THIS CODE IS PROVIDED ON AN *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14 | KIND, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION ANY IMPLIED
15 | WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE,
16 | MERCHANTABLITY OR NON-INFRINGEMENT.
17 |
18 | See the Apache Version 2.0 License for specific language governing permissions
19 | and limitations under the License.
20 | ***************************************************************************** */
21 |
22 | var __assign = function() {
23 | __assign = Object.assign || function __assign(t) {
24 | for (var s, i = 1, n = arguments.length; i < n; i++) {
25 | s = arguments[i];
26 | for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p];
27 | }
28 | return t;
29 | };
30 | return __assign.apply(this, arguments);
31 | };
32 |
33 | var SlotPosition;
34 | (function (SlotPosition) {
35 | SlotPosition["TOP"] = "top";
36 | SlotPosition["BOTTOM"] = "bottom";
37 | SlotPosition["LEFT"] = "left";
38 | SlotPosition["RIGHT"] = "right";
39 | })(SlotPosition || (SlotPosition = {}));
40 |
41 | var maskStyle = function (maskColor) { return "\nposition: absolute;\nborder-radius: 4px;\nbox-shadow: 0 0 0 9999px " + maskColor + ";\nz-index: 10001 !important;\ntransition: all .3s;\n"; };
42 | var slotStyle = function () { return "\nposition: absolute;\nz-index: 10002 !important;\ntransition: all .3s;\n"; };
43 | var layerStyle = function () { return "\nposition: fixed;\ntop: 0;\nleft: 0;\nright: 0;\nbottom: 0;\nz-index: 10000 !important;\n"; };
44 |
45 | var defaultOptions = {
46 | prefix: 'smartour',
47 | padding: 5,
48 | maskColor: 'rgba(0, 0, 0, .5)',
49 | animate: true,
50 | slotPosition: SlotPosition.TOP
51 | };
52 | var Smartour = /** @class */ (function () {
53 | function Smartour(options) {
54 | if (options === void 0) { options = {}; }
55 | this.options = __assign({}, defaultOptions, { layerEvent: this.over.bind(this) }, options);
56 | this.mask = null;
57 | this.slot = null;
58 | this.layer = null;
59 | }
60 | Smartour.prototype._createMask = function () {
61 | if (!this.mask) {
62 | this.mask = document.createElement('div');
63 | this.mask.setAttribute('class', this.options.prefix + '-mask');
64 | this.mask.setAttribute('style', maskStyle(this.options.maskColor));
65 | document.body.appendChild(this.mask);
66 | }
67 | };
68 | Smartour.prototype._createSlot = function (html) {
69 | if (!this.slot) {
70 | this.slot = document.createElement('div');
71 | this.slot.setAttribute('style', slotStyle());
72 | document.body.appendChild(this.slot);
73 | }
74 | this.slot.setAttribute('class', this.options.prefix + "-slot " + this.options.prefix + "-slot_" + this.options.slotPosition);
75 | this.slot.innerHTML = html;
76 | };
77 | Smartour.prototype._createLayer = function () {
78 | if (!this.layer) {
79 | this.layer = document.createElement('div');
80 | this.layer.setAttribute('class', this.options.prefix + '-layer');
81 | this.layer.setAttribute('style', layerStyle());
82 | this.layer.addEventListener('click', this.options.layerEvent);
83 | document.body.appendChild(this.layer);
84 | }
85 | };
86 | Smartour.prototype._setPosition = function (el, attrs) {
87 | ['top', 'left', 'width', 'height'].forEach(function (attr, index) {
88 | if (attrs[index]) {
89 | if (attr === 'top' || attr === 'left') {
90 | var scrollDirection = "scroll" + (attr.charAt(0).toUpperCase() + attr.slice(1));
91 | var scrollDistance = 0;
92 | if (document.documentElement && document.documentElement[scrollDirection]) {
93 | scrollDistance = document.documentElement[scrollDirection];
94 | }
95 | else {
96 | scrollDistance = document.body[scrollDirection];
97 | }
98 | el.style[attr] = attrs[index] + scrollDistance + 'px';
99 | }
100 | else {
101 | el.style[attr] = attrs[index] + 'px';
102 | }
103 | }
104 | });
105 | };
106 | Smartour.prototype._show = function (targetSelector, slotHtml, keyNodes) {
107 | var _a, _b, _c, _d;
108 | if (slotHtml === void 0) { slotHtml = ''; }
109 | if (keyNodes === void 0) { keyNodes = []; }
110 | this._createMask();
111 | this._createSlot(slotHtml);
112 | this._createLayer();
113 | if (!this.options.animate) {
114 | this.mask.style.transition = null;
115 | this.slot.style.transition = null;
116 | }
117 | var target = document.querySelector(targetSelector);
118 | var _e = target.getBoundingClientRect(), top = _e.top, left = _e.left, width = _e.width, height = _e.height;
119 | var _f = [top - this.options.padding, left - this.options.padding, width + 2 * this.options.padding, height + 2 * this.options.padding], maskTop = _f[0], maskLeft = _f[1], maskWidth = _f[2], maskHeight = _f[3];
120 | this._setPosition(this.mask, [maskTop, maskLeft, maskWidth, maskHeight]);
121 | var _g = this.slot.getBoundingClientRect(), slotWidth = _g.width, slotHeight = _g.height;
122 | var slotPosition = this.options.slotPosition;
123 | var _h = [0, 0], slotTop = _h[0], slotLeft = _h[1];
124 | if (slotPosition === SlotPosition.TOP) {
125 | _a = [maskTop - slotHeight, maskLeft + maskWidth / 2 - slotWidth / 2], slotTop = _a[0], slotLeft = _a[1];
126 | }
127 | else if (slotPosition === SlotPosition.BOTTOM) {
128 | _b = [maskTop + maskHeight, maskLeft + maskWidth / 2 - slotWidth / 2], slotTop = _b[0], slotLeft = _b[1];
129 | }
130 | else if (slotPosition === SlotPosition.LEFT) {
131 | _c = [maskTop - (slotHeight - maskHeight) / 2, maskLeft - slotWidth], slotTop = _c[0], slotLeft = _c[1];
132 | }
133 | else if (slotPosition === SlotPosition.RIGHT) {
134 | _d = [maskTop - (slotHeight - maskHeight) / 2, maskLeft + maskWidth], slotTop = _d[0], slotLeft = _d[1];
135 | }
136 | this._setPosition(this.slot, [slotTop, slotLeft]);
137 | if (!slotHtml) {
138 | document.body.removeChild(this.slot);
139 | this.slot = null;
140 | }
141 | if (keyNodes.length) {
142 | keyNodes.forEach(function (_a) {
143 | var el = _a.el, event = _a.event;
144 | document.querySelector(el).addEventListener('click', event);
145 | });
146 | }
147 | };
148 | Smartour.prototype.focus = function (highlightElement) {
149 | if (highlightElement === void 0) { highlightElement = { el: '', slot: '', keyNodes: [], options: {} }; }
150 | if (highlightElement.options && Object.keys(highlightElement.options).length) {
151 | this.options = __assign({}, this.options, highlightElement.options);
152 | }
153 | this._show(highlightElement.el, highlightElement.slot, highlightElement.keyNodes);
154 | };
155 | Smartour.prototype.queue = function (tourList) {
156 | this.tourList = tourList;
157 | this.tourListLength = tourList.length;
158 | this.tourIndex = -1;
159 | return this;
160 | };
161 | Smartour.prototype.run = function (isNext) {
162 | if (isNext === void 0) { isNext = true; }
163 | if (this.tourListLength && this.tourIndex < this.tourListLength - 1) {
164 | isNext ? this.tourIndex++ : this.tourIndex--;
165 | var tour = this.tourList[this.tourIndex];
166 | if (tour.options) {
167 | this.options = __assign({}, this.options, tour.options);
168 | }
169 | this._show(tour.el, tour.slot, tour.keyNodes);
170 | }
171 | else {
172 | this.over();
173 | }
174 | };
175 | Smartour.prototype.next = function () {
176 | this.run(true);
177 | };
178 | Smartour.prototype.prev = function () {
179 | this.run(false);
180 | };
181 | Smartour.prototype.over = function () {
182 | var _this = this;
183 | this.mask && document.body.removeChild(this.mask);
184 | this.slot && document.body.removeChild(this.slot);
185 | this.layer && document.body.removeChild(this.layer);
186 | ['mask', 'slot', 'layer'].forEach(function (attr) {
187 | _this[attr] = null;
188 | });
189 | };
190 | return Smartour;
191 | }());
192 |
193 | return Smartour;
194 |
195 | }));
196 |
--------------------------------------------------------------------------------
/docs/js/app.70244b16.js:
--------------------------------------------------------------------------------
1 | (function(t){function e(e){for(var n,r,l=e[0],a=e[1],u=e[2],d=0,h=[];d div > h1",slot:"
This is it's name
",options:{slotPosition:"top",layerEvent:tour.next.bind(tour)}},{el:"#app > div > h3",slot:"
This is what it does.
",options:{slotPosition:"bottom",layerEvent:tour.next.bind(tour)}},{el:"#app > div > h2",slot:"
Scoll up to see the document
",options:{slotPosition:"top",layerEvent:tour.next.bind(tour)}}]),tour.run()}},u=a,c=(o("9346"),o("2877")),d=Object(c["a"])(u,r,l,!1,null,"4cefd0c2",null),h=d.exports,p=function(){var t=this,e=t.$createElement,o=t._self._c||e;return o("div",{staticClass:"usage basic"},[o("div",{staticClass:"usage-content"},[o("div",{staticClass:"usage-content-doc",domProps:{innerHTML:t._s(t.doc1)}})])])},m=[],f=(o("ac6a"),o("f068")),g=o.n(f),v={data:function(){return{doc1:g.a}},mounted:function(){var t=this;["basic-usage","pure-string","html-string","slot-events","queue"].forEach(function(e,o){document.querySelector(".".concat(e,"-demo")).addEventListener("click",t["demo"+o])}),["top","right","bottom","left"].forEach(function(e){document.querySelector(".slot-".concat(e)).addEventListener("click",function(){t.demoPos(e)})})},methods:{demo0:function(){tour.focus({el:"#basic-usage"})},demo1:function(){tour.focus({el:"#pure-string",slot:"This is a pure string"})},demo2:function(){tour.focus({el:"#html-string",slot:"\n
\n
This is a html string
\n
\n "})},demoPos:function(t){var e=new Smartour;e.focus({el:".slot-".concat(t),slot:t,options:{slotPosition:t}})},demo3:function(){tour.focus({el:".slot-events-demo",options:{slotPosition:"right"},slot:'\n \n \n ',keyNodes:[{el:".occur-1",event:function(){alert("Event!!")}},{el:".occur-2",event:function(){alert("Another event!!")}}]})},demo4:function(){var t=new Smartour;t.queue([{el:".li-1",options:{layerEvent:t.next.bind(t)},slot:"This is the 1st line."},{el:".li-2",options:{layerEvent:t.next.bind(t)},slot:"This is the 2nd line."},{el:".li-3",options:{layerEvent:t.next.bind(t)},slot:"This is the 3rd line."}]).run()}}},b=v,y=(o("619e"),Object(c["a"])(b,p,m,!1,null,"190bd07d",null)),w=y.exports,k=function(){var t=this,e=t.$createElement;t._self._c;return t._m(0)},x=[function(){var t=this,e=t.$createElement,o=t._self._c||e;return o("div",{staticClass:"footer"},[o("p",[t._v("Smartour concerns about the global climate problem.")]),o("p",[t._v("\n The background image was download from "),o("a",{attrs:{href:"https://showyourstripes.info/"}},[t._v("#ShowYourStripes")])])])}],S=(o("a0f1"),{}),E=Object(c["a"])(S,k,x,!1,null,"6091108d",null),_=E.exports,T={name:"app",components:{Intro:h,Doc:w,Footer:_},mounted:function(){hljs.initHighlightingOnLoad()}},j=T,P=Object(c["a"])(j,s,i,!1,null,null,null),C=P.exports,q=(o("a606"),o("5ed6"),o("456d"),o("cebc")),O=o("d225"),L=o("b0b4"),A=function(t,e){return"\nposition: absolute;\nborder-radius: 4px;\nbox-shadow: 0 0 0 9999px ".concat(t,";\nz-index: 10001 !important;\ntransition: all .3s;\n")},I=function(t){return"\nposition: absolute;\nz-index: 10002 !important;\ntransition: all .3s;\n"},M=function(){return"\nposition: fixed;\ntop: 0;\nleft: 0;\nright: 0;\nbottom: 0;\nz-index: 10000 !important;\n"},N={prefix:"smartour",padding:5,maskColor:"rgba(0, 0, 0, .5)",animate:!0,slotPosition:"top"},B=function(){function t(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{};Object(O["a"])(this,t),this.options=Object(q["a"])({},N,{layerEvent:this.over.bind(this)},e),this.mask=null,this.slot=null,this.layer=null}return Object(L["a"])(t,[{key:"_createMask",value:function(){this.mask||(this.mask=document.createElement("div"),this.mask.setAttribute("class",this.options.prefix+"-mask"),this.mask.setAttribute("style",A(this.options.maskColor)),document.body.appendChild(this.mask))}},{key:"_createSlot",value:function(t){this.slot||(this.slot=document.createElement("div"),this.slot.setAttribute("style",I()),document.body.appendChild(this.slot)),this.slot.setAttribute("class","".concat(this.options.prefix,"-slot ").concat(this.options.prefix,"-slot_").concat(this.options.slotPosition)),this.slot.innerHTML=t}},{key:"_createLayer",value:function(){this.layer||(this.layer=document.createElement("div"),this.layer.setAttribute("class",this.options.prefix+"-layer"),this.layer.setAttribute("style",M()),this.layer.addEventListener("click",this.options.layerEvent),document.body.appendChild(this.layer))}},{key:"_setPosition",value:function(t,e){["top","left","width","height"].forEach(function(o,n){if(e[n])if("top"===o||"left"===o){var s="scroll".concat(o.charAt(0).toUpperCase()+o.slice(1)),i=0;i=document.documentElement&&document.documentElement[s]?document.documentElement[s]:document.body[s],t.style[o]=e[n]+i+"px"}else t.style[o]=e[n]+"px"})}},{key:"_show",value:function(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:"",o=arguments.length>2&&void 0!==arguments[2]?arguments[2]:[];this._createMask(),this._createSlot(e),this._createLayer(),this.options.animate||(this.mask.style.transition=null,this.slot.style.transition=null);var n=document.querySelector(t),s=n.getBoundingClientRect(),i=s.top,r=s.left,l=s.width,a=s.height,u=i-this.options.padding,c=r-this.options.padding,d=l+2*this.options.padding,h=a+2*this.options.padding;this._setPosition(this.mask,[u,c,d,h]);var p=this.slot.getBoundingClientRect(),m=p.width,f=p.height,g=this.options.slotPosition,v=0,b=0;"top"===g?(v=u-f,b=c+d/2-m/2):"bottom"===g?(v=u+h,b=c+d/2-m/2):"left"===g?(v=u-(f-h)/2,b=c-m):"right"===g&&(v=u-(f-h)/2,b=c+d),this._setPosition(this.slot,[v,b]),e||(document.body.removeChild(this.slot),this.slot=null),o.length&&o.forEach(function(t){var e=t.el,o=t.event;document.querySelector(e).addEventListener("click",o)})}},{key:"focus",value:function(t){var e=t.el,o=void 0===e?"":e,n=t.slot,s=void 0===n?"":n,i=t.keyNodes,r=void 0===i?[]:i,l=t.options,a=void 0===l?{}:l;Object.keys(a).length&&(this.options=Object(q["a"])({},this.options,a)),this._show(o,s,r)}},{key:"queue",value:function(t){return this.tourList=t,this.tourListLength=t.length,this.tourIndex=-1,this}},{key:"run",value:function(){var t=!(arguments.length>0&&void 0!==arguments[0])||arguments[0];if(this.tourListLength&&this.tourIndexOnce a website has changed its UI, usually they would set a list of tour guide to tell the visitors, that some modules were moved to the other places. We named it as "tour guide", and Smartour is a solution for making tour guide much easier.
\n
Install
\n
Smartour was built to an umd and es modules package.
\n
npm install smartour
/* ES Modules */\nimport Smartour from 'smartour/dist/index.esm.js'\n/* CommandJS */\nconst Smartour = require('smartour')\n/* <script> */\n<script src="smartour/dist/index.js"></script>
Basic usage
\n
Smartour provides a very simple API focus(), it's the easist way to highlight an element.
\n
let tour = new Smartour()\n\ntour.focus({\n el: '#basic-usage'\n})
\n\n
Slot
\n
slot is a html string that allows you to add a description to the highlighted element.
\n
Pure string:
\n
let tour = new Smartour()\n\ntour.focus({\n el: '#pure-string',\n slot: 'This is a pure string'\n})
\n\n
Html string
\n
let tour = new Smartour()\n\ntour.focus({\n el: '#html-string',\n slot: `\n <div>\n <p>This is a html string</p>\n </div>\n `\n})
\n\n
Slot positions
\n
There are 4 positions to place a slot: top, right, left, bottom.
\n
Set the options.slotPosition attribute to overwrite the default top.
\n
let tour = new Smartour()\n\ntour.focus({\n el: '#slot-positions',\n slot: `top`,\n options: {\n slotPosition: 'top' // default is `top`\n }\n})
\n
\n\n\n
\n
Slot events
\n
The slot element could bind events, too. We can use the keyNodes attribute to bind events to them.
\n
keyNodes is an array contains with keyNode. The attribute keyNode.el is a css selector, and the other keyNode.event is the binding event.
\n
let tour = new Smartour()\n\ntour.focus({\n el: '.slot-events-demo',\n options: {\n slotPosition: 'right'\n },\n slot: `\n <button class="demo-btn occur-1">\n Click here to occur an alert event\n </button>\n <button class="demo-btn occur-2">\n Click here to occur an alert event\n </button>\n `,\n keyNodes: [{\n el: '.occur-1',\n event: () => { alert('Event!!') }\n }, {\n el: '.occur-2',\n event: () => { alert('Another event!!') }\n }]\n})
\n\n
Queue
\n
Sometimes there are more than one tour guide to show. Smartour allows you to put the tour guides together as a queue and show them one by one.
\n
Example:
\n
\n
This is the first line.
\n
This is the second line.
\n
This is the thired line.
\n
\n\n
let tour = new Smartour()\n\ntour\n .queue([{\n el: '.li-1',\n options: {\n layerEvent: tour.next.bind(tour)\n },\n slot: 'This is the 1st line.'\n }, {\n el: '.li-2',\n options: {\n layerEvent: tour.next.bind(tour)\n },\n slot: 'This is the 2nd line.'\n }, {\n el: '.li-3',\n options: {\n layerEvent: tour.next.bind(tour)\n },\n slot: 'This is the 3rd line.'\n }])\n .run() // don't forget to trigger api `run()` to show the first tour guide
\n\n
Options
\n
Smartour is a constructor and receives an options parameter to overwrite the default.
\n
Let's take a look at the default options:
\n
{\n prefix: 'smartour', // class prefix\n padding: 5, // padding of the highlight area\n maskColor: 'rgba(0, 0, 0, .5)', // maskColor with alpha\n animate: true, // use animate while changing tour guides\n slotPosition: 'top' // default slot position\n layerEvent: smartour.over // events while clicking the layer\n}
\n
APIs
\n
Besides .focus(), .queue() and .run(), Smartour alse privides two apis to handle the tour guide playing.
\n
\n
.next(): Show the next tour guide. (Only work with .queue())
\n
\n
.prev(): Show the previous tour guide. (Only work with .queue())
\n
\n
\n
Principles of Smartour
\n
Smartour uses api element.getBoundingClientRect() to detect the size and position of the target element, than place a rect element with box-shadow over it as the highlight area.
\n
Because click events could not be triigered from the box-shadow area, Smartour place another transparent layer over the page, and bind layerEvent() to it to solve this problem.
\n
The position of the highlight area and slot are absolute. Every time the page scrolled, the value of document.documentElement.scrollTop or document.documentElement.scrollLeft would be changed, and Smartour will use these values to correct the position.
\n'}});
2 | //# sourceMappingURL=app.70244b16.js.map
--------------------------------------------------------------------------------
/docs/js/app.70244b16.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"sources":["webpack:///webpack/bootstrap","webpack:///./src/App.vue?d403","webpack:///./src/components/Intro.vue?c391","webpack:///src/components/Intro.vue","webpack:///./src/components/Intro.vue?2a05","webpack:///./src/components/Intro.vue","webpack:///./src/components/Doc.vue?82e2","webpack:///src/components/Doc.vue","webpack:///./src/components/Doc.vue?66d4","webpack:///./src/components/Doc.vue","webpack:///./src/components/Footer.vue?cdbf","webpack:///./src/components/Footer.vue","webpack:///src/App.vue","webpack:///./src/App.vue?a7d1","webpack:///./src/App.vue","webpack:///./src/js/smartour.esm.js","webpack:///./src/main.js","webpack:///./src/components/Doc.vue?d7cf","webpack:///./src/components/Intro.vue?ed60","webpack:///./src/components/Footer.vue?8260","webpack:///./src/docs/basic.md"],"names":["webpackJsonpCallback","data","moduleId","chunkId","chunkIds","moreModules","executeModules","i","resolves","length","installedChunks","push","Object","prototype","hasOwnProperty","call","modules","parentJsonpFunction","shift","deferredModules","apply","checkDeferredModules","result","deferredModule","fulfilled","j","depId","splice","__webpack_require__","s","installedModules","app","exports","module","l","m","c","d","name","getter","o","defineProperty","enumerable","get","r","Symbol","toStringTag","value","t","mode","__esModule","ns","create","key","bind","n","object","property","p","jsonpArray","window","oldJsonpFunction","slice","Appvue_type_template_id_08741730_render","_vm","this","_h","$createElement","_c","_self","attrs","id","staticRenderFns","Introvue_type_template_id_4cefd0c2_scoped_true_render","_m","Introvue_type_template_id_4cefd0c2_scoped_true_staticRenderFns","staticClass","_v","Introvue_type_script_lang_js_","mounted","tour","queue","el","slot","options","slotPosition","layerEvent","next","run","components_Introvue_type_script_lang_js_","component","componentNormalizer","Intro","Docvue_type_template_id_190bd07d_scoped_true_render","domProps","innerHTML","_s","doc1","Docvue_type_template_id_190bd07d_scoped_true_staticRenderFns","Docvue_type_script_lang_js_","basic_default","a","_this","forEach","index","document","querySelector","concat","addEventListener","pos","demoPos","methods","demo0","focus","demo1","demo2","demo3Tour","Smartour","demo3","keyNodes","event","alert","demo4","components_Docvue_type_script_lang_js_","Doc_component","Doc","Footervue_type_template_id_6091108d_scoped_true_render","Footervue_type_template_id_6091108d_scoped_true_staticRenderFns","href","script","Footer_component","Footer","Appvue_type_script_lang_js_","components","hljs","initHighlightingOnLoad","src_Appvue_type_script_lang_js_","App_component","App","maskStyle","maskColor","animate","slotStyle","layerStyle","defaultOptions","prefix","padding","arguments","undefined","classCallCheck","objectSpread","over","mask","layer","createElement","setAttribute","body","appendChild","html","attr","scrollDirection","charAt","toUpperCase","scrollDistance","documentElement","style","targetSelector","slotHtml","_createMask","_createSlot","_createLayer","transition","target","_target$getBoundingCl","getBoundingClientRect","top","left","width","height","maskTop","maskLeft","maskWidth","maskHeight","_setPosition","_this$slot$getBoundin","slotWidth","slotHeight","slotTop","slotLeft","removeChild","_ref","_ref2$el","_ref2","_ref2$slot","_ref2$keyNodes","_ref2$options","keys","_show","tourList","tourListLength","tourIndex","isNext","Vue","config","productionTip","render","h","$mount","_node_modules_mini_css_extract_plugin_dist_loader_js_ref_10_oneOf_1_0_node_modules_css_loader_index_js_ref_10_oneOf_1_1_node_modules_vue_loader_lib_loaders_stylePostLoader_js_node_modules_postcss_loader_src_index_js_ref_10_oneOf_1_2_node_modules_less_loader_dist_cjs_js_ref_10_oneOf_1_3_node_modules_cache_loader_dist_cjs_js_ref_0_0_node_modules_vue_loader_lib_index_js_vue_loader_options_Doc_vue_vue_type_style_index_0_id_190bd07d_lang_less_scoped_true___WEBPACK_IMPORTED_MODULE_0__","_node_modules_mini_css_extract_plugin_dist_loader_js_ref_10_oneOf_1_0_node_modules_css_loader_index_js_ref_10_oneOf_1_1_node_modules_vue_loader_lib_loaders_stylePostLoader_js_node_modules_postcss_loader_src_index_js_ref_10_oneOf_1_2_node_modules_less_loader_dist_cjs_js_ref_10_oneOf_1_3_node_modules_cache_loader_dist_cjs_js_ref_0_0_node_modules_vue_loader_lib_index_js_vue_loader_options_Doc_vue_vue_type_style_index_0_id_190bd07d_lang_less_scoped_true___WEBPACK_IMPORTED_MODULE_0___default","_node_modules_mini_css_extract_plugin_dist_loader_js_ref_10_oneOf_1_0_node_modules_css_loader_index_js_ref_10_oneOf_1_1_node_modules_vue_loader_lib_loaders_stylePostLoader_js_node_modules_postcss_loader_src_index_js_ref_10_oneOf_1_2_node_modules_less_loader_dist_cjs_js_ref_10_oneOf_1_3_node_modules_cache_loader_dist_cjs_js_ref_0_0_node_modules_vue_loader_lib_index_js_vue_loader_options_Intro_vue_vue_type_style_index_0_id_4cefd0c2_lang_less_scoped_true___WEBPACK_IMPORTED_MODULE_0__","_node_modules_mini_css_extract_plugin_dist_loader_js_ref_10_oneOf_1_0_node_modules_css_loader_index_js_ref_10_oneOf_1_1_node_modules_vue_loader_lib_loaders_stylePostLoader_js_node_modules_postcss_loader_src_index_js_ref_10_oneOf_1_2_node_modules_less_loader_dist_cjs_js_ref_10_oneOf_1_3_node_modules_cache_loader_dist_cjs_js_ref_0_0_node_modules_vue_loader_lib_index_js_vue_loader_options_Intro_vue_vue_type_style_index_0_id_4cefd0c2_lang_less_scoped_true___WEBPACK_IMPORTED_MODULE_0___default","_node_modules_mini_css_extract_plugin_dist_loader_js_ref_10_oneOf_1_0_node_modules_css_loader_index_js_ref_10_oneOf_1_1_node_modules_vue_loader_lib_loaders_stylePostLoader_js_node_modules_postcss_loader_src_index_js_ref_10_oneOf_1_2_node_modules_less_loader_dist_cjs_js_ref_10_oneOf_1_3_node_modules_cache_loader_dist_cjs_js_ref_0_0_node_modules_vue_loader_lib_index_js_vue_loader_options_Footer_vue_vue_type_style_index_0_id_6091108d_lang_less_scoped_true___WEBPACK_IMPORTED_MODULE_0__","_node_modules_mini_css_extract_plugin_dist_loader_js_ref_10_oneOf_1_0_node_modules_css_loader_index_js_ref_10_oneOf_1_1_node_modules_vue_loader_lib_loaders_stylePostLoader_js_node_modules_postcss_loader_src_index_js_ref_10_oneOf_1_2_node_modules_less_loader_dist_cjs_js_ref_10_oneOf_1_3_node_modules_cache_loader_dist_cjs_js_ref_0_0_node_modules_vue_loader_lib_index_js_vue_loader_options_Footer_vue_vue_type_style_index_0_id_6091108d_lang_less_scoped_true___WEBPACK_IMPORTED_MODULE_0___default"],"mappings":"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","file":"js/app.70244b16.js","sourcesContent":[" \t// install a JSONP callback for chunk loading\n \tfunction webpackJsonpCallback(data) {\n \t\tvar chunkIds = data[0];\n \t\tvar moreModules = data[1];\n \t\tvar executeModules = data[2];\n\n \t\t// add \"moreModules\" to the modules object,\n \t\t// then flag all \"chunkIds\" as loaded and fire callback\n \t\tvar moduleId, chunkId, i = 0, resolves = [];\n \t\tfor(;i < chunkIds.length; i++) {\n \t\t\tchunkId = chunkIds[i];\n \t\t\tif(installedChunks[chunkId]) {\n \t\t\t\tresolves.push(installedChunks[chunkId][0]);\n \t\t\t}\n \t\t\tinstalledChunks[chunkId] = 0;\n \t\t}\n \t\tfor(moduleId in moreModules) {\n \t\t\tif(Object.prototype.hasOwnProperty.call(moreModules, moduleId)) {\n \t\t\t\tmodules[moduleId] = moreModules[moduleId];\n \t\t\t}\n \t\t}\n \t\tif(parentJsonpFunction) parentJsonpFunction(data);\n\n \t\twhile(resolves.length) {\n \t\t\tresolves.shift()();\n \t\t}\n\n \t\t// add entry modules from loaded chunk to deferred list\n \t\tdeferredModules.push.apply(deferredModules, executeModules || []);\n\n \t\t// run deferred modules when all chunks ready\n \t\treturn checkDeferredModules();\n \t};\n \tfunction checkDeferredModules() {\n \t\tvar result;\n \t\tfor(var i = 0; i < deferredModules.length; i++) {\n \t\t\tvar deferredModule = deferredModules[i];\n \t\t\tvar fulfilled = true;\n \t\t\tfor(var j = 1; j < deferredModule.length; j++) {\n \t\t\t\tvar depId = deferredModule[j];\n \t\t\t\tif(installedChunks[depId] !== 0) fulfilled = false;\n \t\t\t}\n \t\t\tif(fulfilled) {\n \t\t\t\tdeferredModules.splice(i--, 1);\n \t\t\t\tresult = __webpack_require__(__webpack_require__.s = deferredModule[0]);\n \t\t\t}\n \t\t}\n \t\treturn result;\n \t}\n\n \t// The module cache\n \tvar installedModules = {};\n\n \t// object to store loaded and loading chunks\n \t// undefined = chunk not loaded, null = chunk preloaded/prefetched\n \t// Promise = chunk loading, 0 = chunk loaded\n \tvar installedChunks = {\n \t\t\"app\": 0\n \t};\n\n \tvar deferredModules = [];\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId]) {\n \t\t\treturn installedModules[moduleId].exports;\n \t\t}\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\ti: moduleId,\n \t\t\tl: false,\n \t\t\texports: {}\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.l = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// define getter function for harmony exports\n \t__webpack_require__.d = function(exports, name, getter) {\n \t\tif(!__webpack_require__.o(exports, name)) {\n \t\t\tObject.defineProperty(exports, name, { enumerable: true, get: getter });\n \t\t}\n \t};\n\n \t// define __esModule on exports\n \t__webpack_require__.r = function(exports) {\n \t\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n \t\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n \t\t}\n \t\tObject.defineProperty(exports, '__esModule', { value: true });\n \t};\n\n \t// create a fake namespace object\n \t// mode & 1: value is a module id, require it\n \t// mode & 2: merge all properties of value into the ns\n \t// mode & 4: return value when already ns object\n \t// mode & 8|1: behave like require\n \t__webpack_require__.t = function(value, mode) {\n \t\tif(mode & 1) value = __webpack_require__(value);\n \t\tif(mode & 8) return value;\n \t\tif((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;\n \t\tvar ns = Object.create(null);\n \t\t__webpack_require__.r(ns);\n \t\tObject.defineProperty(ns, 'default', { enumerable: true, value: value });\n \t\tif(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));\n \t\treturn ns;\n \t};\n\n \t// getDefaultExport function for compatibility with non-harmony modules\n \t__webpack_require__.n = function(module) {\n \t\tvar getter = module && module.__esModule ?\n \t\t\tfunction getDefault() { return module['default']; } :\n \t\t\tfunction getModuleExports() { return module; };\n \t\t__webpack_require__.d(getter, 'a', getter);\n \t\treturn getter;\n \t};\n\n \t// Object.prototype.hasOwnProperty.call\n \t__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"/smartour/\";\n\n \tvar jsonpArray = window[\"webpackJsonp\"] = window[\"webpackJsonp\"] || [];\n \tvar oldJsonpFunction = jsonpArray.push.bind(jsonpArray);\n \tjsonpArray.push = webpackJsonpCallback;\n \tjsonpArray = jsonpArray.slice();\n \tfor(var i = 0; i < jsonpArray.length; i++) webpackJsonpCallback(jsonpArray[i]);\n \tvar parentJsonpFunction = oldJsonpFunction;\n\n\n \t// add entry module to deferred list\n \tdeferredModules.push([0,\"chunk-vendors\"]);\n \t// run deferred modules when ready\n \treturn checkDeferredModules();\n","var render = function () {var _vm=this;var _h=_vm.$createElement;var _c=_vm._self._c||_h;return _c('div',{attrs:{\"id\":\"app\"}},[_c('Intro'),_c('Doc'),_c('Footer')],1)}\nvar staticRenderFns = []\n\nexport { render, staticRenderFns }","var render = function () {var _vm=this;var _h=_vm.$createElement;var _c=_vm._self._c||_h;return _vm._m(0)}\nvar staticRenderFns = [function () {var _vm=this;var _h=_vm.$createElement;var _c=_vm._self._c||_h;return _c('div',{staticClass:\"view intro\"},[_c('h1',[_vm._v(\"Smartour\")]),_c('h3',[_vm._v(\"Makes website tour guide much easier\")]),_c('h2',[_vm._v(\"⬇︎\")])])}]\n\nexport { render, staticRenderFns }","\n
\n
Smartour
\n
Makes website tour guide much easier
\n
⬇︎
\n
\n\n\n\n\n\n","import mod from \"-!../../node_modules/cache-loader/dist/cjs.js??ref--12-0!../../node_modules/thread-loader/dist/cjs.js!../../node_modules/babel-loader/lib/index.js!../../node_modules/cache-loader/dist/cjs.js??ref--0-0!../../node_modules/vue-loader/lib/index.js??vue-loader-options!./Intro.vue?vue&type=script&lang=js&\"; export default mod; export * from \"-!../../node_modules/cache-loader/dist/cjs.js??ref--12-0!../../node_modules/thread-loader/dist/cjs.js!../../node_modules/babel-loader/lib/index.js!../../node_modules/cache-loader/dist/cjs.js??ref--0-0!../../node_modules/vue-loader/lib/index.js??vue-loader-options!./Intro.vue?vue&type=script&lang=js&\"","import { render, staticRenderFns } from \"./Intro.vue?vue&type=template&id=4cefd0c2&scoped=true&\"\nimport script from \"./Intro.vue?vue&type=script&lang=js&\"\nexport * from \"./Intro.vue?vue&type=script&lang=js&\"\nimport style0 from \"./Intro.vue?vue&type=style&index=0&id=4cefd0c2&lang=less&scoped=true&\"\n\n\n/* normalize component */\nimport normalizer from \"!../../node_modules/vue-loader/lib/runtime/componentNormalizer.js\"\nvar component = normalizer(\n script,\n render,\n staticRenderFns,\n false,\n null,\n \"4cefd0c2\",\n null\n \n)\n\nexport default component.exports","var render = function () {var _vm=this;var _h=_vm.$createElement;var _c=_vm._self._c||_h;return _c('div',{staticClass:\"usage basic\"},[_c('div',{staticClass:\"usage-content\"},[_c('div',{staticClass:\"usage-content-doc\",domProps:{\"innerHTML\":_vm._s(_vm.doc1)}})])])}\nvar staticRenderFns = []\n\nexport { render, staticRenderFns }","\n
\n
\n \n
\n
\n\n\n\n\n\n","import mod from \"-!../../node_modules/cache-loader/dist/cjs.js??ref--12-0!../../node_modules/thread-loader/dist/cjs.js!../../node_modules/babel-loader/lib/index.js!../../node_modules/cache-loader/dist/cjs.js??ref--0-0!../../node_modules/vue-loader/lib/index.js??vue-loader-options!./Doc.vue?vue&type=script&lang=js&\"; export default mod; export * from \"-!../../node_modules/cache-loader/dist/cjs.js??ref--12-0!../../node_modules/thread-loader/dist/cjs.js!../../node_modules/babel-loader/lib/index.js!../../node_modules/cache-loader/dist/cjs.js??ref--0-0!../../node_modules/vue-loader/lib/index.js??vue-loader-options!./Doc.vue?vue&type=script&lang=js&\"","import { render, staticRenderFns } from \"./Doc.vue?vue&type=template&id=190bd07d&scoped=true&\"\nimport script from \"./Doc.vue?vue&type=script&lang=js&\"\nexport * from \"./Doc.vue?vue&type=script&lang=js&\"\nimport style0 from \"./Doc.vue?vue&type=style&index=0&id=190bd07d&lang=less&scoped=true&\"\n\n\n/* normalize component */\nimport normalizer from \"!../../node_modules/vue-loader/lib/runtime/componentNormalizer.js\"\nvar component = normalizer(\n script,\n render,\n staticRenderFns,\n false,\n null,\n \"190bd07d\",\n null\n \n)\n\nexport default component.exports","var render = function () {var _vm=this;var _h=_vm.$createElement;var _c=_vm._self._c||_h;return _vm._m(0)}\nvar staticRenderFns = [function () {var _vm=this;var _h=_vm.$createElement;var _c=_vm._self._c||_h;return _c('div',{staticClass:\"footer\"},[_c('p',[_vm._v(\"Smartour concerns about the global climate problem.\")]),_c('p',[_vm._v(\"\\n The background image was download from \"),_c('a',{attrs:{\"href\":\"https://showyourstripes.info/\"}},[_vm._v(\"#ShowYourStripes\")])])])}]\n\nexport { render, staticRenderFns }","import { render, staticRenderFns } from \"./Footer.vue?vue&type=template&id=6091108d&scoped=true&\"\nvar script = {}\nimport style0 from \"./Footer.vue?vue&type=style&index=0&id=6091108d&lang=less&scoped=true&\"\n\n\n/* normalize component */\nimport normalizer from \"!../../node_modules/vue-loader/lib/runtime/componentNormalizer.js\"\nvar component = normalizer(\n script,\n render,\n staticRenderFns,\n false,\n null,\n \"6091108d\",\n null\n \n)\n\nexport default component.exports","\n
Once a website has changed its UI, usually they would set a list of tour guide to tell the visitors, that some modules were moved to the other places. We named it as "tour guide", and Smartour is a solution for making tour guide much easier.
\\n
Install
\\n
Smartour was built to an umd and es modules package.
\\n
npm install smartour
/* ES Modules */\\nimport Smartour from 'smartour/dist/index.esm.js'\\n/* CommandJS */\\nconst Smartour = require('smartour')\\n/* <script> */\\n<script src="smartour/dist/index.js"></script>
Basic usage
\\n
Smartour provides a very simple API focus(), it's the easist way to highlight an element.
\\n
let tour = new Smartour()\\n\\ntour.focus({\\n el: '#basic-usage'\\n})
\\n\\n
Slot
\\n
slot is a html string that allows you to add a description to the highlighted element.
\\n
Pure string:
\\n
let tour = new Smartour()\\n\\ntour.focus({\\n el: '#pure-string',\\n slot: 'This is a pure string'\\n})
\\n\\n
Html string
\\n
let tour = new Smartour()\\n\\ntour.focus({\\n el: '#html-string',\\n slot: `\\n <div>\\n <p>This is a html string</p>\\n </div>\\n `\\n})
\\n\\n
Slot positions
\\n
There are 4 positions to place a slot: top, right, left, bottom.
\\n
Set the options.slotPosition attribute to overwrite the default top.
\\n
let tour = new Smartour()\\n\\ntour.focus({\\n el: '#slot-positions',\\n slot: `top`,\\n options: {\\n slotPosition: 'top' // default is `top`\\n }\\n})
\\n
\\n\\n\\n
\\n
Slot events
\\n
The slot element could bind events, too. We can use the keyNodes attribute to bind events to them.
\\n
keyNodes is an array contains with keyNode. The attribute keyNode.el is a css selector, and the other keyNode.event is the binding event.
\\n
let tour = new Smartour()\\n\\ntour.focus({\\n el: '.slot-events-demo',\\n options: {\\n slotPosition: 'right'\\n },\\n slot: `\\n <button class="demo-btn occur-1">\\n Click here to occur an alert event\\n </button>\\n <button class="demo-btn occur-2">\\n Click here to occur an alert event\\n </button>\\n `,\\n keyNodes: [{\\n el: '.occur-1',\\n event: () => { alert('Event!!') }\\n }, {\\n el: '.occur-2',\\n event: () => { alert('Another event!!') }\\n }]\\n})
\\n\\n
Queue
\\n
Sometimes there are more than one tour guide to show. Smartour allows you to put the tour guides together as a queue and show them one by one.
\\n
Example:
\\n
\\n
This is the first line.
\\n
This is the second line.
\\n
This is the thired line.
\\n
\\n\\n
let tour = new Smartour()\\n\\ntour\\n .queue([{\\n el: '.li-1',\\n options: {\\n layerEvent: tour.next.bind(tour)\\n },\\n slot: 'This is the 1st line.'\\n }, {\\n el: '.li-2',\\n options: {\\n layerEvent: tour.next.bind(tour)\\n },\\n slot: 'This is the 2nd line.'\\n }, {\\n el: '.li-3',\\n options: {\\n layerEvent: tour.next.bind(tour)\\n },\\n slot: 'This is the 3rd line.'\\n }])\\n .run() // don't forget to trigger api `run()` to show the first tour guide
\\n\\n
Options
\\n
Smartour is a constructor and receives an options parameter to overwrite the default.
\\n
Let's take a look at the default options:
\\n
{\\n prefix: 'smartour', // class prefix\\n padding: 5, // padding of the highlight area\\n maskColor: 'rgba(0, 0, 0, .5)', // maskColor with alpha\\n animate: true, // use animate while changing tour guides\\n slotPosition: 'top' // default slot position\\n layerEvent: smartour.over // events while clicking the layer\\n}
\\n
APIs
\\n
Besides .focus(), .queue() and .run(), Smartour alse privides two apis to handle the tour guide playing.
\\n
\\n
.next(): Show the next tour guide. (Only work with .queue())
\\n
\\n
.prev(): Show the previous tour guide. (Only work with .queue())
\\n
\\n
\\n
Principles of Smartour
\\n
Smartour uses api element.getBoundingClientRect() to detect the size and position of the target element, than place a rect element with box-shadow over it as the highlight area.
\\n
Because click events could not be triigered from the box-shadow area, Smartour place another transparent layer over the page, and bind layerEvent() to it to solve this problem.
\\n
The position of the highlight area and slot are absolute. Every time the page scrolled, the value of document.documentElement.scrollTop or document.documentElement.scrollLeft would be changed, and Smartour will use these values to correct the position.