Merge tag '13.5.3' into io
This commit is contained in:
@@ -12,7 +12,7 @@
|
||||
"@rollup/plugin-json": "6.0.0",
|
||||
"@rollup/pluginutils": "5.0.2",
|
||||
"@syuilo/aiscript": "0.12.4",
|
||||
"@tabler/icons-webfont": "2.1.2",
|
||||
"@tabler/icons-webfont": "2.2.0",
|
||||
"@vitejs/plugin-vue": "4.0.0",
|
||||
"@vue/compiler-sfc": "3.2.47",
|
||||
"autobind-decorator": "2.4.0",
|
||||
@@ -23,7 +23,7 @@
|
||||
"canvas-confetti": "1.6.0",
|
||||
"chart.js": "4.2.0",
|
||||
"chartjs-adapter-date-fns": "3.0.0",
|
||||
"chartjs-chart-matrix": "1.3.0",
|
||||
"chartjs-chart-matrix": "2.0.1",
|
||||
"chartjs-plugin-gradient": "0.6.1",
|
||||
"chartjs-plugin-zoom": "2.0.0",
|
||||
"compare-versions": "5.0.1",
|
||||
@@ -44,7 +44,7 @@
|
||||
"punycode": "2.3.0",
|
||||
"querystring": "0.2.1",
|
||||
"rndstr": "1.0.0",
|
||||
"rollup": "3.12.1",
|
||||
"rollup": "3.14.0",
|
||||
"s-age": "1.1.2",
|
||||
"sanitize-html": "2.9.0",
|
||||
"sass": "1.58.0",
|
||||
@@ -55,7 +55,7 @@
|
||||
"textarea-caret": "3.1.0",
|
||||
"three": "0.149.0",
|
||||
"throttle-debounce": "5.0.0",
|
||||
"tinycolor2": "1.5.2",
|
||||
"tinycolor2": "1.6.0",
|
||||
"tsc-alias": "1.8.2",
|
||||
"tsconfig-paths": "4.1.2",
|
||||
"twemoji-parser": "14.0.0",
|
||||
@@ -74,7 +74,7 @@
|
||||
"@types/gulp": "4.0.10",
|
||||
"@types/gulp-rename": "2.0.1",
|
||||
"@types/matter-js": "0.18.2",
|
||||
"@types/node": "18.11.18",
|
||||
"@types/node": "18.13.0",
|
||||
"@types/punycode": "2.1.0",
|
||||
"@types/sanitize-html": "2.8.0",
|
||||
"@types/seedrandom": "3.0.4",
|
||||
@@ -83,8 +83,8 @@
|
||||
"@types/uuid": "9.0.0",
|
||||
"@types/websocket": "1.0.5",
|
||||
"@types/ws": "8.5.4",
|
||||
"@typescript-eslint/eslint-plugin": "5.50.0",
|
||||
"@typescript-eslint/parser": "5.50.0",
|
||||
"@typescript-eslint/eslint-plugin": "5.51.0",
|
||||
"@typescript-eslint/parser": "5.51.0",
|
||||
"@vue/runtime-core": "3.2.47",
|
||||
"cross-env": "7.0.3",
|
||||
"cypress": "12.5.1",
|
||||
|
@@ -61,8 +61,6 @@ export async function signout() {
|
||||
} catch (err) {}
|
||||
//#endregion
|
||||
|
||||
document.cookie = 'igi=; path=/';
|
||||
|
||||
if (accounts.length > 0) login(accounts[0].token);
|
||||
else unisonReload('/');
|
||||
}
|
||||
|
@@ -18,7 +18,7 @@
|
||||
</div>
|
||||
</Transition>
|
||||
<div class="container">
|
||||
<img ref="imgEl" :src="imgUrl" style="display: none;" @load="onImageLoad">
|
||||
<img ref="imgEl" :src="imgUrl" style="display: none;" crossorigin="anonymous" @load="onImageLoad">
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
@@ -1,22 +1,23 @@
|
||||
<template>
|
||||
<div v-if="hide" class="qjewsnkg" @click="hide = false">
|
||||
<ImgWithBlurhash class="bg" :hash="image.blurhash" :title="image.comment" :alt="image.comment"/>
|
||||
<div class="text">
|
||||
<div class="wrapper">
|
||||
<div v-if="hide" :class="$style.hidden" @click="hide = false">
|
||||
<ImgWithBlurhash style="filter: brightness(0.5);" :hash="image.blurhash" :title="image.comment" :alt="image.comment"/>
|
||||
<div :class="$style.hiddenText">
|
||||
<div :class="$style.hiddenTextWrapper">
|
||||
<b style="display: block;"><i class="ti ti-alert-triangle"></i> {{ $ts.sensitive }}</b>
|
||||
<span style="display: block;">{{ $ts.clickToShow }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div v-else class="gqnyydlz">
|
||||
<div v-else :class="$style.visible">
|
||||
<a
|
||||
:class="$style.imageContainer"
|
||||
:href="image.url"
|
||||
:title="image.name"
|
||||
>
|
||||
<ImgWithBlurhash :hash="image.blurhash" :src="url" :alt="image.comment || image.name" :title="image.comment || image.name" :cover="false"/>
|
||||
<div v-if="image.type === 'image/gif'" class="gif">GIF</div>
|
||||
<div v-if="image.type === 'image/gif'" :class="$style.gif">GIF</div>
|
||||
</a>
|
||||
<button v-tooltip="$ts.hide" class="_button hide" @click="hide = true"><i class="ti ti-eye-off"></i></button>
|
||||
<button v-tooltip="$ts.hide" :class="$style.hide" class="_button" @click="hide = true"><i class="ti ti-eye-off"></i></button>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@@ -49,82 +50,77 @@ watch(() => props.image, () => {
|
||||
});
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.qjewsnkg {
|
||||
<style lang="scss" module>
|
||||
.hidden {
|
||||
position: relative;
|
||||
|
||||
> .bg {
|
||||
filter: brightness(0.5);
|
||||
}
|
||||
|
||||
> .text {
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
z-index: 1;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
|
||||
> .wrapper {
|
||||
display: table-cell;
|
||||
text-align: center;
|
||||
font-size: 0.8em;
|
||||
color: #fff;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.gqnyydlz {
|
||||
.hiddenText {
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
z-index: 1;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.hiddenTextWrapper {
|
||||
display: table-cell;
|
||||
text-align: center;
|
||||
font-size: 0.8em;
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
.visible {
|
||||
position: relative;
|
||||
//box-shadow: 0 0 0 1px var(--divider) inset;
|
||||
background: var(--bg);
|
||||
--c: rgb(0 0 0 / 2%);
|
||||
background-image: linear-gradient(45deg, var(--c) 16.67%, var(--bg) 16.67%, var(--bg) 50%, var(--c) 50%, var(--c) 66.67%, var(--bg) 66.67%, var(--bg) 100%);
|
||||
background-size: 16px 16px;
|
||||
}
|
||||
|
||||
> .hide {
|
||||
display: block;
|
||||
position: absolute;
|
||||
border-radius: 6px;
|
||||
background-color: var(--accentedBg);
|
||||
-webkit-backdrop-filter: var(--blur, blur(15px));
|
||||
backdrop-filter: var(--blur, blur(15px));
|
||||
color: var(--accent);
|
||||
font-size: 0.8em;
|
||||
padding: 6px 8px;
|
||||
text-align: center;
|
||||
top: 12px;
|
||||
right: 12px;
|
||||
.hide {
|
||||
display: block;
|
||||
position: absolute;
|
||||
border-radius: 6px;
|
||||
background-color: var(--accentedBg);
|
||||
-webkit-backdrop-filter: var(--blur, blur(15px));
|
||||
backdrop-filter: var(--blur, blur(15px));
|
||||
color: var(--accent);
|
||||
font-size: 0.8em;
|
||||
padding: 6px 8px;
|
||||
text-align: center;
|
||||
top: 12px;
|
||||
right: 12px;
|
||||
}
|
||||
|
||||
> i {
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
.imageContainer {
|
||||
display: block;
|
||||
cursor: zoom-in;
|
||||
overflow: hidden;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-position: center;
|
||||
background-size: contain;
|
||||
background-repeat: no-repeat;
|
||||
}
|
||||
|
||||
> a {
|
||||
display: block;
|
||||
cursor: zoom-in;
|
||||
overflow: hidden;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-position: center;
|
||||
background-size: contain;
|
||||
background-repeat: no-repeat;
|
||||
|
||||
> .gif {
|
||||
background-color: var(--fg);
|
||||
border-radius: 6px;
|
||||
color: var(--accentLighten);
|
||||
display: inline-block;
|
||||
font-size: 14px;
|
||||
font-weight: bold;
|
||||
left: 12px;
|
||||
opacity: .5;
|
||||
padding: 0 6px;
|
||||
text-align: center;
|
||||
top: 12px;
|
||||
pointer-events: none;
|
||||
}
|
||||
}
|
||||
.gif {
|
||||
background-color: var(--fg);
|
||||
border-radius: 6px;
|
||||
color: var(--accentLighten);
|
||||
display: inline-block;
|
||||
font-size: 14px;
|
||||
font-weight: bold;
|
||||
left: 12px;
|
||||
opacity: .5;
|
||||
padding: 0 6px;
|
||||
text-align: center;
|
||||
top: 12px;
|
||||
pointer-events: none;
|
||||
}
|
||||
</style>
|
||||
|
@@ -215,7 +215,7 @@ useTooltip(reactionRef, (showing) => {
|
||||
border-radius: 100%;
|
||||
background: var(--panel);
|
||||
box-shadow: 0 0 0 3px var(--panel);
|
||||
font-size: 12px;
|
||||
font-size: 11px;
|
||||
text-align: center;
|
||||
color: #fff;
|
||||
|
||||
|
@@ -23,7 +23,7 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<XPostForm v-if="$i" :channel="channel" class="post-form _panel _margin" fixed/>
|
||||
<MkPostForm v-if="$i" :channel="channel" class="post-form _panel _margin" fixed/>
|
||||
|
||||
<XTimeline :key="channelId" class="_margin" src="channel" :channel="channelId" @before="before" @after="after"/>
|
||||
</div>
|
||||
@@ -34,7 +34,7 @@
|
||||
<script lang="ts" setup>
|
||||
import { computed, inject, watch } from 'vue';
|
||||
import MkContainer from '@/components/MkContainer.vue';
|
||||
import XPostForm from '@/components/MkPostForm.vue';
|
||||
import MkPostForm from '@/components/MkPostForm.vue';
|
||||
import XTimeline from '@/components/MkTimeline.vue';
|
||||
import XChannelFollowButton from '@/components/MkChannelFollowButton.vue';
|
||||
import * as os from '@/os';
|
||||
|
@@ -29,7 +29,7 @@ import { noteVisibilities } from 'misskey-js';
|
||||
import * as Acct from 'misskey-js/built/acct';
|
||||
import * as Misskey from 'misskey-js';
|
||||
import MkButton from '@/components/MkButton.vue';
|
||||
import XPostForm from '@/components/MkPostForm.vue';
|
||||
import MkPostForm from '@/components/MkPostForm.vue';
|
||||
import * as os from '@/os';
|
||||
import { mainRouter } from '@/router';
|
||||
import { definePageMetadata } from '@/scripts/page-metadata';
|
||||
@@ -69,14 +69,14 @@ async function init() {
|
||||
...(visibleAccts ? visibleAccts.split(',').map(Acct.parse) : []),
|
||||
]
|
||||
// TypeScriptの指示通りに変換する
|
||||
.map(q => 'username' in q ? { username: q.username, host: q.host === null ? undefined : q.host } : q)
|
||||
.map(q => os.api('users/show', q)
|
||||
.then(user => {
|
||||
visibleUsers.push(user);
|
||||
}, () => {
|
||||
console.error(`Invalid user query: ${JSON.stringify(q)}`);
|
||||
}),
|
||||
),
|
||||
.map(q => 'username' in q ? { username: q.username, host: q.host === null ? undefined : q.host } : q)
|
||||
.map(q => os.api('users/show', q)
|
||||
.then(user => {
|
||||
visibleUsers.push(user);
|
||||
}, () => {
|
||||
console.error(`Invalid user query: ${JSON.stringify(q)}`);
|
||||
}),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
@@ -120,13 +120,13 @@ async function init() {
|
||||
if (fileIds) {
|
||||
await Promise.all(
|
||||
fileIds.split(',')
|
||||
.map(fileId => os.api('drive/files/show', { fileId })
|
||||
.then(file => {
|
||||
files.push(file);
|
||||
}, () => {
|
||||
console.error(`Failed to fetch a file ${fileId}`);
|
||||
}),
|
||||
),
|
||||
.map(fileId => os.api('drive/files/show', { fileId })
|
||||
.then(file => {
|
||||
files.push(file);
|
||||
}, () => {
|
||||
console.error(`Failed to fetch a file ${fileId}`);
|
||||
}),
|
||||
),
|
||||
);
|
||||
}
|
||||
//#endregion
|
||||
|
@@ -4,7 +4,7 @@
|
||||
<MkSpacer :content-max="800">
|
||||
<div ref="rootEl" v-hotkey.global="keymap">
|
||||
<XTutorial v-if="$i && $store.reactiveState.tutorial.value != -1" class="_panel" style="margin-bottom: var(--margin);"/>
|
||||
<XPostForm v-if="$store.reactiveState.showFixedPostForm.value" :class="$style.postForm" class="post-form _panel" fixed style="margin-bottom: var(--margin);"/>
|
||||
<MkPostForm v-if="$store.reactiveState.showFixedPostForm.value" :class="$style.postForm" class="post-form _panel" fixed style="margin-bottom: var(--margin);"/>
|
||||
|
||||
<div v-if="queue > 0" :class="$style.new"><button class="_buttonPrimary" @click="top()">{{ i18n.ts.newNoteRecived }}</button></div>
|
||||
<div :class="$style.tl">
|
||||
@@ -24,7 +24,7 @@
|
||||
<script lang="ts" setup>
|
||||
import { defineAsyncComponent, computed, watch } from 'vue';
|
||||
import XTimeline from '@/components/MkTimeline.vue';
|
||||
import XPostForm from '@/components/MkPostForm.vue';
|
||||
import MkPostForm from '@/components/MkPostForm.vue';
|
||||
import { scroll } from '@/scripts/scroll';
|
||||
import * as os from '@/os';
|
||||
import { defaultStore } from '@/store';
|
||||
|
@@ -127,13 +127,12 @@ hr {
|
||||
}
|
||||
|
||||
.ti {
|
||||
vertical-align: -40%;
|
||||
vertical-align: -14%;
|
||||
line-height: 1em;
|
||||
|
||||
&:before {
|
||||
display: inline-block;
|
||||
font-size: 165%;
|
||||
width: 0.74em;
|
||||
font-size: 130%;
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -146,6 +146,7 @@ const addColumn = async (ev) => {
|
||||
'tl',
|
||||
'antenna',
|
||||
'list',
|
||||
'channel',
|
||||
'mentions',
|
||||
'direct',
|
||||
];
|
||||
|
71
packages/frontend/src/ui/deck/channel-column.vue
Normal file
71
packages/frontend/src/ui/deck/channel-column.vue
Normal file
@@ -0,0 +1,71 @@
|
||||
<template>
|
||||
<XColumn :menu="menu" :column="column" :is-stacked="isStacked" @parent-focus="$event => emit('parent-focus', $event)">
|
||||
<template #header>
|
||||
<i class="ti ti-device-tv"></i><span style="margin-left: 8px;">{{ column.name }}</span>
|
||||
</template>
|
||||
|
||||
<template v-if="column.channelId">
|
||||
<div style="padding: 8px; text-align: center;">
|
||||
<MkButton primary gradate rounded inline @click="post"><i class="ti ti-pencil"></i></MkButton>
|
||||
</div>
|
||||
<XTimeline ref="timeline" src="channel" :channel="column.channelId" @after="() => emit('loaded')"/>
|
||||
</template>
|
||||
</XColumn>
|
||||
</template>
|
||||
|
||||
<script lang="ts" setup>
|
||||
import { } from 'vue';
|
||||
import XColumn from './column.vue';
|
||||
import { updateColumn, Column } from './deck-store';
|
||||
import XTimeline from '@/components/MkTimeline.vue';
|
||||
import MkButton from '@/components/MkButton.vue';
|
||||
import * as os from '@/os';
|
||||
import { i18n } from '@/i18n';
|
||||
|
||||
const props = defineProps<{
|
||||
column: Column;
|
||||
isStacked: boolean;
|
||||
}>();
|
||||
|
||||
const emit = defineEmits<{
|
||||
(ev: 'loaded'): void;
|
||||
(ev: 'parent-focus', direction: 'up' | 'down' | 'left' | 'right'): void;
|
||||
}>();
|
||||
|
||||
let timeline = $shallowRef<InstanceType<typeof XTimeline>>();
|
||||
|
||||
if (props.column.channelId == null) {
|
||||
setChannel();
|
||||
}
|
||||
|
||||
async function setChannel() {
|
||||
const channels = await os.api('channels/followed');
|
||||
const { canceled, result: channel } = await os.select({
|
||||
title: i18n.ts.selectChannel,
|
||||
items: channels.map(x => ({
|
||||
value: x, text: x.name,
|
||||
})),
|
||||
default: props.column.channelId,
|
||||
});
|
||||
if (canceled) return;
|
||||
updateColumn(props.column.id, {
|
||||
channelId: channel.id,
|
||||
name: channel.name,
|
||||
});
|
||||
}
|
||||
|
||||
function post() {
|
||||
os.post({
|
||||
channel: {
|
||||
id: props.column.channelId,
|
||||
},
|
||||
instant: true,
|
||||
});
|
||||
}
|
||||
|
||||
const menu = [{
|
||||
icon: 'ti ti-pencil',
|
||||
text: i18n.ts.selectChannel,
|
||||
action: setChannel,
|
||||
}];
|
||||
</script>
|
@@ -6,6 +6,7 @@
|
||||
<XNotificationsColumn v-else-if="column.type === 'notifications'" :column="column" :is-stacked="isStacked" @parent-focus="emit('parent-focus', $event)"/>
|
||||
<XTlColumn v-else-if="column.type === 'tl'" :column="column" :is-stacked="isStacked" @parent-focus="emit('parent-focus', $event)"/>
|
||||
<XListColumn v-else-if="column.type === 'list'" :column="column" :is-stacked="isStacked" @parent-focus="emit('parent-focus', $event)"/>
|
||||
<XChannelColumn v-else-if="column.type === 'channel'" :column="column" :is-stacked="isStacked" @parent-focus="emit('parent-focus', $event)"/>
|
||||
<XAntennaColumn v-else-if="column.type === 'antenna'" :column="column" :is-stacked="isStacked" @parent-focus="emit('parent-focus', $event)"/>
|
||||
<XMentionsColumn v-else-if="column.type === 'mentions'" :column="column" :is-stacked="isStacked" @parent-focus="emit('parent-focus', $event)"/>
|
||||
<XDirectColumn v-else-if="column.type === 'direct'" :column="column" :is-stacked="isStacked" @parent-focus="emit('parent-focus', $event)"/>
|
||||
@@ -17,6 +18,7 @@ import XMainColumn from './main-column.vue';
|
||||
import XTlColumn from './tl-column.vue';
|
||||
import XAntennaColumn from './antenna-column.vue';
|
||||
import XListColumn from './list-column.vue';
|
||||
import XChannelColumn from './channel-column.vue';
|
||||
import XNotificationsColumn from './notifications-column.vue';
|
||||
import XWidgetsColumn from './widgets-column.vue';
|
||||
import XMentionsColumn from './mentions-column.vue';
|
||||
|
@@ -14,7 +14,7 @@ type ColumnWidget = {
|
||||
|
||||
export type Column = {
|
||||
id: string;
|
||||
type: 'main' | 'widgets' | 'notifications' | 'tl' | 'antenna' | 'list' | 'mentions' | 'direct';
|
||||
type: 'main' | 'widgets' | 'notifications' | 'tl' | 'antenna' | 'channel' | 'list' | 'mentions' | 'direct';
|
||||
name: string | null;
|
||||
width: number;
|
||||
widgets?: ColumnWidget[];
|
||||
@@ -22,6 +22,7 @@ export type Column = {
|
||||
flexible?: boolean;
|
||||
antennaId?: string;
|
||||
listId?: string;
|
||||
channelId?: string;
|
||||
includingTypes?: typeof notificationTypes[number][];
|
||||
tl?: 'home' | 'local' | 'social' | 'global';
|
||||
};
|
||||
|
@@ -1,12 +1,12 @@
|
||||
<template>
|
||||
<XPostForm class="_panel mkw-postForm data-cy-mkw-postForm" :fixed="true" :autofocus="false"/>
|
||||
<MkPostForm class="_panel mkw-post-form data-cy-mkw-postForm" :fixed="true" :autofocus="false"/>
|
||||
</template>
|
||||
|
||||
<script lang="ts" setup>
|
||||
import { } from 'vue';
|
||||
import { GetFormResultType } from '@/scripts/form';
|
||||
import { useWidgetPropsManager, Widget, WidgetComponentEmits, WidgetComponentExpose, WidgetComponentProps } from './widget';
|
||||
import XPostForm from '@/components/MkPostForm.vue';
|
||||
import { GetFormResultType } from '@/scripts/form';
|
||||
import MkPostForm from '@/components/MkPostForm.vue';
|
||||
|
||||
const name = 'postForm';
|
||||
|
||||
|
Reference in New Issue
Block a user