merge: Merge Upstream Changes (!408)
View MR for information: https://activitypub.software/TransFem-org/Sharkey/-/merge_requests/408 Approved-by: dakkar <dakkar@thenautilus.net> Approved-by: Amelia Yukii <amelia.yukii@shourai.de>
This commit is contained in:
commit
4007fbb8d8
149 changed files with 1936 additions and 697 deletions
|
|
@ -31,15 +31,15 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||
</template>
|
||||
<template v-else-if="provider === 'mcaptcha'">
|
||||
<MkInput v-model="mcaptchaSiteKey">
|
||||
<template #prefix><i class="ti ti-key"></i></template>
|
||||
<template #prefix><i class="ph-key ph-bold ph-lg"></i></template>
|
||||
<template #label>{{ i18n.ts.mcaptchaSiteKey }}</template>
|
||||
</MkInput>
|
||||
<MkInput v-model="mcaptchaSecretKey">
|
||||
<template #prefix><i class="ti ti-key"></i></template>
|
||||
<template #prefix><i class="ph-key ph-bold ph-lg"></i></template>
|
||||
<template #label>{{ i18n.ts.mcaptchaSecretKey }}</template>
|
||||
</MkInput>
|
||||
<MkInput v-model="mcaptchaInstanceUrl">
|
||||
<template #prefix><i class="ti ti-link"></i></template>
|
||||
<template #prefix><i class="ph-globe-simple ph-bold ph-lg"></i></template>
|
||||
<template #label>{{ i18n.ts.mcaptchaInstanceUrl }}</template>
|
||||
</MkInput>
|
||||
<FormSlot v-if="mcaptchaSiteKey && mcaptchaInstanceUrl">
|
||||
|
|
|
|||
|
|
@ -158,9 +158,9 @@ function save() {
|
|||
themeColor: themeColor.value === '' ? null : themeColor.value,
|
||||
defaultLightTheme: defaultLightTheme.value === '' ? null : defaultLightTheme.value,
|
||||
defaultDarkTheme: defaultDarkTheme.value === '' ? null : defaultDarkTheme.value,
|
||||
infoImageUrl: infoImageUrl.value,
|
||||
notFoundImageUrl: notFoundImageUrl.value,
|
||||
serverErrorImageUrl: serverErrorImageUrl.value,
|
||||
infoImageUrl: infoImageUrl.value === '' ? null : infoImageUrl.value,
|
||||
notFoundImageUrl: notFoundImageUrl.value === '' ? null : notFoundImageUrl.value,
|
||||
serverErrorImageUrl: serverErrorImageUrl.value === '' ? null : serverErrorImageUrl.value,
|
||||
manifestJsonOverride: manifestJsonOverride.value === '' ? '{}' : JSON.stringify(JSON5.parse(manifestJsonOverride.value)),
|
||||
}).then(() => {
|
||||
fetchInstance();
|
||||
|
|
|
|||
|
|
@ -49,6 +49,11 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||
<template #caption>{{ i18n.ts.sensitiveWordsDescription }}<br>{{ i18n.ts.sensitiveWordsDescription2 }}</template>
|
||||
</MkTextarea>
|
||||
|
||||
<MkTextarea v-model="prohibitedWords">
|
||||
<template #label>{{ i18n.ts.prohibitedWords }}</template>
|
||||
<template #caption>{{ i18n.ts.prohibitedWordsDescription }}<br>{{ i18n.ts.prohibitedWordsDescription2 }}</template>
|
||||
</MkTextarea>
|
||||
|
||||
<MkTextarea v-model="hiddenTags">
|
||||
<template #label>{{ i18n.ts.hiddenTags }}</template>
|
||||
<template #caption>{{ i18n.ts.hiddenTagsDescription }}</template>
|
||||
|
|
@ -87,6 +92,7 @@ const emailRequiredForSignup = ref<boolean>(false);
|
|||
const approvalRequiredForSignup = ref<boolean>(false);
|
||||
const bubbleTimelineEnabled = ref<boolean>(false);
|
||||
const sensitiveWords = ref<string>('');
|
||||
const prohibitedWords = ref<string>('');
|
||||
const hiddenTags = ref<string>('');
|
||||
const preservedUsernames = ref<string>('');
|
||||
const bubbleTimeline = ref<string>('');
|
||||
|
|
@ -99,6 +105,7 @@ async function init() {
|
|||
emailRequiredForSignup.value = meta.emailRequiredForSignup;
|
||||
approvalRequiredForSignup.value = meta.approvalRequiredForSignup;
|
||||
sensitiveWords.value = meta.sensitiveWords.join('\n');
|
||||
prohibitedWords.value = meta.prohibitedWords.join('\n');
|
||||
hiddenTags.value = meta.hiddenTags.join('\n');
|
||||
preservedUsernames.value = meta.preservedUsernames.join('\n');
|
||||
tosUrl.value = meta.tosUrl;
|
||||
|
|
@ -115,6 +122,7 @@ function save() {
|
|||
tosUrl: tosUrl.value,
|
||||
privacyPolicyUrl: privacyPolicyUrl.value,
|
||||
sensitiveWords: sensitiveWords.value.split('\n'),
|
||||
prohibitedWords: prohibitedWords.value.split('\n'),
|
||||
hiddenTags: hiddenTags.value.split('\n'),
|
||||
preservedUsernames: preservedUsernames.value.split('\n'),
|
||||
bubbleInstances: bubbleTimeline.value.split('\n'),
|
||||
|
|
|
|||
|
|
@ -42,14 +42,14 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||
<template #label>Use TrueMail API</template>
|
||||
</MkSwitch>
|
||||
<MkInput v-model="truemailInstance">
|
||||
<template #prefix><i class="ti ti-key"></i></template>
|
||||
<template #prefix><i class="ph-key ph-bold ph-lg"></i></template>
|
||||
<template #label>TrueMail API Instance</template>
|
||||
</MkInput>
|
||||
<MkInput v-model="truemailAuthKey">
|
||||
<template #prefix><i class="ti ti-key"></i></template>
|
||||
<template #prefix><i class="ph-key ph-bold ph-lg"></i></template>
|
||||
<template #label>TrueMail API Auth Key</template>
|
||||
</MkInput>
|
||||
<MkButton primary @click="save"><i class="ti ti-device-floppy"></i> {{ i18n.ts.save }}</MkButton>
|
||||
<MkButton primary @click="save"><i class="ph-floppy-disk ph-bold ph-lg"></i> {{ i18n.ts.save }}</MkButton>
|
||||
</div>
|
||||
</MkFolder>
|
||||
|
||||
|
|
|
|||
|
|
@ -893,7 +893,6 @@ function getGameImageDriveFile() {
|
|||
formData.append('file', blob);
|
||||
formData.append('name', `bubble-game-${Date.now()}.png`);
|
||||
formData.append('isSensitive', 'false');
|
||||
formData.append('comment', 'null');
|
||||
formData.append('i', $i.token);
|
||||
if (defaultStore.state.uploadFolder) {
|
||||
formData.append('folderId', defaultStore.state.uploadFolder);
|
||||
|
|
|
|||
|
|
@ -39,7 +39,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||
<MkSwitch v-model="isBlocked" :disabled="!meta || !instance" @update:modelValue="toggleBlock">{{ i18n.ts.blockThisInstance }}</MkSwitch>
|
||||
<MkSwitch v-model="isSilenced" :disabled="!meta || !instance" @update:modelValue="toggleSilenced">{{ i18n.ts.silenceThisInstance }}</MkSwitch>
|
||||
<MkSwitch v-model="isNSFW" :disabled="!instance" @update:modelValue="toggleNSFW">Mark as NSFW</MkSwitch>
|
||||
<MkButton @click="refreshMetadata"><i class="ti ti-refresh"></i> Refresh metadata</MkButton>
|
||||
<MkButton @click="refreshMetadata"><i class="ph-arrows-clockwise ph-bold ph-lg"></i> Refresh metadata</MkButton>
|
||||
</div>
|
||||
</FormSection>
|
||||
|
||||
|
|
|
|||
|
|
@ -36,13 +36,13 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||
<div :class="$style.gamePreviews">
|
||||
<MkA v-for="g in items" :key="g.id" v-panel :class="[$style.gamePreview, !g.isStarted && !g.isEnded && $style.gamePreviewWaiting, g.isStarted && !g.isEnded && $style.gamePreviewActive]" tabindex="-1" :to="`/reversi/g/${g.id}`">
|
||||
<div :class="$style.gamePreviewPlayers">
|
||||
<span v-if="g.winnerId === g.user1Id" style="margin-right: 0.75em; color: var(--accent); font-weight: bold;"><i class="ti ti-trophy"></i></span>
|
||||
<span v-if="g.winnerId === g.user2Id" style="margin-right: 0.75em; visibility: hidden;"><i class="ti ti-x"></i></span>
|
||||
<span v-if="g.winnerId === g.user1Id" style="margin-right: 0.75em; color: var(--accent); font-weight: bold;"><i class="ph-trophy ph-bold ph-lg"></i></span>
|
||||
<span v-if="g.winnerId === g.user2Id" style="margin-right: 0.75em; visibility: hidden;"><i class="ph-x ph-bold ph-lg"></i></span>
|
||||
<MkAvatar :class="$style.gamePreviewPlayersAvatar" :user="g.user1"/>
|
||||
<span style="margin: 0 1em;">vs</span>
|
||||
<MkAvatar :class="$style.gamePreviewPlayersAvatar" :user="g.user2"/>
|
||||
<span v-if="g.winnerId === g.user1Id" style="margin-left: 0.75em; visibility: hidden;"><i class="ti ti-x"></i></span>
|
||||
<span v-if="g.winnerId === g.user2Id" style="margin-left: 0.75em; color: var(--accent); font-weight: bold;"><i class="ti ti-trophy"></i></span>
|
||||
<span v-if="g.winnerId === g.user1Id" style="margin-left: 0.75em; visibility: hidden;"><i class="ph-x ph-bold ph-lg"></i></span>
|
||||
<span v-if="g.winnerId === g.user2Id" style="margin-left: 0.75em; color: var(--accent); font-weight: bold;"><i class="ph-trophy ph-bold ph-lg"></i></span>
|
||||
</div>
|
||||
<div :class="$style.gamePreviewFooter">
|
||||
<span v-if="g.isStarted && !g.isEnded" :class="$style.gamePreviewStatusActive">{{ i18n.ts._reversi.playing }}</span>
|
||||
|
|
@ -63,13 +63,13 @@ SPDX-License-Identifier: AGPL-3.0-only
|
|||
<div :class="$style.gamePreviews">
|
||||
<MkA v-for="g in items" :key="g.id" v-panel :class="[$style.gamePreview, !g.isStarted && !g.isEnded && $style.gamePreviewWaiting, g.isStarted && !g.isEnded && $style.gamePreviewActive]" tabindex="-1" :to="`/reversi/g/${g.id}`">
|
||||
<div :class="$style.gamePreviewPlayers">
|
||||
<span v-if="g.winnerId === g.user1Id" style="margin-right: 0.75em; color: var(--accent); font-weight: bold;"><i class="ti ti-trophy"></i></span>
|
||||
<span v-if="g.winnerId === g.user2Id" style="margin-right: 0.75em; visibility: hidden;"><i class="ti ti-x"></i></span>
|
||||
<span v-if="g.winnerId === g.user1Id" style="margin-right: 0.75em; color: var(--accent); font-weight: bold;"><i class="ph-trophy ph-bold ph-lg"></i></span>
|
||||
<span v-if="g.winnerId === g.user2Id" style="margin-right: 0.75em; visibility: hidden;"><i class="ph-x ph-bold ph-lg"></i></span>
|
||||
<MkAvatar :class="$style.gamePreviewPlayersAvatar" :user="g.user1"/>
|
||||
<span style="margin: 0 1em;">vs</span>
|
||||
<MkAvatar :class="$style.gamePreviewPlayersAvatar" :user="g.user2"/>
|
||||
<span v-if="g.winnerId === g.user1Id" style="margin-left: 0.75em; visibility: hidden;"><i class="ti ti-x"></i></span>
|
||||
<span v-if="g.winnerId === g.user2Id" style="margin-left: 0.75em; color: var(--accent); font-weight: bold;"><i class="ti ti-trophy"></i></span>
|
||||
<span v-if="g.winnerId === g.user1Id" style="margin-left: 0.75em; visibility: hidden;"><i class="ph-x ph-bold ph-lg"></i></span>
|
||||
<span v-if="g.winnerId === g.user2Id" style="margin-left: 0.75em; color: var(--accent); font-weight: bold;"><i class="ph-trophy ph-bold ph-lg"></i></span>
|
||||
</div>
|
||||
<div :class="$style.gamePreviewFooter">
|
||||
<span v-if="g.isStarted && !g.isEnded" :class="$style.gamePreviewStatusActive">{{ i18n.ts._reversi.playing }}</span>
|
||||
|
|
|
|||
|
|
@ -172,7 +172,7 @@ const chooseEmoji = (ev: MouseEvent) => pickEmoji(pinnedEmojis, ev);
|
|||
const setDefaultEmoji = () => setDefault(pinnedEmojis);
|
||||
|
||||
function previewReaction(ev: MouseEvent) {
|
||||
reactionPicker.show(getHTMLElement(ev));
|
||||
reactionPicker.show(getHTMLElement(ev), null);
|
||||
}
|
||||
|
||||
function previewEmoji(ev: MouseEvent) {
|
||||
|
|
|
|||
|
|
@ -132,6 +132,7 @@ import { langmap } from '@/scripts/langmap.js';
|
|||
import { definePageMetadata } from '@/scripts/page-metadata.js';
|
||||
import { claimAchievement } from '@/scripts/achievements.js';
|
||||
import { defaultStore } from '@/store.js';
|
||||
import { globalEvents } from '@/events.js';
|
||||
import MkInfo from '@/components/MkInfo.vue';
|
||||
import MkTextarea from '@/components/MkTextarea.vue';
|
||||
|
||||
|
|
@ -158,7 +159,7 @@ const profile = reactive({
|
|||
lang: $i.lang,
|
||||
isBot: $i.isBot ?? false,
|
||||
isCat: $i.isCat ?? false,
|
||||
speakAsCat: $i.speakAsCat,
|
||||
speakAsCat: $i.speakAsCat ?? false,
|
||||
});
|
||||
|
||||
watch(() => profile, () => {
|
||||
|
|
@ -190,6 +191,7 @@ function saveFields() {
|
|||
os.apiWithDialog('i/update', {
|
||||
fields: fields.value.filter(field => field.name !== '' && field.value !== '').map(field => ({ name: field.name, value: field.value })),
|
||||
});
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
}
|
||||
|
||||
function save() {
|
||||
|
|
@ -217,6 +219,7 @@ function save() {
|
|||
isCat: !!profile.isCat,
|
||||
speakAsCat: !!profile.speakAsCat,
|
||||
});
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
claimAchievement('profileFilled');
|
||||
if (profile.name === 'syuilo' || profile.name === 'しゅいろ') {
|
||||
claimAchievement('setNameToSyuilo');
|
||||
|
|
@ -248,6 +251,7 @@ function changeAvatar(ev) {
|
|||
});
|
||||
$i.avatarId = i.avatarId;
|
||||
$i.avatarUrl = i.avatarUrl;
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
claimAchievement('profileFilled');
|
||||
});
|
||||
}
|
||||
|
|
@ -278,6 +282,7 @@ function changeBanner(ev) {
|
|||
});
|
||||
$i.bannerId = i.bannerId;
|
||||
$i.bannerUrl = i.bannerUrl;
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
});
|
||||
},
|
||||
}, {
|
||||
|
|
@ -288,6 +293,7 @@ function changeBanner(ev) {
|
|||
});
|
||||
$i.bannerId = i.bannerId;
|
||||
$i.bannerUrl = i.bannerUrl;
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
},
|
||||
}], ev.currentTarget ?? ev.target);
|
||||
} else {
|
||||
|
|
@ -312,6 +318,7 @@ function changeBanner(ev) {
|
|||
});
|
||||
$i.bannerId = i.bannerId;
|
||||
$i.bannerUrl = i.bannerUrl;
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
@ -342,6 +349,7 @@ function changeBackground(ev) {
|
|||
});
|
||||
$i.backgroundId = i.backgroundId;
|
||||
$i.backgroundUrl = i.backgroundUrl;
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
});
|
||||
},
|
||||
}, {
|
||||
|
|
@ -352,6 +360,7 @@ function changeBackground(ev) {
|
|||
});
|
||||
$i.backgroundId = i.backgroundId;
|
||||
$i.backgroundUrl = i.backgroundUrl;
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
},
|
||||
}], ev.currentTarget ?? ev.target);
|
||||
} else {
|
||||
|
|
@ -376,6 +385,7 @@ function changeBackground(ev) {
|
|||
});
|
||||
$i.backgroundId = i.backgroundId;
|
||||
$i.backgroundUrl = i.backgroundUrl;
|
||||
globalEvents.emit('requestClearPageCache');
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -88,6 +88,18 @@ import { uniqueBy } from '@/scripts/array.js';
|
|||
import { fetchThemes, getThemes } from '@/theme-store.js';
|
||||
import { definePageMetadata } from '@/scripts/page-metadata.js';
|
||||
import { miLocalStorage } from '@/local-storage.js';
|
||||
import { unisonReload } from '@/scripts/unison-reload.js';
|
||||
import * as os from '@/os.js';
|
||||
|
||||
async function reloadAsk() {
|
||||
const { canceled } = await os.confirm({
|
||||
type: 'info',
|
||||
text: i18n.ts.reloadToApplySetting,
|
||||
});
|
||||
if (canceled) return;
|
||||
|
||||
unisonReload();
|
||||
}
|
||||
|
||||
const installedThemes = ref(getThemes());
|
||||
const builtinThemes = getBuiltinThemesRef();
|
||||
|
|
@ -124,6 +136,7 @@ const lightThemeId = computed({
|
|||
}
|
||||
},
|
||||
});
|
||||
|
||||
const darkMode = computed(defaultStore.makeGetterSetter('darkMode'));
|
||||
const syncDeviceDarkMode = computed(ColdDeviceStorage.makeGetterSetter('syncDeviceDarkMode'));
|
||||
const wallpaper = ref(miLocalStorage.getItem('wallpaper'));
|
||||
|
|
@ -141,7 +154,7 @@ watch(wallpaper, () => {
|
|||
} else {
|
||||
miLocalStorage.setItem('wallpaper', wallpaper.value);
|
||||
}
|
||||
location.reload();
|
||||
reloadAsk();
|
||||
});
|
||||
|
||||
onActivated(() => {
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@
|
|||
|
||||
/* eslint-disable @typescript-eslint/explicit-function-return-type */
|
||||
import { StoryObj } from '@storybook/vue3';
|
||||
import { rest } from 'msw';
|
||||
import { HttpResponse, http } from 'msw';
|
||||
import { userDetailed } from '../../../.storybook/fakes.js';
|
||||
import { commonHandlers } from '../../../.storybook/mocks.js';
|
||||
import home_ from './home.vue';
|
||||
|
|
@ -39,12 +39,13 @@ export const Default = {
|
|||
msw: {
|
||||
handlers: [
|
||||
...commonHandlers,
|
||||
rest.post('/api/users/notes', (req, res, ctx) => {
|
||||
return res(ctx.json([]));
|
||||
http.post('/api/users/notes', () => {
|
||||
return HttpResponse.json([]);
|
||||
}),
|
||||
rest.get('/api/charts/user/notes', (req, res, ctx) => {
|
||||
const length = Math.max(Math.min(parseInt(req.url.searchParams.get('limit') ?? '30', 10), 1), 300);
|
||||
return res(ctx.json({
|
||||
http.get('/api/charts/user/notes', ({ request }) => {
|
||||
const url = new URL(request.url);
|
||||
const length = Math.max(Math.min(parseInt(url.searchParams.get('limit') ?? '30', 10), 1), 300);
|
||||
return HttpResponse.json({
|
||||
total: Array.from({ length }, () => 0),
|
||||
inc: Array.from({ length }, () => 0),
|
||||
dec: Array.from({ length }, () => 0),
|
||||
|
|
@ -54,11 +55,12 @@ export const Default = {
|
|||
renote: Array.from({ length }, () => 0),
|
||||
withFile: Array.from({ length }, () => 0),
|
||||
},
|
||||
}));
|
||||
});
|
||||
}),
|
||||
rest.get('/api/charts/user/pv', (req, res, ctx) => {
|
||||
const length = Math.max(Math.min(parseInt(req.url.searchParams.get('limit') ?? '30', 10), 1), 300);
|
||||
return res(ctx.json({
|
||||
http.get('/api/charts/user/pv', ({ request }) => {
|
||||
const url = new URL(request.url);
|
||||
const length = Math.max(Math.min(parseInt(url.searchParams.get('limit') ?? '30', 10), 1), 300);
|
||||
return HttpResponse.json({
|
||||
upv: {
|
||||
user: Array.from({ length }, () => 0),
|
||||
visitor: Array.from({ length }, () => 0),
|
||||
|
|
@ -67,7 +69,7 @@ export const Default = {
|
|||
user: Array.from({ length }, () => 0),
|
||||
visitor: Array.from({ length }, () => 0),
|
||||
},
|
||||
}));
|
||||
});
|
||||
}),
|
||||
],
|
||||
},
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue