添加列表及一键导入
This commit is contained in:
@@ -11,7 +11,7 @@ from api.dp import RedisDep, AltersDep
|
|||||||
from core.basic.equipment import get_equipment
|
from core.basic.equipment import get_equipment
|
||||||
from core.character.adventure import get_adv_list
|
from core.character.adventure import get_adv_list
|
||||||
from core.basic.character import createCharacter
|
from core.basic.character import createCharacter
|
||||||
from core.open.helper import get_user_info_by_id, get_user_list_by_id
|
from core.open.helper import get_user_info_by_id, get_user_info_by_role_id, get_user_list_by_id, getRoleJobCode
|
||||||
from core.open.skillTree import get_skill_tree_info
|
from core.open.skillTree import get_skill_tree_info
|
||||||
from api.core.exception import ResponseException
|
from api.core.exception import ResponseException
|
||||||
|
|
||||||
@@ -34,9 +34,12 @@ def replace_placeholders(template):
|
|||||||
|
|
||||||
|
|
||||||
@router.get('/adventure')
|
@router.get('/adventure')
|
||||||
async def get_adventure_info(request: Request, redis: RedisDep):
|
async def get_adventure_info(request: Request, redis: RedisDep, name: str = None):
|
||||||
adventure_info = get_redis_info(redis, 'dcalc:adventure', get_adv_list)
|
adventure_info = get_redis_info(redis, 'dcalc:adventure', get_adv_list)
|
||||||
|
if name:
|
||||||
|
total = [item for job in adventure_info for item in job.get('children', [])]
|
||||||
|
code = getRoleJobCode(name)
|
||||||
|
adventure_info = next((x for x in total if (x['title'] == name or x['name'] == code) and x['open']), None)
|
||||||
return response(data=adventure_info)
|
return response(data=adventure_info)
|
||||||
|
|
||||||
|
|
||||||
@@ -128,6 +131,18 @@ async def get_dnfhelper_list(uid: str, redis: RedisDep):
|
|||||||
# return response(code=500, message='Failed to fetch DNFHelper list', data=None)
|
# return response(code=500, message='Failed to fetch DNFHelper list', data=None)
|
||||||
|
|
||||||
|
|
||||||
|
@router.get('/dnfhelper/{uid}/{id}/')
|
||||||
|
async def get_dnfhelper_detail(uid: str, id: str, state: AltersDep, redis: RedisDep):
|
||||||
|
cache_key = f'dnfhelper:{uid}:{id}'
|
||||||
|
|
||||||
|
async def get_detail():
|
||||||
|
return await get_user_info_by_role_id(uid, id, state)
|
||||||
|
|
||||||
|
result = await get_redis_info_async(redis, cache_key, get_detail, expire=12 * 60 * 60)
|
||||||
|
return response(data=result)
|
||||||
|
# return response(code=500, message='Failed to fetch DNFHelper detail', data=None)
|
||||||
|
|
||||||
|
|
||||||
@router.get('/dnfhelper/{uid}/')
|
@router.get('/dnfhelper/{uid}/')
|
||||||
async def get_info_by_dnfhelper(uid: str, state: AltersDep, redis: RedisDep):
|
async def get_info_by_dnfhelper(uid: str, state: AltersDep, redis: RedisDep):
|
||||||
try:
|
try:
|
||||||
|
|||||||
@@ -86,6 +86,19 @@ async def get_user_list_by_id(user_id: str):
|
|||||||
return helper_list
|
return helper_list
|
||||||
|
|
||||||
|
|
||||||
|
def getRoleJobCode(jobName: str):
|
||||||
|
return job_mapping.get(jobName, None)
|
||||||
|
|
||||||
|
|
||||||
|
async def get_user_info_by_role_id(user_id: str, role_id: str, alter: AltersDep):
|
||||||
|
# 通过OCR助手获取用户信息
|
||||||
|
helper_info = await get_main_user_info_by_id(user_id, None, role_id)
|
||||||
|
if helper_info is None:
|
||||||
|
raise ResponseException('当前助手ID不存在或已隐藏,请确认后重试')
|
||||||
|
else:
|
||||||
|
return trans_to_dcalc_set(helper_info, alter)
|
||||||
|
|
||||||
|
|
||||||
async def get_user_info_by_id(user_id: str, alter: AltersDep):
|
async def get_user_info_by_id(user_id: str, alter: AltersDep):
|
||||||
if alter is None:
|
if alter is None:
|
||||||
raise ResponseException('登录过期或无效Token,请刷新后重试')
|
raise ResponseException('登录过期或无效Token,请刷新后重试')
|
||||||
|
|||||||
+1
-1
Submodule backend/openapi updated: be3ff246ed...0c65d37e63
@@ -1,5 +1,5 @@
|
|||||||
import { defineRequest } from '../common'
|
import { defineRequest } from '../common'
|
||||||
import type { IAdventureInfo, ICharacterInfo, IHelperInfo, ISkillInfo } from './type'
|
import type { IAdventureInfo, IAlterInfo, ICharacterInfo, IHelperInfo, ISkillInfo } from './type'
|
||||||
|
|
||||||
export default defineRequest((request) => {
|
export default defineRequest((request) => {
|
||||||
return {
|
return {
|
||||||
@@ -7,6 +7,10 @@ export default defineRequest((request) => {
|
|||||||
const res = await request.get<IAdventureInfo[]>('/adventure')
|
const res = await request.get<IAdventureInfo[]>('/adventure')
|
||||||
return res.data
|
return res.data
|
||||||
},
|
},
|
||||||
|
async alterByName(name: string) {
|
||||||
|
const res = await request.get<IAlterInfo>('/adventure', { params: { name } })
|
||||||
|
return res.data
|
||||||
|
},
|
||||||
async createToken(alter: string, equVersion?: string) {
|
async createToken(alter: string, equVersion?: string) {
|
||||||
const res = await request.get<string>(`/token/get/${alter}`, { params: { equVersion } })
|
const res = await request.get<string>(`/token/get/${alter}`, { params: { equVersion } })
|
||||||
return res.data
|
return res.data
|
||||||
@@ -23,6 +27,10 @@ export default defineRequest((request) => {
|
|||||||
const res = await request.get(`/dnfhelper/${uid}/`)
|
const res = await request.get(`/dnfhelper/${uid}/`)
|
||||||
return res.data
|
return res.data
|
||||||
},
|
},
|
||||||
|
async getConfigFromHelperAlter(uid: string, alter: string) {
|
||||||
|
const res = await request.get(`/dnfhelper/${uid}/${alter}`)
|
||||||
|
return res.data
|
||||||
|
},
|
||||||
async getSkillFromCode(code: string) {
|
async getSkillFromCode(code: string) {
|
||||||
const res = await request.post(`/skillTree/`, { code })
|
const res = await request.post(`/skillTree/`, { code })
|
||||||
return res.data
|
return res.data
|
||||||
|
|||||||
@@ -216,15 +216,17 @@ export interface Attribute {
|
|||||||
detail: string
|
detail: string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface IHelperRoleInfo {
|
||||||
|
roleId: string
|
||||||
|
roleName: string
|
||||||
|
roleJob: string
|
||||||
|
avatarLink: string
|
||||||
|
fame: number
|
||||||
|
}
|
||||||
|
|
||||||
export interface IHelperInfo {
|
export interface IHelperInfo {
|
||||||
id: string
|
id: string
|
||||||
avatar: string
|
avatar: string
|
||||||
name: string
|
name: string
|
||||||
roleList: {
|
roleList: IHelperRoleInfo[]
|
||||||
roleId: string
|
|
||||||
roleName: string
|
|
||||||
roleJob: string
|
|
||||||
avatarLink: string
|
|
||||||
fame: number
|
|
||||||
}[]
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,80 @@
|
|||||||
|
<script lang="tsx">
|
||||||
|
import { useAsyncState } from '@vueuse/core'
|
||||||
|
import { defineComponent, ref } from 'vue'
|
||||||
|
import api from '@/api'
|
||||||
|
import { useDialog } from '@/components/hooks/dialog'
|
||||||
|
import { isShow, onShow } from '@/components/hooks/show'
|
||||||
|
import { useConfigStore } from '@/stores'
|
||||||
|
import { type IHelperRoleInfo } from '@/api/info/type'
|
||||||
|
|
||||||
|
export default defineComponent({
|
||||||
|
props: {
|
||||||
|
alter: {
|
||||||
|
type: Object as () => IHelperRoleInfo,
|
||||||
|
},
|
||||||
|
uid: {
|
||||||
|
type: String,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
setup(props) {
|
||||||
|
const configStore = useConfigStore()
|
||||||
|
const { state, execute, isLoading } = useAsyncState(
|
||||||
|
async () => {
|
||||||
|
const res = await api.getConfigFromHelperAlter(props.uid || '', props.alter?.roleId || '')
|
||||||
|
configStore.config.equips = res.equips
|
||||||
|
configStore.config.avatar = res.avatars
|
||||||
|
configStore.config.avatarLink = res.avatarLink
|
||||||
|
configStore.config.emblems = res.emblems
|
||||||
|
configStore.config.sundry.fog = res.fogOathLv
|
||||||
|
configStore.config.oaths = res.oaths
|
||||||
|
const { alert } = useDialog()
|
||||||
|
visible.value = false
|
||||||
|
await alert({
|
||||||
|
content: '导入成功',
|
||||||
|
})
|
||||||
|
return res
|
||||||
|
},
|
||||||
|
undefined,
|
||||||
|
{
|
||||||
|
resetOnExecute: false,
|
||||||
|
immediate: false,
|
||||||
|
onError: Promise.reject,
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
|
onShow(
|
||||||
|
() => {
|
||||||
|
state.value = undefined
|
||||||
|
},
|
||||||
|
{ immediate: true },
|
||||||
|
)
|
||||||
|
|
||||||
|
const visible = isShow()
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<div class="h-45 w-80 py-2 px-4 text-#e9c556">
|
||||||
|
<div class="flex justify-around items-center flex-col gap-1">
|
||||||
|
<div>检测到以下信息,是否导入助手数据?</div>
|
||||||
|
<div class="text-#DED29A">{props.alter?.roleName}</div>
|
||||||
|
<div class="text-#908150">{props.alter?.roleJob}</div>
|
||||||
|
<div class="text-#3ea74e">名望:{props.alter?.fame}</div>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<p class="text-#e9c556/80">* 点击导入后会从助手通过文字识别获取打造</p>
|
||||||
|
<p class="text-#e9c556/80">* 部分打造无法获取,此处仅做快捷导入</p>
|
||||||
|
</div>
|
||||||
|
<div class="flex justify-around items-center">
|
||||||
|
<calc-button onClick={execute} disabled={isLoading.value}>
|
||||||
|
导入
|
||||||
|
</calc-button>
|
||||||
|
<calc-button onClick={() => (visible.value = false)}>取消</calc-button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
})
|
||||||
|
</script>
|
||||||
@@ -1,7 +1,7 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="w-100% h-100% main flex" :class="infoStore.infos?.alter">
|
<div class="w-100% h-100% main flex" :class="infoStore.infos?.alter">
|
||||||
<div class="header">
|
<div class="header">
|
||||||
<calc-tabs route>
|
<calc-tabs route :query="route.query">
|
||||||
<calc-tab :value="`/character/equipment/${props.alter}`">装备设置</calc-tab>
|
<calc-tab :value="`/character/equipment/${props.alter}`">装备设置</calc-tab>
|
||||||
<calc-tab :value="`/character/skill/${props.alter}`">技能设置</calc-tab>
|
<calc-tab :value="`/character/skill/${props.alter}`">技能设置</calc-tab>
|
||||||
<calc-tab :value="`/character/forge/${props.alter}`">打造设置</calc-tab>
|
<calc-tab :value="`/character/forge/${props.alter}`">打造设置</calc-tab>
|
||||||
@@ -38,6 +38,10 @@
|
|||||||
<calc-dialog lazy header="技能导入" v-model:visible="importSkillVisible">
|
<calc-dialog lazy header="技能导入" v-model:visible="importSkillVisible">
|
||||||
<ImportSkillVue></ImportSkillVue>
|
<ImportSkillVue></ImportSkillVue>
|
||||||
</calc-dialog>
|
</calc-dialog>
|
||||||
|
|
||||||
|
<calc-dialog lazy header="助手打造导入" v-model:visible="helperImport">
|
||||||
|
<ImportDnfhelper :alter="toImport" :uid="helperStore.helperInfo?.id"></ImportDnfhelper>
|
||||||
|
</calc-dialog>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts" setup name="Index">
|
<script lang="ts" setup name="Index">
|
||||||
@@ -45,16 +49,22 @@ import { useInfoStore } from '@/stores/info'
|
|||||||
import { useConfigStore } from '@/stores'
|
import { useConfigStore } from '@/stores'
|
||||||
import ImportVue from './Config/import.vue'
|
import ImportVue from './Config/import.vue'
|
||||||
import ImportSkillVue from './Config/importSkill.vue'
|
import ImportSkillVue from './Config/importSkill.vue'
|
||||||
|
import ImportDnfhelper from './Config/importDnfhelper.vue'
|
||||||
import Result from './Result/Index.vue'
|
import Result from './Result/Index.vue'
|
||||||
|
import { useDnfHelperStore } from '@/stores/dnfhelper.ts'
|
||||||
|
import { type IHelperRoleInfo } from '@/api/info/type'
|
||||||
const props = defineProps<{
|
const props = defineProps<{
|
||||||
alter: string
|
alter: string
|
||||||
}>()
|
}>()
|
||||||
const infoStore = useInfoStore()
|
const infoStore = useInfoStore()
|
||||||
const configStore = useConfigStore()
|
const configStore = useConfigStore()
|
||||||
|
const helperImport = ref(false)
|
||||||
const importVisible = ref(false)
|
const importVisible = ref(false)
|
||||||
const importSkillVisible = ref(false)
|
const importSkillVisible = ref(false)
|
||||||
|
const helperStore = useDnfHelperStore()
|
||||||
|
const toImport = ref<IHelperRoleInfo>()
|
||||||
|
|
||||||
const shouldWatch = ref(true)
|
// const shouldWatch = ref(true)
|
||||||
|
|
||||||
const isExecuting = ref(false)
|
const isExecuting = ref(false)
|
||||||
|
|
||||||
@@ -81,11 +91,22 @@ const showImport = () => {
|
|||||||
const showImportSkill = () => {
|
const showImportSkill = () => {
|
||||||
importSkillVisible.value = true
|
importSkillVisible.value = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const route = useRoute()
|
||||||
|
|
||||||
onMounted(async () => {
|
onMounted(async () => {
|
||||||
await infoStore.createCharacter(props.alter, '0')
|
await infoStore.createCharacter(props.alter, '0')
|
||||||
window.addEventListener('beforeunload', () => {
|
window.addEventListener('beforeunload', () => {
|
||||||
configStore.saveConfig()
|
configStore.saveConfig()
|
||||||
})
|
})
|
||||||
|
// 检测router的传参
|
||||||
|
const { roleId } = route.query
|
||||||
|
if (roleId) {
|
||||||
|
toImport.value = helperStore.helperInfo?.roleList.find((a) => a.roleId === roleId)
|
||||||
|
if (toImport.value) {
|
||||||
|
helperImport.value = true
|
||||||
|
}
|
||||||
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
onUnmounted(() => {
|
onUnmounted(() => {
|
||||||
|
|||||||
@@ -39,6 +39,8 @@
|
|||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
<script setup lang="ts" name="dnfhelper-list">
|
<script setup lang="ts" name="dnfhelper-list">
|
||||||
|
import api from '@/api'
|
||||||
|
import { useDialog } from '@/components/hooks/dialog'
|
||||||
import router from '@/router'
|
import router from '@/router'
|
||||||
import { useDnfHelperStore } from '@/stores/dnfhelper'
|
import { useDnfHelperStore } from '@/stores/dnfhelper'
|
||||||
import { computed } from 'vue'
|
import { computed } from 'vue'
|
||||||
@@ -70,12 +72,24 @@ const navToHome = () => {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const chooseRole = ({ roleId }: { roleId: string }) => {
|
const chooseRole = ({ roleId }: { roleId: string }) => {
|
||||||
console.log(roleId)
|
|
||||||
acitveRoleId.value = roleId
|
acitveRoleId.value = roleId
|
||||||
}
|
}
|
||||||
|
|
||||||
const importRole = () => {
|
const { alert } = useDialog()
|
||||||
console.log('import')
|
|
||||||
|
const currentRoleInfo = computed(() => {
|
||||||
|
return list.value.find((item) => item.roleId === acitveRoleId.value)
|
||||||
|
})
|
||||||
|
|
||||||
|
const importRole = async () => {
|
||||||
if (!acitveRoleId.value) return
|
if (!acitveRoleId.value) return
|
||||||
|
const alter = await api.alterByName(currentRoleInfo.value?.roleJob || '')
|
||||||
|
if (!alter) {
|
||||||
|
return await alert({
|
||||||
|
content: '当前职业尚在开发中,敬请期待。',
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
return window.open(`/character/equipment/${alter.value}?roleId=${acitveRoleId.value}`, '_blank')
|
||||||
|
}
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ const routes: RouteRecordRaw[] = [
|
|||||||
{
|
{
|
||||||
path: '/character/:alter',
|
path: '/character/:alter',
|
||||||
redirect: (to) => {
|
redirect: (to) => {
|
||||||
return { path: `/character/equipment/${to.params.alter}` }
|
return { path: `/character/equipment/${to.params.alter}`, query: to.query }
|
||||||
},
|
},
|
||||||
props: true,
|
props: true,
|
||||||
name: 'character',
|
name: 'character',
|
||||||
|
|||||||
@@ -49,12 +49,12 @@ export default defineConfig({
|
|||||||
proxy: {
|
proxy: {
|
||||||
'/api': {
|
'/api': {
|
||||||
target: 'http://127.0.0.1:47173/api',
|
target: 'http://127.0.0.1:47173/api',
|
||||||
changeOrigin: true,
|
changeOrigin: false,
|
||||||
rewrite: (path) => path.replace(/^\/api/, ''),
|
rewrite: (path) => path.replace(/^\/api/, ''),
|
||||||
},
|
},
|
||||||
'/image': {
|
'/image': {
|
||||||
target: 'http://127.0.0.1:3000',
|
target: 'http://127.0.0.1:3000',
|
||||||
changeOrigin: true,
|
changeOrigin: false,
|
||||||
rewrite: (path) => path.replace(/^\/image/, ''),
|
rewrite: (path) => path.replace(/^\/image/, ''),
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|||||||
Reference in New Issue
Block a user