mirror of
https://iceshrimp.dev/crimekillz/trashposs
synced 2024-11-21 16:33:48 +01:00
Snippets: Unify Clips & Bookmarks
This commit is contained in:
parent
bacd8eb9b2
commit
6f57bce3aa
@ -19,6 +19,7 @@ __2024.04.1 is out!__
|
|||||||
---
|
---
|
||||||
- Highlighted changes:
|
- Highlighted changes:
|
||||||
- Achievements adopting code from Sharkey/Misskey
|
- Achievements adopting code from Sharkey/Misskey
|
||||||
|
- Unified Bookmarks and Clips (Snippets, dev branch)
|
||||||
- Chomp! Activity Support (Patch adopted [from mia](https://iceshrimp.dev/mia/withdrawal))
|
- Chomp! Activity Support (Patch adopted [from mia](https://iceshrimp.dev/mia/withdrawal))
|
||||||
- Fast🚜 Scream🚜 Mod🔌 Tracker/SID playback support (Thanks to [Jeder](https://iceshrimp.dev/iceshrimp/iceshrimp/pulls/490))
|
- Fast🚜 Scream🚜 Mod🔌 Tracker/SID playback support (Thanks to [Jeder](https://iceshrimp.dev/iceshrimp/iceshrimp/pulls/490))
|
||||||
- Suppress the "You haven't configured mail" message (Patch adopted [from mia](https://iceshrimp.dev/mia/withdrawal))
|
- Suppress the "You haven't configured mail" message (Patch adopted [from mia](https://iceshrimp.dev/mia/withdrawal))
|
||||||
@ -26,15 +27,20 @@ __2024.04.1 is out!__
|
|||||||
- Allow federation via Tor / i2p
|
- Allow federation via Tor / i2p
|
||||||
- Allow proxying of videos and audio content (Thanks to ShittyKopper)
|
- Allow proxying of videos and audio content (Thanks to ShittyKopper)
|
||||||
- Post language selection and translate functionality by Namekuji
|
- Post language selection and translate functionality by Namekuji
|
||||||
|
- Profile pictures can be viewed fullscreen (dev branch)
|
||||||
|
- Accessibility settings in the unauthenticated web viewer (dev branch)
|
||||||
- So much more - Read the [changelog](CHANGELOG.md) to get an overview of all changes
|
- So much more - Read the [changelog](CHANGELOG.md) to get an overview of all changes
|
||||||
- Planned changes:
|
- Planned changes:
|
||||||
- Unified Lists and News UI
|
- Unified Lists and News UI
|
||||||
- New central Messenger UI unifying Chats, Groups, Channels and Announcements
|
- New central Messenger UI unifying Chats, Groups, Channels and Announcements
|
||||||
|
- Unified Exploration and Search of Users, Posts, Channels
|
||||||
|
- E2E encrypted messaging
|
||||||
- Improvements for single-user instances, anonymous and pseudonymous federation via Tor / i2p
|
- Improvements for single-user instances, anonymous and pseudonymous federation via Tor / i2p
|
||||||
- Posts Health/XP Bar to indicate how many ppl have reported a post vs. interaction rate
|
- Posts Health/XP Bar to indicate how many ppl have reported a post vs. interaction rate
|
||||||
- Train Table Delay Captcha
|
- Train Table Delay Captcha
|
||||||
- Individual session revocation and One Time Access Tokens
|
- Individual session revocation and One Time Access Tokens
|
||||||
- Accessibility settings in the unauthenticated web viewer
|
- Need Ideas for:
|
||||||
|
- Better integration of User Gallery and Pages
|
||||||
- Don't like the Web UI? Good luck, the Mastodon-compatible API might work with the following clients:
|
- Don't like the Web UI? Good luck, the Mastodon-compatible API might work with the following clients:
|
||||||
- [Elk](https://elk.zone), [Phanpy](https://phanpy.social/), [Enafore](https://enafore.social/), [Masto-FE-standalone](https://iceshrimp.dev/iceshrimp/masto-fe-standalone) (Web)
|
- [Elk](https://elk.zone), [Phanpy](https://phanpy.social/), [Enafore](https://enafore.social/), [Masto-FE-standalone](https://iceshrimp.dev/iceshrimp/masto-fe-standalone) (Web)
|
||||||
- [Mona](https://apps.apple.com/us/app/mona-for-mastodon/id1659154653), [Toot!](https://apps.apple.com/us/app/toot-for-mastodon/id1229021451), [Ice Cubes](https://apps.apple.com/us/app/ice-cubes-for-mastodon/id6444915884), [Tusker](https://apps.apple.com/us/app/tusker/id1498334597), [Feditext](https://github.com/feditext/feditext), [Mastodon](https://apps.apple.com/us/app/mastodon-for-iphone-and-ipad/id1571998974) (iOS)
|
- [Mona](https://apps.apple.com/us/app/mona-for-mastodon/id1659154653), [Toot!](https://apps.apple.com/us/app/toot-for-mastodon/id1229021451), [Ice Cubes](https://apps.apple.com/us/app/ice-cubes-for-mastodon/id6444915884), [Tusker](https://apps.apple.com/us/app/tusker/id1498334597), [Feditext](https://github.com/feditext/feditext), [Mastodon](https://apps.apple.com/us/app/mastodon-for-iphone-and-ipad/id1571998974) (iOS)
|
||||||
|
@ -36,6 +36,7 @@ save: "Save"
|
|||||||
users: "Users"
|
users: "Users"
|
||||||
addUser: "Add a user"
|
addUser: "Add a user"
|
||||||
addInstance: "Add a server"
|
addInstance: "Add a server"
|
||||||
|
snippets: "Snippets"
|
||||||
favorite: "Add to bookmarks"
|
favorite: "Add to bookmarks"
|
||||||
favorites: "Bookmarks"
|
favorites: "Bookmarks"
|
||||||
unfavorite: "Remove from bookmarks"
|
unfavorite: "Remove from bookmarks"
|
||||||
|
@ -36,6 +36,7 @@ addUser: "ユーザーを追加"
|
|||||||
addInstance: "サーバーを追加"
|
addInstance: "サーバーを追加"
|
||||||
favorite: "お気に入り"
|
favorite: "お気に入り"
|
||||||
favorites: "お気に入り"
|
favorites: "お気に入り"
|
||||||
|
snippets: "Snippets"
|
||||||
unfavorite: "お気に入り解除"
|
unfavorite: "お気に入り解除"
|
||||||
favorited: "お気に入りに登録しました。"
|
favorited: "お気に入りに登録しました。"
|
||||||
alreadyFavorited: "既にお気に入りに登録されています。"
|
alreadyFavorited: "既にお気に入りに登録されています。"
|
||||||
|
@ -97,7 +97,7 @@ async function openSearchFilters(ev) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
icon: "ph-bookmark-simple ph-bold ph-lg",
|
icon: "ph-bookmarks ph-bold ph-lg",
|
||||||
text: i18n.ts._filters.inBookmarks,
|
text: i18n.ts._filters.inBookmarks,
|
||||||
action: () => {
|
action: () => {
|
||||||
appendSearchFilter("in:bookmarks");
|
appendSearchFilter("in:bookmarks");
|
||||||
|
@ -22,7 +22,7 @@ export const navbarItemDef = reactive({
|
|||||||
title: "messaging",
|
title: "messaging",
|
||||||
icon: "ph-tornado ph-bold ph-lg",
|
icon: "ph-tornado ph-bold ph-lg",
|
||||||
show: computed(() => $i != null),
|
show: computed(() => $i != null),
|
||||||
indicated: computed(() => $i?.hasUnreadMessagingMessage),
|
indicated: computed(() => $i?.hasUnreadMessagingMessage || $i?.hasUnreadAnnouncement),
|
||||||
to: "/my/messaging",
|
to: "/my/messaging",
|
||||||
},
|
},
|
||||||
drive: {
|
drive: {
|
||||||
@ -43,12 +43,6 @@ export const navbarItemDef = reactive({
|
|||||||
icon: "ph-hash ph-bold ph-lg",
|
icon: "ph-hash ph-bold ph-lg",
|
||||||
to: "/explore",
|
to: "/explore",
|
||||||
},
|
},
|
||||||
announcements: {
|
|
||||||
title: "announcements",
|
|
||||||
icon: "ph-megaphone-simple ph-bold ph-lg",
|
|
||||||
indicated: computed(() => $i?.hasUnreadAnnouncement),
|
|
||||||
to: "/announcements",
|
|
||||||
},
|
|
||||||
search: {
|
search: {
|
||||||
title: "search",
|
title: "search",
|
||||||
icon: "ph-magnifying-glass ph-bold ph-lg",
|
icon: "ph-magnifying-glass ph-bold ph-lg",
|
||||||
@ -74,11 +68,11 @@ export const navbarItemDef = reactive({
|
|||||||
show: computed(() => $i != null),
|
show: computed(() => $i != null),
|
||||||
to: "/my/antennas",
|
to: "/my/antennas",
|
||||||
},
|
},
|
||||||
favorites: {
|
snippets: {
|
||||||
title: "favorites",
|
title: "snippets",
|
||||||
icon: "ph-bookmark-simple ph-bold ph-lg",
|
icon: "ph-bookmark ph-bold ph-lg",
|
||||||
show: computed(() => $i != null),
|
show: computed(() => $i != null),
|
||||||
to: "/my/favorites",
|
to: "/my/snippets",
|
||||||
},
|
},
|
||||||
pages: {
|
pages: {
|
||||||
title: "pages",
|
title: "pages",
|
||||||
@ -90,22 +84,11 @@ export const navbarItemDef = reactive({
|
|||||||
icon: "ph-image-square ph-bold ph-lg",
|
icon: "ph-image-square ph-bold ph-lg",
|
||||||
to: "/gallery",
|
to: "/gallery",
|
||||||
},
|
},
|
||||||
clips: {
|
|
||||||
title: "clips",
|
|
||||||
icon: "ph-paperclip ph-bold ph-lg",
|
|
||||||
show: computed(() => $i != null),
|
|
||||||
to: "/my/clips",
|
|
||||||
},
|
|
||||||
channels: {
|
channels: {
|
||||||
title: "channel",
|
title: "channel",
|
||||||
icon: "ph-television ph-bold ph-lg",
|
icon: "ph-television ph-bold ph-lg",
|
||||||
to: "/channels",
|
to: "/channels",
|
||||||
},
|
},
|
||||||
groups: {
|
|
||||||
title: "groups",
|
|
||||||
icon: "ph-users-three ph-bold ph-lg",
|
|
||||||
to: "/my/groups",
|
|
||||||
},
|
|
||||||
achievements: {
|
achievements: {
|
||||||
title: "achievements",
|
title: "achievements",
|
||||||
icon: "ph-medal-military ph-bold ph-lg",
|
icon: "ph-medal-military ph-bold ph-lg",
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
<template>
|
<template>
|
||||||
<MkStickyContainer>
|
<MkStickyContainer>
|
||||||
<template #header><MkPageHeader :actions="headerActions" /></template>
|
<template #header><MkPageHeader :actions="headerActions" :display-back-button="true" /></template>
|
||||||
<MkSpacer :content-max="800">
|
<MkSpacer :content-max="800">
|
||||||
<div v-if="clip">
|
<div v-if="clip">
|
||||||
<div class="okzinsic _panel">
|
<div class="okzinsic _panel">
|
||||||
|
@ -1,63 +0,0 @@
|
|||||||
<template>
|
|
||||||
<MkStickyContainer>
|
|
||||||
<template #header><MkPageHeader /></template>
|
|
||||||
<MkSpacer :content-max="800">
|
|
||||||
<MkPagination ref="pagingComponent" :pagination="pagination">
|
|
||||||
<template #empty>
|
|
||||||
<div class="_fullinfo">
|
|
||||||
<img
|
|
||||||
:src="instance.images.info"
|
|
||||||
class="_ghost"
|
|
||||||
alt="Info"
|
|
||||||
/>
|
|
||||||
<div>{{ i18n.ts.noNotes }}</div>
|
|
||||||
</div>
|
|
||||||
</template>
|
|
||||||
|
|
||||||
<template #default="{ items }">
|
|
||||||
<XList
|
|
||||||
v-slot="{ item }"
|
|
||||||
:items="items"
|
|
||||||
:direction="'down'"
|
|
||||||
:no-gap="false"
|
|
||||||
>
|
|
||||||
<XNote
|
|
||||||
:key="item.id"
|
|
||||||
:note="item.note"
|
|
||||||
:class="$style.note"
|
|
||||||
/>
|
|
||||||
</XList>
|
|
||||||
</template>
|
|
||||||
</MkPagination>
|
|
||||||
</MkSpacer>
|
|
||||||
</MkStickyContainer>
|
|
||||||
</template>
|
|
||||||
|
|
||||||
<script lang="ts" setup>
|
|
||||||
import { ref } from "vue";
|
|
||||||
import MkPagination from "@/components/MkPagination.vue";
|
|
||||||
import XNote from "@/components/MkNote.vue";
|
|
||||||
import XList from "@/components/MkDateSeparatedList.vue";
|
|
||||||
import { i18n } from "@/i18n";
|
|
||||||
import { definePageMetadata } from "@/scripts/page-metadata";
|
|
||||||
import {instance} from "@/instance";
|
|
||||||
|
|
||||||
const pagination = {
|
|
||||||
endpoint: "i/favorites" as const,
|
|
||||||
limit: 10,
|
|
||||||
};
|
|
||||||
|
|
||||||
const pagingComponent = ref<InstanceType<typeof MkPagination>>();
|
|
||||||
|
|
||||||
definePageMetadata({
|
|
||||||
title: i18n.ts.favorites,
|
|
||||||
icon: "ph-bookmark-simple ph-bold ph-lg",
|
|
||||||
});
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<style lang="scss" module>
|
|
||||||
.note {
|
|
||||||
background: var(--panel);
|
|
||||||
border-radius: var(--radius);
|
|
||||||
}
|
|
||||||
</style>
|
|
@ -1,118 +0,0 @@
|
|||||||
<template>
|
|
||||||
<MkStickyContainer>
|
|
||||||
<template #header
|
|
||||||
><MkPageHeader
|
|
||||||
:actions="headerActions"
|
|
||||||
:tabs="headerTabs"
|
|
||||||
:display-back-button="true"
|
|
||||||
/></template>
|
|
||||||
<MkSpacer :content-max="700">
|
|
||||||
<div class="qtcaoidl">
|
|
||||||
<MkPagination
|
|
||||||
ref="pagingComponent"
|
|
||||||
:pagination="pagination"
|
|
||||||
class="list"
|
|
||||||
>
|
|
||||||
<template #empty>
|
|
||||||
<MkInfo :icon="'paperclip'" :card="true">
|
|
||||||
<p>{{ i18n.ts.clipsDesc }}</p>
|
|
||||||
</MkInfo>
|
|
||||||
</template>
|
|
||||||
<template #default="{ items }">
|
|
||||||
<MkA
|
|
||||||
v-for="item in items"
|
|
||||||
:key="item.id"
|
|
||||||
:to="`/clips/${item.id}`"
|
|
||||||
class="item _panel _gap"
|
|
||||||
>
|
|
||||||
<b>{{ item.name }}</b>
|
|
||||||
<div v-if="item.description" class="description">
|
|
||||||
{{ item.description }}
|
|
||||||
</div>
|
|
||||||
</MkA>
|
|
||||||
</template>
|
|
||||||
</MkPagination>
|
|
||||||
</div>
|
|
||||||
</MkSpacer>
|
|
||||||
</MkStickyContainer>
|
|
||||||
</template>
|
|
||||||
|
|
||||||
<script lang="ts" setup>
|
|
||||||
import {} from "vue";
|
|
||||||
import MkPagination from "@/components/MkPagination.vue";
|
|
||||||
import MkButton from "@/components/MkButton.vue";
|
|
||||||
import MkInfo from "@/components/MkInfo.vue";
|
|
||||||
import * as os from "@/os";
|
|
||||||
import { i18n } from "@/i18n";
|
|
||||||
import { definePageMetadata } from "@/scripts/page-metadata";
|
|
||||||
|
|
||||||
const pagination = {
|
|
||||||
endpoint: "clips/list" as const,
|
|
||||||
limit: 10,
|
|
||||||
};
|
|
||||||
|
|
||||||
const pagingComponent = $ref<InstanceType<typeof MkPagination>>();
|
|
||||||
|
|
||||||
async function create() {
|
|
||||||
const { canceled, result } = await os.form(i18n.ts.createNewClip, {
|
|
||||||
name: {
|
|
||||||
type: "string",
|
|
||||||
label: i18n.ts.name,
|
|
||||||
},
|
|
||||||
description: {
|
|
||||||
type: "string",
|
|
||||||
required: false,
|
|
||||||
multiline: true,
|
|
||||||
label: i18n.ts.description,
|
|
||||||
},
|
|
||||||
isPublic: {
|
|
||||||
type: "boolean",
|
|
||||||
label: i18n.ts.public,
|
|
||||||
default: false,
|
|
||||||
},
|
|
||||||
});
|
|
||||||
if (canceled) return;
|
|
||||||
|
|
||||||
os.apiWithDialog("clips/create", result);
|
|
||||||
|
|
||||||
pagingComponent.reload();
|
|
||||||
}
|
|
||||||
|
|
||||||
function onClipCreated() {
|
|
||||||
pagingComponent.reload();
|
|
||||||
}
|
|
||||||
|
|
||||||
function onClipDeleted() {
|
|
||||||
pagingComponent.reload();
|
|
||||||
}
|
|
||||||
|
|
||||||
const headerActions = $computed(() => []);
|
|
||||||
|
|
||||||
const headerTabs = $computed(() => []);
|
|
||||||
|
|
||||||
definePageMetadata({
|
|
||||||
title: i18n.ts.clip,
|
|
||||||
icon: "ph-paperclip ph-bold ph-lg",
|
|
||||||
action: {
|
|
||||||
icon: "ph-plus ph-bold ph-lg",
|
|
||||||
handler: create,
|
|
||||||
},
|
|
||||||
});
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<style lang="scss" scoped>
|
|
||||||
.qtcaoidl {
|
|
||||||
> .list {
|
|
||||||
> .item {
|
|
||||||
display: block;
|
|
||||||
padding: 16px;
|
|
||||||
|
|
||||||
> .description {
|
|
||||||
margin-top: 8px;
|
|
||||||
padding-top: 8px;
|
|
||||||
border-top: solid 0.5px var(--divider);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</style>
|
|
234
packages/client/src/pages/my-snippets/index.vue
Normal file
234
packages/client/src/pages/my-snippets/index.vue
Normal file
@ -0,0 +1,234 @@
|
|||||||
|
<template>
|
||||||
|
<MkStickyContainer>
|
||||||
|
<template #header
|
||||||
|
><MkPageHeader
|
||||||
|
v-model:tab="tab"
|
||||||
|
:actions="headerActions"
|
||||||
|
:tabs="headerTabs"
|
||||||
|
/></template>
|
||||||
|
<div>
|
||||||
|
<MkSpacer :content-max="800">
|
||||||
|
<swiper
|
||||||
|
:round-lengths="true"
|
||||||
|
:touch-angle="25"
|
||||||
|
:threshold="10"
|
||||||
|
:centeredSlides="true"
|
||||||
|
:modules="[Virtual]"
|
||||||
|
:space-between="20"
|
||||||
|
:virtual="true"
|
||||||
|
:allow-touch-move="
|
||||||
|
defaultStore.state.swipeOnMobile &&
|
||||||
|
(deviceKind !== 'desktop' ||
|
||||||
|
defaultStore.state.swipeOnDesktop)
|
||||||
|
"
|
||||||
|
@swiper="setSwiperRef"
|
||||||
|
@slide-change="onSlideChange"
|
||||||
|
>
|
||||||
|
<swiper-slide>
|
||||||
|
<div class="_content qtcaoidl favorites">
|
||||||
|
<MkPagination ref="pagingComponent" :pagination="favPagination">
|
||||||
|
<template #empty>
|
||||||
|
<div class="_fullinfo">
|
||||||
|
<img
|
||||||
|
:src="instance.images.info"
|
||||||
|
class="_ghost"
|
||||||
|
alt="Info"
|
||||||
|
/>
|
||||||
|
<div>{{ i18n.ts.noNotes }}</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<template #default="{ items }">
|
||||||
|
<XList
|
||||||
|
v-slot="{ item }"
|
||||||
|
:items="items"
|
||||||
|
:direction="'down'"
|
||||||
|
:no-gap="false"
|
||||||
|
>
|
||||||
|
<XNote
|
||||||
|
:key="item.id"
|
||||||
|
:note="item.note"
|
||||||
|
:class="$style.note"
|
||||||
|
/>
|
||||||
|
</XList>
|
||||||
|
</template>
|
||||||
|
</MkPagination>
|
||||||
|
</div>
|
||||||
|
</swiper-slide>
|
||||||
|
<swiper-slide>
|
||||||
|
<div class="_content qtcaoidl clips">
|
||||||
|
<MkPagination
|
||||||
|
ref="pagingComponent"
|
||||||
|
:pagination="clipPagination"
|
||||||
|
class="list"
|
||||||
|
>
|
||||||
|
<template #empty>
|
||||||
|
<MkInfo :icon="'paperclip'" :card="true">
|
||||||
|
<p>{{ i18n.ts.clipsDesc }}</p>
|
||||||
|
</MkInfo>
|
||||||
|
</template>
|
||||||
|
<template #default="{ items }">
|
||||||
|
<MkA
|
||||||
|
v-for="item in items"
|
||||||
|
:key="item.id"
|
||||||
|
:to="`/clips/${item.id}`"
|
||||||
|
class="item _panel _gap"
|
||||||
|
>
|
||||||
|
<b>{{ item.name }}</b>
|
||||||
|
<div v-if="item.description" class="description">
|
||||||
|
{{ item.description }}
|
||||||
|
</div>
|
||||||
|
</MkA>
|
||||||
|
</template>
|
||||||
|
</MkPagination>
|
||||||
|
</div>
|
||||||
|
</swiper-slide>
|
||||||
|
</swiper>
|
||||||
|
</MkSpacer>
|
||||||
|
</div>
|
||||||
|
</MkStickyContainer>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script lang="ts" setup>
|
||||||
|
import { ref, onMounted, watch } from "vue";
|
||||||
|
import { Virtual } from "swiper/modules";
|
||||||
|
import { Swiper, SwiperSlide } from "swiper/vue";
|
||||||
|
import MkPagination from "@/components/MkPagination.vue";
|
||||||
|
import MkButton from "@/components/MkButton.vue";
|
||||||
|
import MkInfo from "@/components/MkInfo.vue";
|
||||||
|
import XNote from "@/components/MkNote.vue";
|
||||||
|
import XList from "@/components/MkDateSeparatedList.vue";
|
||||||
|
import * as os from "@/os";
|
||||||
|
import { i18n } from "@/i18n";
|
||||||
|
import { definePageMetadata } from "@/scripts/page-metadata";
|
||||||
|
import {instance} from "@/instance";
|
||||||
|
import { defaultStore } from "@/store";
|
||||||
|
import { deviceKind } from "@/scripts/device-kind";
|
||||||
|
import "swiper/scss";
|
||||||
|
import "swiper/scss/virtual";
|
||||||
|
|
||||||
|
const tabs = ["favorites", "clips"];
|
||||||
|
let tab = $ref(tabs[0]);
|
||||||
|
watch($$(tab), () => syncSlide(tabs.indexOf(tab)));
|
||||||
|
|
||||||
|
const MOBILE_THRESHOLD = 500;
|
||||||
|
const isMobile = ref(
|
||||||
|
deviceKind === "smartphone" || window.innerWidth <= MOBILE_THRESHOLD,
|
||||||
|
);
|
||||||
|
window.addEventListener("resize", () => {
|
||||||
|
isMobile.value =
|
||||||
|
deviceKind === "smartphone" || window.innerWidth <= MOBILE_THRESHOLD;
|
||||||
|
});
|
||||||
|
|
||||||
|
const clipPagination = {
|
||||||
|
endpoint: "clips/list" as const,
|
||||||
|
limit: 10,
|
||||||
|
};
|
||||||
|
|
||||||
|
const favPagination = {
|
||||||
|
endpoint: "i/favorites" as const,
|
||||||
|
limit: 10,
|
||||||
|
};
|
||||||
|
|
||||||
|
const pagingComponent = $ref<InstanceType<typeof MkPagination>>();
|
||||||
|
|
||||||
|
async function create() {
|
||||||
|
const { canceled, result } = await os.form(i18n.ts.createNewClip, {
|
||||||
|
name: {
|
||||||
|
type: "string",
|
||||||
|
label: i18n.ts.name,
|
||||||
|
},
|
||||||
|
description: {
|
||||||
|
type: "string",
|
||||||
|
required: false,
|
||||||
|
multiline: true,
|
||||||
|
label: i18n.ts.description,
|
||||||
|
},
|
||||||
|
isPublic: {
|
||||||
|
type: "boolean",
|
||||||
|
label: i18n.ts.public,
|
||||||
|
default: false,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
if (canceled) return;
|
||||||
|
|
||||||
|
os.apiWithDialog("clips/create", result);
|
||||||
|
|
||||||
|
pagingComponent.reload();
|
||||||
|
}
|
||||||
|
|
||||||
|
function onClipCreated() {
|
||||||
|
pagingComponent.reload();
|
||||||
|
}
|
||||||
|
|
||||||
|
function onClipDeleted() {
|
||||||
|
pagingComponent.reload();
|
||||||
|
}
|
||||||
|
|
||||||
|
const headerActions = $computed(() => []);
|
||||||
|
|
||||||
|
const headerTabs = $computed(() => [
|
||||||
|
{
|
||||||
|
key: "favorites",
|
||||||
|
title: i18n.ts.favorites,
|
||||||
|
icon: "ph-bookmarks ph-bold ph-lg",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
key: "clips",
|
||||||
|
title: i18n.ts.clips,
|
||||||
|
icon: "ph-paperclip ph-bold ph-lg",
|
||||||
|
},
|
||||||
|
]);
|
||||||
|
|
||||||
|
let swiperRef = null;
|
||||||
|
|
||||||
|
function setSwiperRef(swiper) {
|
||||||
|
swiperRef = swiper;
|
||||||
|
syncSlide(tabs.indexOf(tab));
|
||||||
|
}
|
||||||
|
|
||||||
|
function onSlideChange() {
|
||||||
|
tab = tabs[swiperRef.activeIndex];
|
||||||
|
}
|
||||||
|
|
||||||
|
function syncSlide(index) {
|
||||||
|
swiperRef.slideTo(index);
|
||||||
|
}
|
||||||
|
|
||||||
|
onMounted(() => {
|
||||||
|
syncSlide(tabs.indexOf(swiperRef.activeIndex));
|
||||||
|
});
|
||||||
|
|
||||||
|
definePageMetadata({
|
||||||
|
title: i18n.ts.snippets,
|
||||||
|
icon: "ph-bookmark ph-bold ph-lg",
|
||||||
|
action: {
|
||||||
|
icon: "ph-plus ph-bold ph-lg",
|
||||||
|
handler: create,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style lang="scss" module>
|
||||||
|
.note {
|
||||||
|
background: var(--panel);
|
||||||
|
border-radius: var(--radius);
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
|
||||||
|
<style lang="scss" scoped>
|
||||||
|
.qtcaoidl {
|
||||||
|
> .list {
|
||||||
|
> .item {
|
||||||
|
display: block;
|
||||||
|
padding: 16px;
|
||||||
|
|
||||||
|
> .description {
|
||||||
|
margin-top: 8px;
|
||||||
|
padding-top: 8px;
|
||||||
|
border-top: solid 0.5px var(--divider);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</style>
|
@ -88,7 +88,7 @@
|
|||||||
v-tooltip.noDelay="i18n.ts.isAdmin"
|
v-tooltip.noDelay="i18n.ts.isAdmin"
|
||||||
style="color: var(--badge)"
|
style="color: var(--badge)"
|
||||||
><i
|
><i
|
||||||
class="ph-bookmark-simple ph-fill ph-lg"
|
class="ph-crown-simple ph-fill ph-lg"
|
||||||
></i
|
></i
|
||||||
></span>
|
></span>
|
||||||
<span
|
<span
|
||||||
@ -96,7 +96,7 @@
|
|||||||
v-tooltip.noDelay="i18n.ts.isModerator"
|
v-tooltip.noDelay="i18n.ts.isModerator"
|
||||||
style="color: var(--badge)"
|
style="color: var(--badge)"
|
||||||
><i
|
><i
|
||||||
class="ph-bookmark-simple ph-bold ph-lg"
|
class="ph-crown-simple ph-bold ph-lg"
|
||||||
></i
|
></i
|
||||||
></span>
|
></span>
|
||||||
<span
|
<span
|
||||||
@ -164,7 +164,7 @@
|
|||||||
v-tooltip.noDelay="i18n.ts.isAdmin"
|
v-tooltip.noDelay="i18n.ts.isAdmin"
|
||||||
style="color: var(--badge)"
|
style="color: var(--badge)"
|
||||||
><i
|
><i
|
||||||
class="ph-bookmark-simple ph-fill ph-lg"
|
class="ph-crown-simple ph-fill ph-lg"
|
||||||
></i
|
></i
|
||||||
></span>
|
></span>
|
||||||
<span
|
<span
|
||||||
@ -175,7 +175,7 @@
|
|||||||
margin-left: 0.5rem;
|
margin-left: 0.5rem;
|
||||||
"
|
"
|
||||||
><i
|
><i
|
||||||
class="ph-bookmark-simple ph-bold ph-lg"
|
class="ph-crown-simple ph-bold ph-lg"
|
||||||
></i
|
></i
|
||||||
></span>
|
></span>
|
||||||
<span
|
<span
|
||||||
|
@ -594,8 +594,8 @@ export const routes = [
|
|||||||
loginRequired: true,
|
loginRequired: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "/my/favorites",
|
path: "/my/snippets",
|
||||||
component: page(() => import("./pages/favorites.vue")),
|
component: page(() => import("./pages/my-snippets/index.vue")),
|
||||||
loginRequired: true,
|
loginRequired: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -644,11 +644,6 @@ export const routes = [
|
|||||||
component: page(() => import("./pages/my-lists/index.vue")),
|
component: page(() => import("./pages/my-lists/index.vue")),
|
||||||
loginRequired: true,
|
loginRequired: true,
|
||||||
},
|
},
|
||||||
{
|
|
||||||
path: "/my/clips",
|
|
||||||
component: page(() => import("./pages/my-clips/index.vue")),
|
|
||||||
loginRequired: true,
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
path: "/my/groups",
|
path: "/my/groups",
|
||||||
component: page(() => import("./pages/my-groups/index.vue")),
|
component: page(() => import("./pages/my-groups/index.vue")),
|
||||||
|
@ -284,12 +284,12 @@ export function getNoteMenu(props: {
|
|||||||
statePromise.then((state) =>
|
statePromise.then((state) =>
|
||||||
state?.isFavorited
|
state?.isFavorited
|
||||||
? {
|
? {
|
||||||
icon: "ph-bookmark-simple ph-bold ph-lg",
|
icon: "ph-bookmarks ph-bold ph-lg",
|
||||||
text: i18n.ts.unfavorite,
|
text: i18n.ts.unfavorite,
|
||||||
action: () => toggleFavorite(false),
|
action: () => toggleFavorite(false),
|
||||||
}
|
}
|
||||||
: {
|
: {
|
||||||
icon: "ph-bookmark-simple ph-bold ph-lg",
|
icon: "ph-bookmarks ph-bold ph-lg",
|
||||||
text: i18n.ts.favorite,
|
text: i18n.ts.favorite,
|
||||||
action: () => toggleFavorite(true),
|
action: () => toggleFavorite(true),
|
||||||
},
|
},
|
||||||
|
@ -13,10 +13,13 @@ const menuOptions = [
|
|||||||
"followRequests",
|
"followRequests",
|
||||||
"messaging",
|
"messaging",
|
||||||
"-",
|
"-",
|
||||||
"favorites",
|
"snippets",
|
||||||
"announcements",
|
"antennas",
|
||||||
"explore",
|
"explore",
|
||||||
"search",
|
"search",
|
||||||
|
"-",
|
||||||
|
"achievements",
|
||||||
|
"drive"
|
||||||
];
|
];
|
||||||
|
|
||||||
// TODO: それぞれいちいちwhereとかdefaultというキーを付けなきゃいけないの冗長なのでなんとかする(ただ型定義が面倒になりそう)
|
// TODO: それぞれいちいちwhereとかdefaultというキーを付けなきゃいけないの冗長なのでなんとかする(ただ型定義が面倒になりそう)
|
||||||
|
Loading…
Reference in New Issue
Block a user