diff options
| author | syuilo <syuilotan@yahoo.co.jp> | 2018-02-18 23:51:41 +0900 |
|---|---|---|
| committer | syuilo <syuilotan@yahoo.co.jp> | 2018-02-18 23:51:41 +0900 |
| commit | e01b9d3f16dacb6504c69a65b2f3c3e0f85c4094 (patch) | |
| tree | c503ed5aea35864ee8d46804039727cf309e4a67 /src/web/app/common | |
| parent | wip (diff) | |
| download | sharkey-e01b9d3f16dacb6504c69a65b2f3c3e0f85c4094.tar.gz sharkey-e01b9d3f16dacb6504c69a65b2f3c3e0f85c4094.tar.bz2 sharkey-e01b9d3f16dacb6504c69a65b2f3c3e0f85c4094.zip | |
wip
Diffstat (limited to 'src/web/app/common')
| -rw-r--r-- | src/web/app/common/define-widget.ts | 23 | ||||
| -rw-r--r-- | src/web/app/common/views/components/index.ts | 22 | ||||
| -rw-r--r-- | src/web/app/common/views/components/messaging-form.vue | 18 | ||||
| -rw-r--r-- | src/web/app/common/views/components/messaging.vue | 2 | ||||
| -rw-r--r-- | src/web/app/common/views/components/widgets/calendar.vue | 192 | ||||
| -rw-r--r-- | src/web/app/common/views/components/widgets/donation.vue | 45 | ||||
| -rw-r--r-- | src/web/app/common/views/components/widgets/nav.vue | 29 | ||||
| -rw-r--r-- | src/web/app/common/views/components/widgets/photo-stream.vue | 122 | ||||
| -rw-r--r-- | src/web/app/common/views/components/widgets/profile.vue | 125 | ||||
| -rw-r--r-- | src/web/app/common/views/components/widgets/slideshow.vue | 153 | ||||
| -rw-r--r-- | src/web/app/common/views/components/widgets/tips.vue | 108 |
11 files changed, 27 insertions, 812 deletions
diff --git a/src/web/app/common/define-widget.ts b/src/web/app/common/define-widget.ts index 4e83e37c6e..6088efd7e5 100644 --- a/src/web/app/common/define-widget.ts +++ b/src/web/app/common/define-widget.ts @@ -6,22 +6,13 @@ export default function<T extends object>(data: { }) { return Vue.extend({ props: { - wid: { - type: String, - required: true - }, - wplace: { - type: String, - required: true - }, - wprops: { - type: Object, - required: false + widget: { + type: Object } }, computed: { id(): string { - return this.wid; + return this.widget.id; } }, data() { @@ -32,19 +23,19 @@ export default function<T extends object>(data: { watch: { props(newProps, oldProps) { if (JSON.stringify(newProps) == JSON.stringify(oldProps)) return; - this.$root.$data.os.api('i/update_home', { + (this as any).api('i/update_home', { id: this.id, data: newProps }).then(() => { - this.$root.$data.os.i.client_settings.home.find(w => w.id == this.id).data = newProps; + (this as any).os.i.client_settings.home.find(w => w.id == this.id).data = newProps; }); } }, created() { if (this.props) { Object.keys(this.props).forEach(prop => { - if (this.wprops.hasOwnProperty(prop)) { - this.props[prop] = this.wprops[prop]; + if (this.widget.data.hasOwnProperty(prop)) { + this.props[prop] = this.widget.data[prop]; } }); } diff --git a/src/web/app/common/views/components/index.ts b/src/web/app/common/views/components/index.ts index 209a68fe52..646fa3b71c 100644 --- a/src/web/app/common/views/components/index.ts +++ b/src/web/app/common/views/components/index.ts @@ -5,6 +5,7 @@ import signup from './signup.vue'; import forkit from './forkit.vue'; import nav from './nav.vue'; import postHtml from './post-html'; +import pollEditor from './poll-editor.vue'; import reactionIcon from './reaction-icon.vue'; import reactionsViewer from './reactions-viewer.vue'; import time from './time.vue'; @@ -13,18 +14,17 @@ import uploader from './uploader.vue'; import specialMessage from './special-message.vue'; import streamIndicator from './stream-indicator.vue'; import ellipsis from './ellipsis.vue'; -import wNav from './widgets/nav.vue'; -import wCalendar from './widgets/calendar.vue'; -import wPhotoStream from './widgets/photo-stream.vue'; -import wSlideshow from './widgets/slideshow.vue'; -import wTips from './widgets/tips.vue'; -import wDonation from './widgets/donation.vue'; +import messaging from './messaging.vue'; +import messagingForm from './messaging-form.vue'; +import messagingRoom from './messaging-room.vue'; +import messagingMessage from './messaging-message.vue'; Vue.component('mk-signin', signin); Vue.component('mk-signup', signup); Vue.component('mk-forkit', forkit); Vue.component('mk-nav', nav); Vue.component('mk-post-html', postHtml); +Vue.component('mk-poll-editor', pollEditor); Vue.component('mk-reaction-icon', reactionIcon); Vue.component('mk-reactions-viewer', reactionsViewer); Vue.component('mk-time', time); @@ -33,9 +33,7 @@ Vue.component('mk-uploader', uploader); Vue.component('mk-special-message', specialMessage); Vue.component('mk-stream-indicator', streamIndicator); Vue.component('mk-ellipsis', ellipsis); -Vue.component('mkw-nav', wNav); -Vue.component('mkw-calendar', wCalendar); -Vue.component('mkw-photo-stream', wPhotoStream); -Vue.component('mkw-slideshoe', wSlideshow); -Vue.component('mkw-tips', wTips); -Vue.component('mkw-donation', wDonation); +Vue.component('mk-messaging', messaging); +Vue.component('mk-messaging-form', messagingForm); +Vue.component('mk-messaging-room', messagingRoom); +Vue.component('mk-messaging-message', messagingMessage); diff --git a/src/web/app/common/views/components/messaging-form.vue b/src/web/app/common/views/components/messaging-form.vue index 18d45790e4..37ac51509d 100644 --- a/src/web/app/common/views/components/messaging-form.vue +++ b/src/web/app/common/views/components/messaging-form.vue @@ -23,7 +23,7 @@ export default Vue.extend({ data() { return { text: null, - files: [], + file: null, sending: false }; }, @@ -49,17 +49,17 @@ export default Vue.extend({ }, chooseFileFromDrive() { - const w = new MkDriveChooserWindow({ - propsData: { - multiple: true - } - }).$mount(); - w.$once('selected', files => { - files.forEach(this.addFile); + (this as any).apis.chooseDriveFile({ + multiple: false + }).then(file => { + this.file = file; }); - document.body.appendChild(w.$el); }, + upload() { + // TODO + } + send() { this.sending = true; (this as any).api('messaging/messages/create', { diff --git a/src/web/app/common/views/components/messaging.vue b/src/web/app/common/views/components/messaging.vue index 1b56382b08..c0b3a1924b 100644 --- a/src/web/app/common/views/components/messaging.vue +++ b/src/web/app/common/views/components/messaging.vue @@ -1,6 +1,6 @@ <template> <div class="mk-messaging" :data-compact="compact"> - <div class="search" v-if="!opts.compact"> + <div class="search" v-if="!compact"> <div class="form"> <label for="search-input">%fa:search%</label> <input v-model="q" type="search" @input="search" @keydown="onSearchKeydown" placeholder="%i18n:common.tags.mk-messaging.search-user%"/> diff --git a/src/web/app/common/views/components/widgets/calendar.vue b/src/web/app/common/views/components/widgets/calendar.vue deleted file mode 100644 index 308f43cd99..0000000000 --- a/src/web/app/common/views/components/widgets/calendar.vue +++ /dev/null @@ -1,192 +0,0 @@ -<template> -<div class="mkw-calendar" - :data-melt="props.design == 1" - :data-special="special" -> - <div class="calendar" :data-is-holiday="isHoliday"> - <p class="month-and-year"> - <span class="year">{{ year }}年</span> - <span class="month">{{ month }}月</span> - </p> - <p class="day">{{ day }}日</p> - <p class="week-day">{{ weekDay }}曜日</p> - </div> - <div class="info"> - <div> - <p>今日:<b>{{ dayP.toFixed(1) }}%</b></p> - <div class="meter"> - <div class="val" :style="{ width: `${dayP}%` }"></div> - </div> - </div> - <div> - <p>今月:<b>{{ monthP.toFixed(1) }}%</b></p> - <div class="meter"> - <div class="val" :style="{ width: `${monthP}%` }"></div> - </div> - </div> - <div> - <p>今年:<b>{{ yearP.toFixed(1) }}%</b></p> - <div class="meter"> - <div class="val" :style="{ width: `${yearP}%` }"></div> - </div> - </div> - </div> -</div> -</template> - -<script lang="ts"> -import define from '../../../define-widget'; -export default define({ - name: 'calendar', - props: { - design: 0 - } -}).extend({ - data() { - return { - now: new Date(), - year: null, - month: null, - day: null, - weekDay: null, - yearP: null, - dayP: null, - monthP: null, - isHoliday: null, - special: null, - clock: null - }; - }, - created() { - this.tick(); - this.clock = setInterval(this.tick, 1000); - }, - beforeDestroy() { - clearInterval(this.clock); - }, - methods: { - func() { - if (this.props.design == 2) { - this.props.design = 0; - } else { - this.props.design++; - } - }, - tick() { - const now = new Date(); - const nd = now.getDate(); - const nm = now.getMonth(); - const ny = now.getFullYear(); - - this.year = ny; - this.month = nm + 1; - this.day = nd; - this.weekDay = ['日', '月', '火', '水', '木', '金', '土'][now.getDay()]; - - const dayNumer = now.getTime() - new Date(ny, nm, nd).getTime(); - const dayDenom = 1000/*ms*/ * 60/*s*/ * 60/*m*/ * 24/*h*/; - const monthNumer = now.getTime() - new Date(ny, nm, 1).getTime(); - const monthDenom = new Date(ny, nm + 1, 1).getTime() - new Date(ny, nm, 1).getTime(); - const yearNumer = now.getTime() - new Date(ny, 0, 1).getTime(); - const yearDenom = new Date(ny + 1, 0, 1).getTime() - new Date(ny, 0, 1).getTime(); - - this.dayP = dayNumer / dayDenom * 100; - this.monthP = monthNumer / monthDenom * 100; - this.yearP = yearNumer / yearDenom * 100; - - this.isHoliday = now.getDay() == 0 || now.getDay() == 6; - - this.special = - nm == 0 && nd == 1 ? 'on-new-years-day' : - false; - } - } -}); -</script> - -<style lang="stylus" scoped> -.mkw-calendar - padding 16px 0 - color #777 - background #fff - border solid 1px rgba(0, 0, 0, 0.075) - border-radius 6px - - &[data-special='on-new-years-day'] - border-color #ef95a0 - - &[data-melt] - background transparent - border none - - &:after - content "" - display block - clear both - - > .calendar - float left - width 60% - text-align center - - &[data-is-holiday] - > .day - color #ef95a0 - - > p - margin 0 - line-height 18px - font-size 14px - - > span - margin 0 4px - - > .day - margin 10px 0 - line-height 32px - font-size 28px - - > .info - display block - float left - width 40% - padding 0 16px 0 0 - - > div - margin-bottom 8px - - &:last-child - margin-bottom 4px - - > p - margin 0 0 2px 0 - font-size 12px - line-height 18px - color #888 - - > b - margin-left 2px - - > .meter - width 100% - overflow hidden - background #eee - border-radius 8px - - > .val - height 4px - background $theme-color - - &:nth-child(1) - > .meter > .val - background #f7796c - - &:nth-child(2) - > .meter > .val - background #a1de41 - - &:nth-child(3) - > .meter > .val - background #41ddde - -</style> diff --git a/src/web/app/common/views/components/widgets/donation.vue b/src/web/app/common/views/components/widgets/donation.vue deleted file mode 100644 index 50adc531bf..0000000000 --- a/src/web/app/common/views/components/widgets/donation.vue +++ /dev/null @@ -1,45 +0,0 @@ -<template> -<div class="mkw-donation"> - <article> - <h1>%fa:heart%%i18n:desktop.tags.mk-donation-home-widget.title%</h1> - <p> - {{ '%i18n:desktop.tags.mk-donation-home-widget.text%'.substr(0, '%i18n:desktop.tags.mk-donation-home-widget.text%'.indexOf('{')) }} - <a href="/syuilo" data-user-preview="@syuilo">@syuilo</a> - {{ '%i18n:desktop.tags.mk-donation-home-widget.text%'.substr('%i18n:desktop.tags.mk-donation-home-widget.text%'.indexOf('}') + 1) }} - </p> - </article> -</div> -</template> - -<script lang="ts"> -import define from '../../../define-widget'; -export default define({ - name: 'donation' -}); -</script> - -<style lang="stylus" scoped> -.mkw-donation - background #fff - border solid 1px #ead8bb - border-radius 6px - - > article - padding 20px - - > h1 - margin 0 0 5px 0 - font-size 1em - color #888 - - > [data-fa] - margin-right 0.25em - - > p - display block - z-index 1 - margin 0 - font-size 0.8em - color #999 - -</style> diff --git a/src/web/app/common/views/components/widgets/nav.vue b/src/web/app/common/views/components/widgets/nav.vue deleted file mode 100644 index 77e1eea492..0000000000 --- a/src/web/app/common/views/components/widgets/nav.vue +++ /dev/null @@ -1,29 +0,0 @@ -<template> -<div class="mkw-nav"> - <mk-nav-links/> -</div> -</template> - -<script lang="ts"> -import define from '../../../define-widget'; -export default define({ - name: 'nav' -}); -</script> - -<style lang="stylus" scoped> -.mkw-nav - padding 16px - font-size 12px - color #aaa - background #fff - border solid 1px rgba(0, 0, 0, 0.075) - border-radius 6px - - a - color #999 - - i - color #ccc - -</style> diff --git a/src/web/app/common/views/components/widgets/photo-stream.vue b/src/web/app/common/views/components/widgets/photo-stream.vue deleted file mode 100644 index 4d6b660696..0000000000 --- a/src/web/app/common/views/components/widgets/photo-stream.vue +++ /dev/null @@ -1,122 +0,0 @@ -<template> -<div class="mkw-photo-stream" :data-melt="props.design == 2"> - <p class="title" v-if="props.design == 0">%fa:camera%%i18n:desktop.tags.mk-photo-stream-home-widget.title%</p> - <p class="fetching" v-if="fetching">%fa:spinner .pulse .fw%%i18n:common.loading%<mk-ellipsis/></p> - <div class="stream" v-if="!fetching && images.length > 0"> - <div v-for="image in images" :key="image.id" class="img" :style="`background-image: url(${image.url}?thumbnail&size=256)`"></div> - </div> - <p class="empty" v-if="!fetching && images.length == 0">%i18n:desktop.tags.mk-photo-stream-home-widget.no-photos%</p> -</div> -</template> - -<script lang="ts"> -import define from '../../../define-widget'; -export default define({ - name: 'photo-stream', - props: { - design: 0 - } -}).extend({ - data() { - return { - images: [], - fetching: true, - connection: null, - connectionId: null - }; - }, - mounted() { - this.connection = (this as any).os.stream.getConnection(); - this.connectionId = (this as any).os.stream.use(); - - this.connection.on('drive_file_created', this.onDriveFileCreated); - - (this as any).api('drive/stream', { - type: 'image/*', - limit: 9 - }).then(images => { - this.fetching = false; - this.images = images; - }); - }, - beforeDestroy() { - this.connection.off('drive_file_created', this.onDriveFileCreated); - (this as any).os.stream.dispose(this.connectionId); - }, - methods: { - onDriveFileCreated(file) { - if (/^image\/.+$/.test(file.type)) { - this.images.unshift(file); - if (this.images.length > 9) this.images.pop(); - } - }, - func() { - if (this.props.design == 2) { - this.props.design = 0; - } else { - this.props.design++; - } - } - } -}); -</script> - -<style lang="stylus" scoped> -.mkw-photo-stream - background #fff - border solid 1px rgba(0, 0, 0, 0.075) - border-radius 6px - - &[data-melt] - background transparent !important - border none !important - - > .stream - padding 0 - - > .img - border solid 4px transparent - border-radius 8px - - > .title - z-index 1 - margin 0 - padding 0 16px - line-height 42px - font-size 0.9em - font-weight bold - color #888 - box-shadow 0 1px rgba(0, 0, 0, 0.07) - - > [data-fa] - margin-right 4px - - > .stream - display -webkit-flex - display -moz-flex - display -ms-flex - display flex - justify-content center - flex-wrap wrap - padding 8px - - > .img - flex 1 1 33% - width 33% - height 80px - background-position center center - background-size cover - border solid 2px transparent - border-radius 4px - - > .fetching - > .empty - margin 0 - padding 16px - text-align center - color #aaa - - > [data-fa] - margin-right 4px - -</style> diff --git a/src/web/app/common/views/components/widgets/profile.vue b/src/web/app/common/views/components/widgets/profile.vue deleted file mode 100644 index d64ffad931..0000000000 --- a/src/web/app/common/views/components/widgets/profile.vue +++ /dev/null @@ -1,125 +0,0 @@ -<template> -<div class="mkw-profile" - :data-compact="props.design == 1 || props.design == 2" - :data-melt="props.design == 2" -> - <div class="banner" - style={ I.banner_url ? 'background-image: url(' + I.banner_url + '?thumbnail&size=256)' : '' } - title="クリックでバナー編集" - @click="wapi_setBanner" - ></div> - <img class="avatar" - src={ I.avatar_url + '?thumbnail&size=96' } - @click="wapi_setAvatar" - alt="avatar" - title="クリックでアバター編集" - v-user-preview={ I.id } - /> - <a class="name" href={ '/' + I.username }>{ I.name }</a> - <p class="username">@{ I.username }</p> -</div> -</template> - -<script lang="ts"> -import define from '../../../define-widget'; -export default define({ - name: 'profile', - props: { - design: 0 - } -}).extend({ - methods: { - func() { - if (this.props.design == 2) { - this.props.design = 0; - } else { - this.props.design++; - } - } - } -}); -</script> - -<style lang="stylus" scoped> -.mkw-profile - overflow hidden - background #fff - border solid 1px rgba(0, 0, 0, 0.075) - border-radius 6px - - &[data-compact] - > .banner:before - content "" - display block - width 100% - height 100% - background rgba(0, 0, 0, 0.5) - - > .avatar - top ((100px - 58px) / 2) - left ((100px - 58px) / 2) - border none - border-radius 100% - box-shadow 0 0 16px rgba(0, 0, 0, 0.5) - - > .name - position absolute - top 0 - left 92px - margin 0 - line-height 100px - color #fff - text-shadow 0 0 8px rgba(0, 0, 0, 0.5) - - > .username - display none - - &[data-melt] - background transparent !important - border none !important - - > .banner - visibility hidden - - > .avatar - box-shadow none - - > .name - color #666 - text-shadow none - - > .banner - height 100px - background-color #f5f5f5 - background-size cover - background-position center - cursor pointer - - > .avatar - display block - position absolute - top 76px - left 16px - width 58px - height 58px - margin 0 - border solid 3px #fff - border-radius 8px - vertical-align bottom - cursor pointer - - > .name - display block - margin 10px 0 0 84px - line-height 16px - font-weight bold - color #555 - - > .username - display block - margin 4px 0 8px 84px - line-height 16px - font-size 0.9em - color #999 - -</style> diff --git a/src/web/app/common/views/components/widgets/slideshow.vue b/src/web/app/common/views/components/widgets/slideshow.vue deleted file mode 100644 index ea8e38a2c1..0000000000 --- a/src/web/app/common/views/components/widgets/slideshow.vue +++ /dev/null @@ -1,153 +0,0 @@ -<template> -<div class="mkw-slideshow"> - <div @click="choose"> - <p v-if="data.folder === undefined">クリックしてフォルダを指定してください</p> - <p v-if="data.folder !== undefined && images.length == 0 && !fetching">このフォルダには画像がありません</p> - <div ref="slideA" class="slide a"></div> - <div ref="slideB" class="slide b"></div> - </div> - <button @click="resize">%fa:expand%</button> -</div> -</template> - -<script lang="ts"> -import * as anime from 'animejs'; -import define from '../../../define-widget'; -export default define({ - name: 'slideshow', - props: { - folder: undefined, - size: 0 - } -}).extend({ - data() { - return { - images: [], - fetching: true, - clock: null - }; - }, - mounted() { - this.$nextTick(() => { - this.applySize(); - }); - - if (this.props.folder !== undefined) { - this.fetch(); - } - - this.clock = setInterval(this.change, 10000); - }, - beforeDestroy() { - clearInterval(this.clock); - }, - methods: { - applySize() { - let h; - - if (this.props.size == 1) { - h = 250; - } else { - h = 170; - } - - this.$el.style.height = `${h}px`; - }, - resize() { - if (this.props.size == 1) { - this.props.size = 0; - } else { - this.props.size++; - } - - this.applySize(); - }, - change() { - if (this.images.length == 0) return; - - const index = Math.floor(Math.random() * this.images.length); - const img = `url(${ this.images[index].url }?thumbnail&size=1024)`; - - (this.$refs.slideB as any).style.backgroundImage = img; - - anime({ - targets: this.$refs.slideB, - opacity: 1, - duration: 1000, - easing: 'linear', - complete: () => { - (this.$refs.slideA as any).style.backgroundImage = img; - anime({ - targets: this.$refs.slideB, - opacity: 0, - duration: 0 - }); - } - }); - }, - fetch() { - this.fetching = true; - - (this as any).api('drive/files', { - folder_id: this.props.folder, - type: 'image/*', - limit: 100 - }).then(images => { - this.fetching = false; - this.images = images; - (this.$refs.slideA as any).style.backgroundImage = ''; - (this.$refs.slideB as any).style.backgroundImage = ''; - this.change(); - }); - }, - choose() { - (this as any).apis.chooseDriveFolder().then(folder => { - this.props.folder = folder ? folder.id : null; - this.fetch(); - }); - } - } -}); -</script> - -<style lang="stylus" scoped> -.mkw-slideshow - overflow hidden - background #fff - border solid 1px rgba(0, 0, 0, 0.075) - border-radius 6px - - &:hover > button - display block - - > button - position absolute - left 0 - bottom 0 - display none - padding 4px - font-size 24px - color #fff - text-shadow 0 0 8px #000 - - > div - width 100% - height 100% - cursor pointer - - > * - pointer-events none - - > .slide - position absolute - top 0 - left 0 - width 100% - height 100% - background-size cover - background-position center - - &.b - opacity 0 - -</style> diff --git a/src/web/app/common/views/components/widgets/tips.vue b/src/web/app/common/views/components/widgets/tips.vue deleted file mode 100644 index d9e1fbc940..0000000000 --- a/src/web/app/common/views/components/widgets/tips.vue +++ /dev/null @@ -1,108 +0,0 @@ -<template> -<div class="mkw-tips"> - <p ref="tip">%fa:R lightbulb%<span v-html="tip"></span></p> -</div> -</template> - -<script lang="ts"> -import * as anime from 'animejs'; -import define from '../../../define-widget'; - -const tips = [ - '<kbd>t</kbd>でタイムラインにフォーカスできます', - '<kbd>p</kbd>または<kbd>n</kbd>で投稿フォームを開きます', - '投稿フォームにはファイルをドラッグ&ドロップできます', - '投稿フォームにクリップボードにある画像データをペーストできます', - 'ドライブにファイルをドラッグ&ドロップしてアップロードできます', - 'ドライブでファイルをドラッグしてフォルダ移動できます', - 'ドライブでフォルダをドラッグしてフォルダ移動できます', - 'ホームは設定からカスタマイズできます', - 'MisskeyはMIT Licenseです', - 'タイムマシンウィジェットを利用すると、簡単に過去のタイムラインに遡れます', - '投稿の ... をクリックして、投稿をユーザーページにピン留めできます', - 'ドライブの容量は(デフォルトで)1GBです', - '投稿に添付したファイルは全てドライブに保存されます', - 'ホームのカスタマイズ中、ウィジェットを右クリックしてデザインを変更できます', - 'タイムライン上部にもウィジェットを設置できます', - '投稿をダブルクリックすると詳細が見れます', - '「**」でテキストを囲むと**強調表示**されます', - 'チャンネルウィジェットを利用すると、よく利用するチャンネルを素早く確認できます', - 'いくつかのウィンドウはブラウザの外に切り離すことができます', - 'カレンダーウィジェットのパーセンテージは、経過の割合を示しています', - 'APIを利用してbotの開発なども行えます', - 'MisskeyはLINEを通じてでも利用できます', - 'まゆかわいいよまゆ', - 'Misskeyは2014年にサービスを開始しました', - '対応ブラウザではMisskeyを開いていなくても通知を受け取れます' -] - -export default define({ - name: 'tips' -}).extend({ - data() { - return { - tip: null, - clock: null - }; - }, - mounted() { - this.$nextTick(() => { - this.set(); - }); - - this.clock = setInterval(this.change, 20000); - }, - beforeDestroy() { - clearInterval(this.clock); - }, - methods: { - set() { - this.tip = tips[Math.floor(Math.random() * tips.length)]; - }, - change() { - anime({ - targets: this.$refs.tip, - opacity: 0, - duration: 500, - easing: 'linear', - complete: this.set - }); - - setTimeout(() => { - anime({ - targets: this.$refs.tip, - opacity: 1, - duration: 500, - easing: 'linear' - }); - }, 500); - } - } -}); -</script> - -<style lang="stylus" scoped> -.mkw-tips - overflow visible !important - - > p - display block - margin 0 - padding 0 12px - text-align center - font-size 0.7em - color #999 - - > [data-fa] - margin-right 4px - - kbd - display inline - padding 0 6px - margin 0 2px - font-size 1em - font-family inherit - border solid 1px #999 - border-radius 2px - -</style> |