mirror of
https://github.com/nagisa77/OpenIsle.git
synced 2026-05-09 04:07:31 +08:00
feat: add invite
This commit is contained in:
@@ -29,6 +29,12 @@
|
|||||||
<i :class="iconClass"></i>
|
<i :class="iconClass"></i>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div v-if="!isMobile" class="invite_text" @click="copyInviteLink">
|
||||||
|
<i class="fas fa-copy"></i>
|
||||||
|
邀请
|
||||||
|
<i v-if="isCopying" class="fas fa-spinner fa-spin"></i>
|
||||||
|
</div>
|
||||||
|
|
||||||
<ToolTip v-if="!isMobile && isLogin" content="发帖" placement="bottom">
|
<ToolTip v-if="!isMobile && isLogin" content="发帖" placement="bottom">
|
||||||
<div class="new-post-icon" @click="goToNewPost">
|
<div class="new-post-icon" @click="goToNewPost">
|
||||||
<i class="fas fa-edit"></i>
|
<i class="fas fa-edit"></i>
|
||||||
@@ -66,6 +72,11 @@ import { authState, clearToken, loadCurrentUser } from '~/utils/auth'
|
|||||||
import { fetchUnreadCount, notificationState } from '~/utils/notification'
|
import { fetchUnreadCount, notificationState } from '~/utils/notification'
|
||||||
import { useIsMobile } from '~/utils/screen'
|
import { useIsMobile } from '~/utils/screen'
|
||||||
import { themeState, cycleTheme, ThemeMode } from '~/utils/theme'
|
import { themeState, cycleTheme, ThemeMode } from '~/utils/theme'
|
||||||
|
import { toast } from '~/main'
|
||||||
|
import { getToken } from '~/utils/auth'
|
||||||
|
const config = useRuntimeConfig()
|
||||||
|
const API_BASE_URL = config.public.apiBaseUrl
|
||||||
|
const WEBSITE_BASE_URL = config.public.websiteBaseUrl
|
||||||
|
|
||||||
const props = defineProps({
|
const props = defineProps({
|
||||||
showMenuBtn: {
|
showMenuBtn: {
|
||||||
@@ -82,6 +93,7 @@ const showSearch = ref(false)
|
|||||||
const searchDropdown = ref(null)
|
const searchDropdown = ref(null)
|
||||||
const userMenu = ref(null)
|
const userMenu = ref(null)
|
||||||
const menuBtn = ref(null)
|
const menuBtn = ref(null)
|
||||||
|
const isCopying = ref(false)
|
||||||
|
|
||||||
const search = () => {
|
const search = () => {
|
||||||
showSearch.value = true
|
showSearch.value = true
|
||||||
@@ -100,6 +112,35 @@ const goToLogin = () => {
|
|||||||
const goToSettings = () => {
|
const goToSettings = () => {
|
||||||
navigateTo('/settings', { replace: true })
|
navigateTo('/settings', { replace: true })
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const copyInviteLink = async () => {
|
||||||
|
isCopying.value = true
|
||||||
|
const token = getToken()
|
||||||
|
if (!token) {
|
||||||
|
toast.error('请先登录')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
const res = await fetch(`${API_BASE_URL}/api/invite/generate`, {
|
||||||
|
method: 'POST',
|
||||||
|
headers: { Authorization: `Bearer ${token}` },
|
||||||
|
})
|
||||||
|
if (res.ok) {
|
||||||
|
const data = await res.json()
|
||||||
|
const inviteLink = data.token ? `${WEBSITE_BASE_URL}/signup?invite_token=${data.token}` : ''
|
||||||
|
await navigator.clipboard.writeText(inviteLink)
|
||||||
|
toast.success('邀请链接已复制')
|
||||||
|
} else {
|
||||||
|
const data = await res.json().catch(() => ({}))
|
||||||
|
toast.error(data.error || '生成邀请链接失败')
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
toast.error('生成邀请链接失败')
|
||||||
|
} finally {
|
||||||
|
isCopying.value = false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const goToProfile = async () => {
|
const goToProfile = async () => {
|
||||||
if (!authState.loggedIn) {
|
if (!authState.loggedIn) {
|
||||||
navigateTo('/login', { replace: true })
|
navigateTo('/login', { replace: true })
|
||||||
@@ -224,7 +265,7 @@ onMounted(async () => {
|
|||||||
margin-left: auto;
|
margin-left: auto;
|
||||||
flex-direction: row;
|
flex-direction: row;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
gap: 20px;
|
gap: 30px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.auth-btns {
|
.auth-btns {
|
||||||
@@ -315,6 +356,16 @@ onMounted(async () => {
|
|||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.invite_text {
|
||||||
|
font-size: 12px;
|
||||||
|
cursor: pointer;
|
||||||
|
color: var(--primary-color);
|
||||||
|
}
|
||||||
|
|
||||||
|
.invite_text:hover {
|
||||||
|
text-decoration: underline;
|
||||||
|
}
|
||||||
|
|
||||||
.new-post-icon {
|
.new-post-icon {
|
||||||
font-size: 18px;
|
font-size: 18px;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
|
|||||||
Reference in New Issue
Block a user