enhance(client): RSSティッカーで表示順序をシャッフルできるように

This commit is contained in:
syuilo
2022-07-15 17:12:08 +09:00
parent 165c4b2c00
commit 6f45208ab6
7 changed files with 39 additions and 1 deletions

View File

@ -28,6 +28,9 @@
<MkInput v-model="statusbar.props.url" manual-save class="_formBlock" type="url">
<template #label>URL</template>
</MkInput>
<MkSwitch v-model="statusbar.props.shuffle" class="_formBlock">
<template #label>{{ i18n.ts.shuffle }}</template>
</MkSwitch>
<MkInput v-model="statusbar.props.refreshIntervalSec" manual-save class="_formBlock" type="number">
<template #label>{{ i18n.ts.refreshInterval }}</template>
</MkInput>
@ -100,6 +103,7 @@ watch(() => statusbar.type, () => {
if (statusbar.type === 'rss') {
statusbar.name = 'NEWS';
statusbar.props.url = 'http://feeds.afpbb.com/rss/afpbb/afpbbnews';
statusbar.props.shuffle = true;
statusbar.props.refreshIntervalSec = 120;
statusbar.props.display = 'marquee';
statusbar.props.marqueeDuration = 100;

View File

@ -0,0 +1,19 @@
/**
* 配列をシャッフル (破壊的)
*/
export function shuffle<T extends any[]>(array: T): T {
let currentIndex = array.length, randomIndex;
// While there remain elements to shuffle.
while (currentIndex !== 0) {
// Pick a remaining element.
randomIndex = Math.floor(Math.random() * currentIndex);
currentIndex--;
// And swap it with the current element.
[array[currentIndex], array[randomIndex]] = [
array[randomIndex], array[currentIndex]];
}
return array;
}

View File

@ -20,9 +20,11 @@ import { computed, defineAsyncComponent, ref, toRef, watch } from 'vue';
import MarqueeText from '@/components/marquee.vue';
import * as os from '@/os';
import { useInterval } from '@/scripts/use-interval';
import { shuffle } from '@/scripts/shuffle';
const props = defineProps<{
url?: string;
shuffle?: boolean;
display?: 'marquee' | 'oneByOne';
marqueeDuration?: number;
marqueeReverse?: boolean;
@ -37,6 +39,9 @@ let key = $ref(0);
const tick = () => {
fetch(`/api/fetch-rss?url=${props.url}`, {}).then(res => {
res.json().then(feed => {
if (props.shuffle) {
shuffle(feed.items);
}
items.value = feed.items;
fetching.value = false;
key++;

View File

@ -10,7 +10,7 @@
}]"
>
<span class="name">{{ x.name }}</span>
<XRss v-if="x.type === 'rss'" class="body" :refresh-interval-sec="x.props.refreshIntervalSec" :marquee-duration="x.props.marqueeDuration" :marquee-reverse="x.props.marqueeReverse" :display="x.props.display" :url="x.props.url"/>
<XRss v-if="x.type === 'rss'" class="body" :refresh-interval-sec="x.props.refreshIntervalSec" :marquee-duration="x.props.marqueeDuration" :marquee-reverse="x.props.marqueeReverse" :display="x.props.display" :url="x.props.url" :shuffle="x.props.shuffle"/>
<XFederation v-else-if="x.type === 'federation'" class="body" :refresh-interval-sec="x.props.refreshIntervalSec" :marquee-duration="x.props.marqueeDuration" :marquee-reverse="x.props.marqueeReverse" :display="x.props.display" :colored="x.props.colored"/>
<XUserList v-else-if="x.type === 'userList'" class="body" :refresh-interval-sec="x.props.refreshIntervalSec" :marquee-duration="x.props.marqueeDuration" :marquee-reverse="x.props.marqueeReverse" :display="x.props.display" :user-list-id="x.props.userListId"/>
</div>

View File

@ -26,6 +26,7 @@ import { GetFormResultType } from '@/scripts/form';
import * as os from '@/os';
import MkContainer from '@/components/ui/container.vue';
import { useInterval } from '@/scripts/use-interval';
import { shuffle } from '@/scripts/shuffle';
const name = 'rssTicker';
@ -34,6 +35,10 @@ const widgetPropsDef = {
type: 'string' as const,
default: 'http://feeds.afpbb.com/rss/afpbb/afpbbnews',
},
shuffle: {
type: 'boolean' as const,
default: true,
},
refreshIntervalSec: {
type: 'number' as const,
default: 60,
@ -80,6 +85,9 @@ let key = $ref(0);
const tick = () => {
fetch(`/api/fetch-rss?url=${widgetProps.url}`, {}).then(res => {
res.json().then(feed => {
if (widgetProps.shuffle) {
shuffle(feed.items);
}
items.value = feed.items;
fetching.value = false;
key++;