save
This commit is contained in:
@@ -4,13 +4,13 @@ import { BaseState, useBaseStore } from "@/stores/base.ts";
|
||||
import { useRuntimeStore } from "@/stores/runtime.ts";
|
||||
import { useSettingStore } from "@/stores/setting.ts";
|
||||
import useTheme from "@/hooks/theme.ts";
|
||||
import { APP_VERSION, LOCAL_FILE_KEY, SAVE_DICT_KEY, SAVE_SETTING_KEY } from "@/utils/const.ts";
|
||||
import { shakeCommonDict } from "@/utils";
|
||||
import { routes } from "@/router.ts";
|
||||
import { get, set } from 'idb-keyval'
|
||||
|
||||
import { useRoute } from "vue-router";
|
||||
import { DictId } from "@/types/types.ts";
|
||||
import { APP_VERSION, LOCAL_FILE_KEY, SAVE_DICT_KEY, SAVE_SETTING_KEY } from "@/config/ENV.ts";
|
||||
|
||||
const store = useBaseStore()
|
||||
const runtimeStore = useRuntimeStore()
|
||||
|
||||
5
src/apis/index.ts
Normal file
5
src/apis/index.ts
Normal file
@@ -0,0 +1,5 @@
|
||||
import http from "@/utils/http.ts";
|
||||
|
||||
export function officialList() {
|
||||
return http('dict/officialList', null, null, 'get')
|
||||
}
|
||||
@@ -1,56 +1,54 @@
|
||||
[
|
||||
[
|
||||
{
|
||||
"id": "article_nce1",
|
||||
"name": "新概念英语1-课文",
|
||||
"description": "",
|
||||
"category": "文章学习",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "NCE_1.json",
|
||||
"length": 72,
|
||||
"translateLanguage": "common",
|
||||
"language": "en"
|
||||
},
|
||||
{
|
||||
"id": "article_nce2",
|
||||
"name": "新概念英语2-课文",
|
||||
"description": "新概念英语2-课文",
|
||||
"category": "文章学习",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "NCE_2.json",
|
||||
"length": 96,
|
||||
"translateLanguage": "common",
|
||||
"language": "en"
|
||||
},
|
||||
{
|
||||
"id": "article_nce3",
|
||||
"name": "新概念英语3-课文",
|
||||
"description": "新概念英语3-课文",
|
||||
"category": "文章学习",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "NCE_3.json",
|
||||
"length": 60,
|
||||
"translateLanguage": "common",
|
||||
"language": "en"
|
||||
},
|
||||
{
|
||||
"id": "article_nce4",
|
||||
"name": "新概念英语4-课文",
|
||||
"description": "新概念英语4-课文",
|
||||
"category": "文章学习",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "NCE_4.json",
|
||||
"length": 48,
|
||||
"translateLanguage": "common",
|
||||
"language": "en"
|
||||
}
|
||||
]
|
||||
{
|
||||
"id": "article_nce1",
|
||||
"name": "新概念英语1-课文",
|
||||
"description": "",
|
||||
"category": "文章学习",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "NCE_1.json",
|
||||
"length": 72,
|
||||
"translateLanguage": "common",
|
||||
"language": "en"
|
||||
},
|
||||
{
|
||||
"id": "article_nce2",
|
||||
"name": "新概念英语2-课文",
|
||||
"description": "新概念英语2-课文",
|
||||
"category": "文章学习",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "NCE_2.json",
|
||||
"length": 96,
|
||||
"translateLanguage": "common",
|
||||
"language": "en"
|
||||
},
|
||||
{
|
||||
"id": "article_nce3",
|
||||
"name": "新概念英语3-课文",
|
||||
"description": "新概念英语3-课文",
|
||||
"category": "文章学习",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "NCE_3.json",
|
||||
"length": 60,
|
||||
"translateLanguage": "common",
|
||||
"language": "en"
|
||||
},
|
||||
{
|
||||
"id": "article_nce4",
|
||||
"name": "新概念英语4-课文",
|
||||
"description": "新概念英语4-课文",
|
||||
"category": "文章学习",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "NCE_4.json",
|
||||
"length": 48,
|
||||
"translateLanguage": "common",
|
||||
"language": "en"
|
||||
}
|
||||
]
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,184 +0,0 @@
|
||||
[
|
||||
{
|
||||
"id": "cet4",
|
||||
"name": "CET-4",
|
||||
"description": "大学英语四级词库",
|
||||
"category": "中国考试",
|
||||
"tags": [
|
||||
"大学英语"
|
||||
],
|
||||
"url": "CET4_T.json",
|
||||
"length": 2607,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "cet6",
|
||||
"name": "CET-6",
|
||||
"description": "大学英语六级词库",
|
||||
"category": "中国考试",
|
||||
"tags": [
|
||||
"大学英语"
|
||||
],
|
||||
"url": "CET6_T.json",
|
||||
"length": 2345,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "level4",
|
||||
"name": "专四",
|
||||
"description": "英语专业四级词库",
|
||||
"category": "中国考试",
|
||||
"tags": [
|
||||
"大学英语"
|
||||
],
|
||||
"url": "Level4luan_2_T.json",
|
||||
"length": 4025,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "level8",
|
||||
"name": "专八",
|
||||
"description": "英语专业八级词库",
|
||||
"category": "中国考试",
|
||||
"tags": [
|
||||
"大学英语"
|
||||
],
|
||||
"url": "Level8luan_2_T.json",
|
||||
"length": 12197,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "kaoyan",
|
||||
"name": "考研",
|
||||
"description": "研究生英语入学考试词库",
|
||||
"category": "中国考试",
|
||||
"tags": [
|
||||
"考研"
|
||||
],
|
||||
"url": "KaoYan_3_T.json",
|
||||
"length": 3728,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "toefl",
|
||||
"name": "TOEFL",
|
||||
"description": "托福考试常见词",
|
||||
"category": "国际考试",
|
||||
"tags": [
|
||||
"TOEFL"
|
||||
],
|
||||
"url": "TOEFL_3_T.json",
|
||||
"length": 4264,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "ielts",
|
||||
"name": "IELTS",
|
||||
"description": "雅思词库",
|
||||
"category": "国际考试",
|
||||
"tags": [
|
||||
"IELTS"
|
||||
],
|
||||
"url": "IELTS_3_T.json",
|
||||
"length": 3575,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "gaokao3500",
|
||||
"name": "高考 3500 词",
|
||||
"description": "高考常见词 3500",
|
||||
"category": "青少年英语",
|
||||
"tags": [
|
||||
"通用"
|
||||
],
|
||||
"url": "GaoKao_3500.json",
|
||||
"length": 3893,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "coder",
|
||||
"name": "Coder Dict",
|
||||
"description": "程序员常见单词词库",
|
||||
"category": "代码练习",
|
||||
"tags": [
|
||||
"通用"
|
||||
],
|
||||
"url": "it-words.json",
|
||||
"length": 1700,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "itVocabulary",
|
||||
"name": "计算机专用英语",
|
||||
"description": "大学计算机专业英语词汇",
|
||||
"category": "代码练习",
|
||||
"tags": [
|
||||
"通用"
|
||||
],
|
||||
"url": "itVocabulary.json",
|
||||
"length": 1665,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "nce-new-1",
|
||||
"name": "新概念英语-1",
|
||||
"description": "新概念英语第一册",
|
||||
"category": "青少年英语",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "nce-new-1.json",
|
||||
"length": 908,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "nce-new-2",
|
||||
"name": "新概念英语-2",
|
||||
"description": "新概念英语第二册",
|
||||
"category": "青少年英语",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "nce-new-2.json",
|
||||
"length": 862,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "nce-new-3",
|
||||
"name": "新概念英语-3",
|
||||
"description": "新概念英语第三册",
|
||||
"category": "青少年英语",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "nce-new-3.json",
|
||||
"length": 1062,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
},
|
||||
{
|
||||
"id": "nce-new-4",
|
||||
"name": "新概念英语-4",
|
||||
"description": "新概念英语第四册",
|
||||
"category": "青少年英语",
|
||||
"tags": [
|
||||
"新概念英语"
|
||||
],
|
||||
"url": "nce-new-4.json",
|
||||
"length": 793,
|
||||
"language": "en",
|
||||
"translateLanguage": "zh-CN"
|
||||
}
|
||||
]
|
||||
@@ -2,13 +2,58 @@ export const GITHUB = 'https://github.com/zyronon/TypeWords'
|
||||
export const ProjectName = 'Type Words'
|
||||
export const Host = '2study.top'
|
||||
export const Origin = `https://${Host}`
|
||||
export const APP_NAME = 'Type Words'
|
||||
|
||||
const common = {
|
||||
word_dict_list_version: 1
|
||||
}
|
||||
const map = {
|
||||
dev: {
|
||||
api: 'http://localhost/index.php',
|
||||
api: 'http://localhost/',
|
||||
}
|
||||
}
|
||||
export const env = Object.assign(map['dev'], common)
|
||||
|
||||
export const DICT_LIST = {
|
||||
WORD: {
|
||||
ALL: '/list/dict-list.json',
|
||||
RECOMMENDED: '/list/recommend-dict-list.json',
|
||||
},
|
||||
ARTICLE: {
|
||||
ALL: '/list/book-list.json',
|
||||
RECOMMENDED: '/list/book-list.json',
|
||||
}
|
||||
}
|
||||
|
||||
export const SoundFileOptions = [
|
||||
{value: '机械键盘', label: '机械键盘'},
|
||||
{value: '机械键盘1', label: '机械键盘1'},
|
||||
{value: '机械键盘2', label: '机械键盘2'},
|
||||
{value: '老式机械键盘', label: '老式机械键盘'},
|
||||
{value: '笔记本键盘', label: '笔记本键盘'},
|
||||
]
|
||||
export const APP_VERSION = {
|
||||
key: 'type-words-app-version',
|
||||
version: 1
|
||||
}
|
||||
export const SAVE_DICT_KEY = {
|
||||
key: 'typing-word-dict',
|
||||
version: 4
|
||||
}
|
||||
export const SAVE_SETTING_KEY = {
|
||||
key: 'typing-word-setting',
|
||||
version: 15
|
||||
}
|
||||
export const EXPORT_DATA_KEY = {
|
||||
key: 'typing-word-export',
|
||||
version: 4
|
||||
}
|
||||
export const LOCAL_FILE_KEY = 'typing-word-files'
|
||||
export const PracticeSaveWordKey = {
|
||||
key: 'PracticeSaveWord',
|
||||
version: 1
|
||||
}
|
||||
export const PracticeSaveArticleKey = {
|
||||
key: 'PracticeSaveArticle',
|
||||
version: 1
|
||||
}
|
||||
@@ -1,5 +1,6 @@
|
||||
// src/directives/loading.js
|
||||
import {createApp, h} from 'vue'
|
||||
//@ts-ignore
|
||||
import IconEosIconsLoading from '~icons/eos-icons/loading'
|
||||
|
||||
// 创建一个 Loading 组件
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
import {onMounted, watchEffect} from "vue"
|
||||
import {useSettingStore} from "@/stores/setting.ts";
|
||||
import {PronunciationApi} from "@/types/types.ts";
|
||||
import {SoundFileOptions} from "@/utils/const.ts";
|
||||
|
||||
import { SoundFileOptions } from "@/config/ENV.ts";
|
||||
|
||||
export function useSound(audioSrcList?: string[], audioFileLength?: number) {
|
||||
let audioList: HTMLAudioElement[] = $ref([])
|
||||
|
||||
@@ -14,11 +14,11 @@ import PopConfirm from "@/components/PopConfirm.vue";
|
||||
import { watch } from "vue";
|
||||
import { getDefaultDict } from "@/types/func.ts";
|
||||
import DeleteIcon from "@/components/icon/DeleteIcon.vue";
|
||||
import recommendBookList from "@/assets/book-list.json";
|
||||
import dayjs from "dayjs";
|
||||
import isBetween from "dayjs/plugin/isBetween";
|
||||
import { PracticeSaveArticleKey } from "@/utils/const.ts";
|
||||
import isoWeek from 'dayjs/plugin/isoWeek'
|
||||
import { useFetch } from "@vueuse/core";
|
||||
import { DICT_LIST, PracticeSaveArticleKey } from "@/config/ENV.ts";
|
||||
|
||||
dayjs.extend(isoWeek)
|
||||
dayjs.extend(isBetween);
|
||||
@@ -152,6 +152,9 @@ const weekList = $computed(() => {
|
||||
});
|
||||
return list
|
||||
})
|
||||
|
||||
const {data: recommendBookList, isFetching} = useFetch(DICT_LIST.ARTICLE.RECOMMENDED).json()
|
||||
|
||||
</script>
|
||||
|
||||
<template>
|
||||
@@ -246,7 +249,8 @@ const weekList = $computed(() => {
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="card flex flex-col">
|
||||
|
||||
<div class="card flex flex-col min-h-50" v-loading="isFetching">
|
||||
<div class="flex justify-between">
|
||||
<div class="title">推荐</div>
|
||||
<div class="flex gap-4 items-center">
|
||||
@@ -258,7 +262,7 @@ const weekList = $computed(() => {
|
||||
<Book :is-add="false"
|
||||
quantifier="篇"
|
||||
:item="item as any"
|
||||
v-for="(item, j) in recommendBookList[0]" @click="goBookDetail(item as any)"/>
|
||||
v-for="(item, j) in recommendBookList" @click="goBookDetail(item as any)"/>
|
||||
</div>
|
||||
</div>
|
||||
</BasePage>
|
||||
|
||||
@@ -11,15 +11,16 @@ import BaseButton from "@/components/BaseButton.vue";
|
||||
import { useRoute, useRouter } from "vue-router";
|
||||
import EditBook from "@/pages/article/components/EditBook.vue";
|
||||
import { computed, onMounted } from "vue";
|
||||
import { _dateFormat, _getDictDataByUrl, cloneDeep, msToHourMinute, total, useNav } from "@/utils";
|
||||
import { _dateFormat, _getDictDataByUrl, msToHourMinute, total, useNav } from "@/utils";
|
||||
import BaseIcon from "@/components/BaseIcon.vue";
|
||||
import { useArticleOptions } from "@/hooks/dict.ts";
|
||||
import { getDefaultArticle, getDefaultDict } from "@/types/func.ts";
|
||||
import Toast from "@/components/base/toast/Toast.ts";
|
||||
import ArticleAudio from "@/pages/article/components/ArticleAudio.vue";
|
||||
import { MessageBox } from "@/utils/MessageBox.tsx";
|
||||
import book_list from "@/assets/book-list.json";
|
||||
import { useSettingStore } from "@/stores/setting.ts";
|
||||
import { useFetch } from "@vueuse/core";
|
||||
import { DICT_LIST } from "@/config/ENV.ts";
|
||||
|
||||
const runtimeStore = useRuntimeStore()
|
||||
const settingStore = useSettingStore()
|
||||
@@ -109,12 +110,14 @@ const {
|
||||
toggleArticleCollect
|
||||
} = useArticleOptions()
|
||||
|
||||
const {data: book_list} = useFetch(DICT_LIST.ARTICLE.ALL).json()
|
||||
|
||||
function reset() {
|
||||
MessageBox.confirm(
|
||||
'继续此操作会重置所有文章,并从官方书籍获取最新文章列表,学习记录不会被重置。确认恢复默认吗?',
|
||||
'恢复默认',
|
||||
async () => {
|
||||
let dict = book_list.flat().find(v => v.url === runtimeStore.editDict.url) as Dict
|
||||
let dict = book_list.value.find(v => v.url === runtimeStore.editDict.url) as Dict
|
||||
if (dict && dict.id) {
|
||||
dict = await _getDictDataByUrl(dict, DictType.article)
|
||||
let rIndex = base.article.bookList.findIndex(v => v.id === runtimeStore.editDict.id)
|
||||
|
||||
@@ -1,18 +1,19 @@
|
||||
<script setup lang="ts">
|
||||
import {useNav} from "@/utils";
|
||||
import { useNav } from "@/utils";
|
||||
import BasePage from "@/components/BasePage.vue";
|
||||
import {DictResource} from "@/types/types.ts";
|
||||
import {useRuntimeStore} from "@/stores/runtime.ts";
|
||||
import { DictResource } from "@/types/types.ts";
|
||||
import { useRuntimeStore } from "@/stores/runtime.ts";
|
||||
import BaseIcon from "@/components/BaseIcon.vue";
|
||||
import Empty from "@/components/Empty.vue";
|
||||
import Input from "@/components/Input.vue";
|
||||
import BaseButton from "@/components/BaseButton.vue";
|
||||
import DictList from "@/components/list/DictList.vue";
|
||||
import BackIcon from "@/components/BackIcon.vue";
|
||||
import {useRouter} from "vue-router";
|
||||
import book_list from "@/assets/book-list.json";
|
||||
import {computed} from "vue";
|
||||
import {getDefaultDict} from "@/types/func.ts";
|
||||
import { useRouter } from "vue-router";
|
||||
import { computed } from "vue";
|
||||
import { getDefaultDict } from "@/types/func.ts";
|
||||
import { useFetch } from "@vueuse/core";
|
||||
import { DICT_LIST } from "@/config/ENV.ts";
|
||||
|
||||
const {nav} = useNav()
|
||||
const runtimeStore = useRuntimeStore()
|
||||
@@ -30,11 +31,12 @@ async function getDictDetail(val: DictResource) {
|
||||
|
||||
let showSearchInput = $ref(false)
|
||||
let searchKey = $ref('')
|
||||
const {data: bookList, isFetching} = useFetch(DICT_LIST.ARTICLE.ALL).json()
|
||||
|
||||
const searchList = computed<any[]>(() => {
|
||||
if (searchKey) {
|
||||
let s = searchKey.toLowerCase()
|
||||
return book_list.flat().filter((item) => {
|
||||
return bookList.value.filter((item) => {
|
||||
return item.id.toLowerCase().includes(s)
|
||||
|| item.name.toLowerCase().includes(s)
|
||||
|| item.category.toLowerCase().includes(s)
|
||||
@@ -49,7 +51,7 @@ const searchList = computed<any[]>(() => {
|
||||
|
||||
<template>
|
||||
<BasePage>
|
||||
<div class="card">
|
||||
<div class="card min-h-50" v-loading="isFetching">
|
||||
<div class="flex items-center relative gap-2">
|
||||
<BackIcon class="z-2" @Click='router.back'/>
|
||||
<div class="flex flex-1 gap-4" v-if="showSearchInput">
|
||||
@@ -75,9 +77,9 @@ const searchList = computed<any[]>(() => {
|
||||
</div>
|
||||
<div class="w-full mt-2" v-else>
|
||||
<DictList
|
||||
v-if="book_list.flat().length "
|
||||
v-if="bookList?.length "
|
||||
@selectDict="selectDict"
|
||||
:list="book_list.flat()"
|
||||
:list="bookList"
|
||||
quantifier="篇"
|
||||
:select-id="'-1'"/>
|
||||
</div>
|
||||
|
||||
@@ -31,11 +31,10 @@ import EditSingleArticleModal from "@/pages/article/components/EditSingleArticle
|
||||
import Tooltip from "@/components/base/Tooltip.vue";
|
||||
import ConflictNotice from "@/components/ConflictNotice.vue";
|
||||
import { useRoute, useRouter } from "vue-router";
|
||||
import book_list from "@/assets/book-list.json";
|
||||
import PracticeLayout from "@/components/PracticeLayout.vue";
|
||||
import ArticleAudio from "@/pages/article/components/ArticleAudio.vue";
|
||||
import { PracticeSaveArticleKey } from "@/utils/const.ts";
|
||||
import VolumeSetting from "@/pages/article/components/VolumeSetting.vue";
|
||||
import { DICT_LIST, PracticeSaveArticleKey } from "@/config/ENV.ts";
|
||||
|
||||
const store = useBaseStore()
|
||||
const settingStore = useSettingStore()
|
||||
@@ -51,7 +50,6 @@ let typingArticleRef = $ref<any>()
|
||||
let loading = $ref<boolean>(false)
|
||||
let allWrongWords = new Set()
|
||||
let editArticle = $ref<Article>(getDefaultArticle())
|
||||
let speedMinute = $ref(0)
|
||||
let timer = $ref(0)
|
||||
let isFocus = true
|
||||
|
||||
@@ -109,6 +107,8 @@ async function init() {
|
||||
if (dictId) {
|
||||
//先在自己的词典列表里面找,如果没有再在资源列表里面找
|
||||
dict = store.article.bookList.find(v => v.id === dictId)
|
||||
let r = await fetch(DICT_LIST.ARTICLE.ALL)
|
||||
let book_list = await r.json()
|
||||
if (!dict) dict = book_list.flat().find(v => v.id === dictId) as Dict
|
||||
if (dict && dict.id) {
|
||||
//如果是不是自定义词典,就请求数据
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
<script setup lang="ts">
|
||||
import { Article } from "@/types/types.ts";
|
||||
import { watch } from "vue";
|
||||
import { LOCAL_FILE_KEY } from "@/utils/const.ts";
|
||||
import { get } from "idb-keyval";
|
||||
import Audio from "@/components/base/Audio.vue";
|
||||
import { LOCAL_FILE_KEY } from "@/config/ENV.ts";
|
||||
|
||||
const props = defineProps<{
|
||||
article: Article
|
||||
|
||||
@@ -18,10 +18,10 @@ import Tooltip from "@/components/base/Tooltip.vue";
|
||||
import InputNumber from "@/components/base/InputNumber.vue";
|
||||
import {nanoid} from "nanoid";
|
||||
import {update} from "idb-keyval";
|
||||
import {LOCAL_FILE_KEY} from "@/utils/const.ts";
|
||||
import ArticleAudio from "@/pages/article/components/ArticleAudio.vue";
|
||||
import BaseInput from "@/components/base/BaseInput.vue";
|
||||
import Textarea from "@/components/base/Textarea.vue";
|
||||
import { LOCAL_FILE_KEY } from "@/config/ENV.ts";
|
||||
|
||||
const Dialog = defineAsyncComponent(() => import('@/components/dialog/Dialog.vue'))
|
||||
|
||||
|
||||
@@ -18,8 +18,8 @@ import Space from "@/pages/article/components/Space.vue";
|
||||
import { useWordOptions } from "@/hooks/dict.ts";
|
||||
import nlp from "compromise/three";
|
||||
import { nanoid } from "nanoid";
|
||||
import { PracticeSaveArticleKey } from "@/utils/const.ts";
|
||||
import { usePracticeStore } from "@/stores/practice.ts";
|
||||
import { PracticeSaveArticleKey } from "@/config/ENV.ts";
|
||||
|
||||
interface IProps {
|
||||
article: Article,
|
||||
|
||||
@@ -38,7 +38,3 @@ useWindowClick(() => show = false)
|
||||
</MiniDialog>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style scoped lang="scss">
|
||||
@import "@/assets/css/style";
|
||||
</style>
|
||||
@@ -6,20 +6,17 @@ import { getShortcutKey, useEventListener } from "@/hooks/event.ts";
|
||||
import { checkAndUpgradeSaveDict, checkAndUpgradeSaveSetting, cloneDeep, loadJsLib, shakeCommonDict } from "@/utils";
|
||||
import { DefaultShortcutKeyMap, ShortcutKey } from "@/types/types.ts";
|
||||
import BaseButton from "@/components/BaseButton.vue";
|
||||
import {
|
||||
APP_NAME,
|
||||
APP_VERSION,
|
||||
EXPORT_DATA_KEY,
|
||||
LOCAL_FILE_KEY, PracticeSaveArticleKey,
|
||||
PracticeSaveWordKey,
|
||||
SAVE_DICT_KEY,
|
||||
SAVE_SETTING_KEY,
|
||||
SoundFileOptions
|
||||
} from "@/utils/const.ts";
|
||||
import VolumeIcon from "@/components/icon/VolumeIcon.vue";
|
||||
import { useBaseStore } from "@/stores/base.ts";
|
||||
import { saveAs } from "file-saver";
|
||||
import { Origin } from "@/config/ENV.ts";
|
||||
import {
|
||||
APP_NAME, APP_VERSION,
|
||||
EXPORT_DATA_KEY,
|
||||
LOCAL_FILE_KEY,
|
||||
Origin,
|
||||
PracticeSaveArticleKey,
|
||||
PracticeSaveWordKey, SAVE_DICT_KEY, SAVE_SETTING_KEY, SoundFileOptions
|
||||
} from "@/config/ENV.ts";
|
||||
import dayjs from "dayjs";
|
||||
import BasePage from "@/components/BasePage.vue";
|
||||
import Toast from '@/components/base/toast/Toast.ts'
|
||||
|
||||
@@ -2,9 +2,9 @@
|
||||
// import origin from './data.json'
|
||||
import BaseButton from "@/components/BaseButton.vue";
|
||||
import {checkAndUpgradeSaveDict} from "@/utils";
|
||||
import {SAVE_DICT_KEY} from "@/utils/const.ts";
|
||||
import str from './data.json'
|
||||
import {get} from 'idb-keyval'
|
||||
import { SAVE_DICT_KEY } from "@/config/ENV.ts";
|
||||
|
||||
let data = {}
|
||||
let origin = {}
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<script setup lang="ts">
|
||||
import {groupBy, useNav} from "@/utils";
|
||||
import { groupBy, useNav } from "@/utils";
|
||||
import BasePage from "@/components/BasePage.vue";
|
||||
import {DictResource} from "@/types/types.ts";
|
||||
import {useRuntimeStore} from "@/stores/runtime.ts";
|
||||
import { DictResource } from "@/types/types.ts";
|
||||
import { useRuntimeStore } from "@/stores/runtime.ts";
|
||||
import BaseIcon from "@/components/BaseIcon.vue";
|
||||
import Empty from "@/components/Empty.vue";
|
||||
import Input from "@/components/Input.vue";
|
||||
@@ -10,11 +10,12 @@ import BaseButton from "@/components/BaseButton.vue";
|
||||
import DictList from "@/components/list/DictList.vue";
|
||||
import BackIcon from "@/components/BackIcon.vue";
|
||||
import DictGroup from "@/components/list/DictGroup.vue";
|
||||
import {useBaseStore} from "@/stores/base.ts";
|
||||
import {useRouter} from "vue-router";
|
||||
import {computed} from "vue";
|
||||
import {getDefaultDict} from "@/types/func.ts";
|
||||
import dict_list from "@/assets/dict-list.json";
|
||||
import { useBaseStore } from "@/stores/base.ts";
|
||||
import { useRouter } from "vue-router";
|
||||
import { computed } from "vue";
|
||||
import { getDefaultDict } from "@/types/func.ts";
|
||||
import { useFetch } from "@vueuse/core";
|
||||
import { DICT_LIST } from "@/config/ENV.ts";
|
||||
|
||||
const {nav} = useNav()
|
||||
const runtimeStore = useRuntimeStore()
|
||||
@@ -45,9 +46,12 @@ function groupByDictTags(dictList: DictResource[]) {
|
||||
}, {})
|
||||
}
|
||||
|
||||
const {data: dict_list, isFetching} = useFetch(DICT_LIST.WORD.ALL).json()
|
||||
|
||||
const groupedByCategoryAndTag = $computed(() => {
|
||||
const groupByCategory = groupBy(dict_list.flat(), 'category')
|
||||
let data = []
|
||||
if (!dict_list.value) return data
|
||||
const groupByCategory = groupBy(dict_list.value.flat(), 'category')
|
||||
for (const [key, value] of Object.entries(groupByCategory)) {
|
||||
data.push([key, groupByDictTags(value)])
|
||||
}
|
||||
@@ -61,7 +65,7 @@ let searchKey = $ref('')
|
||||
const searchList = computed<any[]>(() => {
|
||||
if (searchKey) {
|
||||
let s = searchKey.toLowerCase()
|
||||
return dict_list.flat().filter((item) => {
|
||||
return dict_list.value.flat().filter((item) => {
|
||||
return item.id.toLowerCase().includes(s)
|
||||
|| item.name.toLowerCase().includes(s)
|
||||
|| item.category.toLowerCase().includes(s)
|
||||
@@ -76,7 +80,7 @@ const searchList = computed<any[]>(() => {
|
||||
|
||||
<template>
|
||||
<BasePage>
|
||||
<div class="card">
|
||||
<div class="card min-h-200" v-loading="isFetching">
|
||||
<div class="flex items-center relative gap-2">
|
||||
<BackIcon class="z-2" @click='router.back'/>
|
||||
<div class="flex flex-1 gap-4" v-if="showSearchInput">
|
||||
@@ -85,9 +89,11 @@ const searchList = computed<any[]>(() => {
|
||||
</div>
|
||||
<div class="py-1 flex flex-1 justify-end" v-else>
|
||||
<span class="page-title absolute w-full center">词典列表</span>
|
||||
<BaseIcon @click="showSearchInput = true"
|
||||
class="z-1"
|
||||
icon="fluent:search-24-regular">
|
||||
<BaseIcon
|
||||
title="搜索"
|
||||
@click="showSearchInput = true"
|
||||
class="z-1"
|
||||
icon="fluent:search-24-regular">
|
||||
<IconFluentSearch24Regular/>
|
||||
</BaseIcon>
|
||||
</div>
|
||||
|
||||
@@ -24,9 +24,9 @@ import { usePracticeStore } from "@/stores/practice.ts";
|
||||
import Toast from '@/components/base/toast/Toast.ts'
|
||||
import { getDefaultDict, getDefaultWord } from "@/types/func.ts";
|
||||
import ConflictNotice from "@/components/ConflictNotice.vue";
|
||||
import dict_list from "@/assets/dict-list.json";
|
||||
import PracticeLayout from "@/components/PracticeLayout.vue";
|
||||
import { PracticeSaveWordKey } from "@/utils/const.ts";
|
||||
|
||||
import { DICT_LIST, PracticeSaveWordKey } from "@/config/ENV.ts";
|
||||
|
||||
const {
|
||||
isWordCollect,
|
||||
@@ -64,6 +64,8 @@ async function loadDict() {
|
||||
if (dictId) {
|
||||
//先在自己的词典列表里面找,如果没有再在资源列表里面找
|
||||
dict = store.word.bookList.find(v => v.id === dictId)
|
||||
let r = await fetch(DICT_LIST.WORD.ALL)
|
||||
let dict_list = await r.json()
|
||||
if (!dict) dict = dict_list.flat().find(v => v.id === dictId) as Dict
|
||||
if (dict && dict.id) {
|
||||
//如果是不是自定义词典,就请求数据
|
||||
|
||||
@@ -18,9 +18,9 @@ import DeleteIcon from "@/components/icon/DeleteIcon.vue";
|
||||
import PracticeSettingDialog from "@/pages/word/components/PracticeSettingDialog.vue";
|
||||
import ChangeLastPracticeIndexDialog from "@/pages/word/components/ChangeLastPracticeIndexDialog.vue";
|
||||
import { useSettingStore } from "@/stores/setting.ts";
|
||||
import recommendDictList from "@/assets/recommend-dict-list.json";
|
||||
import CollectNotice from "@/components/CollectNotice.vue";
|
||||
import { PracticeSaveWordKey } from "@/utils/const.ts";
|
||||
import { useFetch } from "@vueuse/core";
|
||||
import { DICT_LIST, PracticeSaveWordKey } from "@/config/ENV.ts";
|
||||
|
||||
|
||||
const store = useBaseStore()
|
||||
@@ -130,7 +130,6 @@ const progressTextRight = $computed(() => {
|
||||
return store.sdict?.lastLearnIndex
|
||||
})
|
||||
|
||||
|
||||
function check(cb: Function) {
|
||||
if (!store.sdict.id) {
|
||||
Toast.warning('请先选择一本词典')
|
||||
@@ -154,6 +153,8 @@ function saveLastPracticeIndex(e) {
|
||||
localStorage.removeItem(PracticeSaveWordKey.key)
|
||||
currentStudy = getCurrentStudyWord()
|
||||
}
|
||||
|
||||
const {data: recommendDictList, isFetching} = useFetch(DICT_LIST.WORD.RECOMMENDED).json()
|
||||
</script>
|
||||
|
||||
<template>
|
||||
@@ -266,7 +267,7 @@ function saveLastPracticeIndex(e) {
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="card flex flex-col">
|
||||
<div class="card flex flex-col overflow-hidden" v-loading="isFetching">
|
||||
<div class="flex justify-between">
|
||||
<div class="title">推荐</div>
|
||||
<div class="flex gap-4 items-center">
|
||||
@@ -274,7 +275,7 @@ function saveLastPracticeIndex(e) {
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="flex gap-4 flex-wrap mt-4">
|
||||
<div class="flex gap-4 flex-wrap mt-4 min-h-50">
|
||||
<Book :is-add="false"
|
||||
quantifier="个词"
|
||||
:item="item as any"
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
import {defineStore} from 'pinia'
|
||||
import {Dict, DictId, Word} from "../types/types.ts"
|
||||
import {_getAccomplishDate, _getStudyProgress, checkAndUpgradeSaveDict} from "@/utils";
|
||||
import {SAVE_DICT_KEY} from "@/utils/const.ts";
|
||||
import {shallowReactive} from "vue";
|
||||
import {getDefaultDict} from "@/types/func.ts";
|
||||
import {get, set} from 'idb-keyval'
|
||||
import { SAVE_DICT_KEY } from "@/config/ENV.ts";
|
||||
|
||||
export interface BaseState {
|
||||
simpleWords: string[],
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
import {defineStore} from "pinia"
|
||||
import {checkAndUpgradeSaveSetting, cloneDeep} from "@/utils";
|
||||
import {DefaultShortcutKeyMap} from "@/types/types.ts";
|
||||
import {APP_VERSION, SAVE_SETTING_KEY} from "@/utils/const.ts";
|
||||
import {get} from "idb-keyval";
|
||||
import { APP_VERSION, SAVE_SETTING_KEY } from "@/config/ENV.ts";
|
||||
|
||||
export interface SettingState {
|
||||
soundType: string,
|
||||
|
||||
@@ -1,38 +0,0 @@
|
||||
export const SoundFileOptions = [
|
||||
{value: '机械键盘', label: '机械键盘'},
|
||||
{value: '机械键盘1', label: '机械键盘1'},
|
||||
{value: '机械键盘2', label: '机械键盘2'},
|
||||
{value: '老式机械键盘', label: '老式机械键盘'},
|
||||
{value: '笔记本键盘', label: '笔记本键盘'},
|
||||
]
|
||||
|
||||
export const APP_NAME = 'Type Words'
|
||||
export const APP_VERSION = {
|
||||
key: 'type-words-app-version',
|
||||
version: 1
|
||||
}
|
||||
|
||||
export const SAVE_DICT_KEY = {
|
||||
key: 'typing-word-dict',
|
||||
version: 4
|
||||
}
|
||||
export const SAVE_SETTING_KEY = {
|
||||
key: 'typing-word-setting',
|
||||
version: 15
|
||||
}
|
||||
export const EXPORT_DATA_KEY = {
|
||||
key: 'typing-word-export',
|
||||
version: 4
|
||||
}
|
||||
|
||||
export const LOCAL_FILE_KEY = 'typing-word-files'
|
||||
|
||||
export const PracticeSaveWordKey = {
|
||||
key: 'PracticeSaveWord',
|
||||
version: 1
|
||||
}
|
||||
|
||||
export const PracticeSaveArticleKey = {
|
||||
key: 'PracticeSaveArticle',
|
||||
version: 1
|
||||
}
|
||||
@@ -1,4 +1,3 @@
|
||||
import {SAVE_SETTING_KEY} from "@/utils/const";
|
||||
|
||||
export default {
|
||||
$notice(val) {
|
||||
|
||||
@@ -1,114 +1,89 @@
|
||||
// import axios, {AxiosInstance} from 'axios'
|
||||
// // import globalMethods from './global-methods'
|
||||
// // import Config from '../config/index'
|
||||
// // import CONSTANT from './const_var'
|
||||
// // import store from '../store'
|
||||
// // import Storage from './storage'
|
||||
//
|
||||
// export const axiosInstance: AxiosInstance = axios.create({
|
||||
// // baseURL: process.env.NODE_ENV === 'production' ? Config.PRODUCT_API_URL : Config.API_URL,
|
||||
// // baseURL: 'http://testtestgp.com',
|
||||
// timeout: 15000,
|
||||
// })
|
||||
//
|
||||
// // request 拦截器
|
||||
// axiosInstance.interceptors.request.use(
|
||||
// (config) => {
|
||||
// // console.log('config', config)
|
||||
// if (config.url === 'https://api.fanyi.baidu.com/api/trans/vip/translate') {
|
||||
// config.url = '/baidu'
|
||||
// }
|
||||
// return config
|
||||
// },
|
||||
// error => Promise.reject(error),
|
||||
// )
|
||||
import axios, { AxiosInstance } from 'axios'
|
||||
import { env } from "@/config/ENV.ts";
|
||||
import Toast from "@/components/base/toast/Toast.ts";
|
||||
|
||||
// respone 拦截器
|
||||
// instance.interceptors.response.use(
|
||||
// // 响应正常的处理
|
||||
// (response) => {
|
||||
// // console.log(response)
|
||||
// // console.log(response.data)
|
||||
// const { data } = response
|
||||
// if (response.status !== 200) {
|
||||
// globalMethods.$warning(response.statusText)
|
||||
// return Promise.reject(data)
|
||||
// }
|
||||
// if (data === null) {
|
||||
// return Promise.resolve({
|
||||
// code: '009900',
|
||||
// msg: '系统出现错误',
|
||||
// data: {},
|
||||
// })
|
||||
// }
|
||||
// return Promise.resolve(data)
|
||||
// },
|
||||
// // 请求出错的处理
|
||||
// (error) => {
|
||||
// console.log(error)
|
||||
// if (error.response === undefined && error.status === undefined) {
|
||||
// return Promise.resolve({
|
||||
// code: '009900',
|
||||
// msg: '服务器响应超时',
|
||||
// data: null,
|
||||
// })
|
||||
// }
|
||||
// if (error.response.status >= 500) {
|
||||
// return Promise.resolve({
|
||||
// code: '009900',
|
||||
// msg: '服务器出现错误',
|
||||
// data: null,
|
||||
// })
|
||||
// }
|
||||
// if (error.response.status === 401) {
|
||||
// return Promise.resolve({
|
||||
// code: '009900',
|
||||
// msg: '用户名或密码不正确',
|
||||
// data: null,
|
||||
// })
|
||||
// }
|
||||
// const { data } = error.response
|
||||
// if (data.code !== undefined) {
|
||||
// return Promise.resolve({
|
||||
// code: data.code,
|
||||
// msg: data.msg,
|
||||
// })
|
||||
// }
|
||||
// return Promise.resolve({
|
||||
// code: '009900',
|
||||
// msg: data.msg,
|
||||
// data: null,
|
||||
// })
|
||||
// },
|
||||
// )
|
||||
export const axiosInstance: AxiosInstance = axios.create({
|
||||
baseURL: env.api,
|
||||
timeout: 15000,
|
||||
})
|
||||
|
||||
axiosInstance.interceptors.request.use(
|
||||
(config) => {
|
||||
// console.log('config', config)
|
||||
// if (config.url === 'https://api.fanyi.baidu.com/api/trans/vip/translate') {
|
||||
// config.url = '/baidu'
|
||||
// }
|
||||
return config
|
||||
},
|
||||
error => Promise.reject(error),
|
||||
)
|
||||
|
||||
axiosInstance.interceptors.response.use(
|
||||
// 响应正常的处理
|
||||
(response) => {
|
||||
// console.log(response)
|
||||
// console.log(response.data)
|
||||
const {data} = response
|
||||
if (response.status !== 200) {
|
||||
Toast.warning(response.statusText)
|
||||
return Promise.reject(data)
|
||||
}
|
||||
if (data === null) {
|
||||
return Promise.resolve({
|
||||
code: '009900',
|
||||
msg: '系统出现错误',
|
||||
data: {},
|
||||
})
|
||||
}
|
||||
return Promise.resolve(data)
|
||||
},
|
||||
// 请求出错的处理
|
||||
(error) => {
|
||||
console.log(error)
|
||||
if (error.response === undefined && error.status === undefined) {
|
||||
return Promise.resolve({
|
||||
code: '009900',
|
||||
msg: '服务器响应超时',
|
||||
data: null,
|
||||
})
|
||||
}
|
||||
if (error.response.status >= 500) {
|
||||
return Promise.resolve({
|
||||
code: '009900',
|
||||
msg: '服务器出现错误',
|
||||
data: null,
|
||||
})
|
||||
}
|
||||
if (error.response.status === 401) {
|
||||
return Promise.resolve({
|
||||
code: '009900',
|
||||
msg: '用户名或密码不正确',
|
||||
data: null,
|
||||
})
|
||||
}
|
||||
const {data} = error.response
|
||||
if (data.code !== undefined) {
|
||||
return Promise.resolve({
|
||||
code: data.code,
|
||||
msg: data.msg,
|
||||
})
|
||||
}
|
||||
return Promise.resolve({
|
||||
code: '009900',
|
||||
msg: data.msg,
|
||||
data: null,
|
||||
})
|
||||
},
|
||||
)
|
||||
|
||||
|
||||
/**
|
||||
* @apiDescription 封装的网络请求方法
|
||||
* @apiGroup
|
||||
* @apiName request
|
||||
* @apiParam url 地址
|
||||
* @apiParam data 请求数据
|
||||
* @apiParam params 请求参数
|
||||
* @apiParam method 方法类型:get或者post
|
||||
* @apiParam version 接口版本号
|
||||
* @apiParamExample
|
||||
* request('Appointment/appointmentList', data, params, CONSTANT.GET)
|
||||
* @apiReturn Promise
|
||||
*/
|
||||
// async function request(url, data = {}, params = {}, method = CONSTANT.POST, version = Config.API_VERSION) {
|
||||
// // console.log(url)
|
||||
// if (method === CONSTANT.POST) {
|
||||
// data.userId = store.state.user.userInfo === null ? '' : store.state.user.userInfo.id
|
||||
// } else {
|
||||
// params.userId = store.state.user.userInfo === null ? '' : store.state.user.userInfo.id
|
||||
// }
|
||||
// return instance({
|
||||
// url: version + url,
|
||||
// method,
|
||||
// data,
|
||||
// params,
|
||||
// })
|
||||
// }
|
||||
async function request(url, data = {}, params = {}, method) {
|
||||
return axiosInstance({
|
||||
url: '/v1/' + url,
|
||||
method,
|
||||
data,
|
||||
params,
|
||||
})
|
||||
}
|
||||
|
||||
// export default request
|
||||
export default request
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { SAVE_DICT_KEY, SAVE_SETTING_KEY } from "@/utils/const.ts";
|
||||
|
||||
import { BaseState, DefaultBaseState } from "@/stores/base.ts";
|
||||
import { getDefaultSettingState, SettingState } from "@/stores/setting.ts";
|
||||
import { Dict, DictId, DictResource, DictType } from "@/types/types.ts";
|
||||
@@ -6,13 +6,10 @@ import { useRouter } from "vue-router";
|
||||
import { useRuntimeStore } from "@/stores/runtime.ts";
|
||||
import dayjs from 'dayjs'
|
||||
import axios from "axios";
|
||||
import { env } from "@/config/ENV.ts";
|
||||
import { env, SAVE_DICT_KEY, SAVE_SETTING_KEY } from "@/config/ENV.ts";
|
||||
import { nextTick } from "vue";
|
||||
import Toast from '@/components/base/toast/Toast.ts'
|
||||
import { getDefaultArticle, getDefaultDict, getDefaultWord } from "@/types/func.ts";
|
||||
import { set } from "idb-keyval";
|
||||
import book_list from "@/assets/book-list.json";
|
||||
import dict_list from "@/assets/dict-list.json";
|
||||
import { getDefaultDict, getDefaultWord } from "@/types/func.ts";
|
||||
import duration from "dayjs/plugin/duration";
|
||||
|
||||
dayjs.extend(duration);
|
||||
@@ -58,141 +55,6 @@ export function checkAndUpgradeSaveDict(val: any) {
|
||||
})
|
||||
return defaultState
|
||||
} else {
|
||||
if (version === 3) {
|
||||
localStorage.setItem('type-word-dict-v3', JSON.stringify(state))
|
||||
set('type-word-dict-v3', JSON.stringify(state))
|
||||
|
||||
let studyDictId = ''
|
||||
if (state.current.index >= 0) {
|
||||
let dict = state.myDictList[state.current.index]
|
||||
if (dict) {
|
||||
studyDictId = dict.id
|
||||
}
|
||||
}
|
||||
|
||||
const safeString = (str) => (typeof str === 'string' ? str.trim() : '');
|
||||
|
||||
function formatWord(dict) {
|
||||
dict.words = dict.words?.map?.(v => {
|
||||
return getDefaultWord({
|
||||
word: v.name,
|
||||
phonetic0: v.usphone,
|
||||
phonetic1: v.ukphone,
|
||||
trans: v.trans.map(line => {
|
||||
const match = line.match(/^([^\s.]+\.?)\s*(.*)$/);
|
||||
if (match) {
|
||||
let pos = safeString(match[1]);
|
||||
let cn = safeString(match[2]);
|
||||
|
||||
// 如果 pos 不是常规词性(不以字母开头),例如 "【名】"
|
||||
if (!/^[a-zA-Z]+\.?$/.test(pos)) {
|
||||
cn = safeString(line); // 整行放到 cn
|
||||
pos = ''; // pos 置空
|
||||
}
|
||||
|
||||
return {pos, cn};
|
||||
}
|
||||
return {pos: '', cn: safeString(line)};
|
||||
})
|
||||
})
|
||||
}) || []
|
||||
dict.statistics = dict.statistics?.map?.(v => {
|
||||
return {
|
||||
startDate: v.startDate,
|
||||
spend: v.endDate - v.startDate,
|
||||
total: v.total,
|
||||
new: v.total,
|
||||
wrong: v.wrongWordNumber
|
||||
}
|
||||
}) || []
|
||||
dict.articles = dict.articles?.map?.(v => {
|
||||
let r = getDefaultArticle({
|
||||
textTranslate: v.textCustomTranslate
|
||||
})
|
||||
checkRiskKey(r, v)
|
||||
return r
|
||||
}) || []
|
||||
}
|
||||
|
||||
state.myDictList.map((v: any) => {
|
||||
try {
|
||||
let currentDictId = v.id
|
||||
let currentType = v.type
|
||||
delete v.type
|
||||
if (['collect', 'simple', 'wrong'].includes(currentType)) {
|
||||
formatWord(v)
|
||||
delete v.id
|
||||
delete v.name
|
||||
if (currentType === 'collect') {
|
||||
if (v.words.length) {
|
||||
if (currentDictId === studyDictId) defaultState.word.studyIndex = 0
|
||||
checkRiskKey(defaultState.word.bookList[0], cloneDeep(v))
|
||||
defaultState.word.bookList[0].length = v.words.length
|
||||
}
|
||||
if (v.articles.length) {
|
||||
if (currentDictId === studyDictId) defaultState.article.studyIndex = 0
|
||||
checkRiskKey(defaultState.article.bookList[0], cloneDeep(v))
|
||||
defaultState.article.bookList[0].length = v.articles.length
|
||||
}
|
||||
}
|
||||
if (currentType === 'simple' || currentType === 'skip') {
|
||||
if (currentDictId === studyDictId) defaultState.word.studyIndex = 2
|
||||
checkRiskKey(defaultState.word.bookList[2], v)
|
||||
defaultState.word.bookList[2].length = v.words.length
|
||||
}
|
||||
if (currentType === 'wrong') {
|
||||
if (currentDictId === studyDictId) defaultState.word.studyIndex = 1
|
||||
checkRiskKey(defaultState.word.bookList[1], v)
|
||||
defaultState.word.bookList[1].length = v.words.length
|
||||
}
|
||||
}
|
||||
if (currentType === 'word') {
|
||||
if (v.isCustom) {
|
||||
formatWord(v)
|
||||
let dict = getDefaultDict({custom: true})
|
||||
checkRiskKey(dict, v)
|
||||
dict.length = dict.words.length
|
||||
defaultState.word.bookList.push(dict)
|
||||
if (currentDictId === studyDictId) defaultState.word.studyIndex = defaultState.word.bookList.length - 1
|
||||
} else {
|
||||
//当时把选中的词典的id设为随机了,导致通过id找不到
|
||||
let r: any = dict_list.flat().find(a => a.name === v.name)
|
||||
if (r) {
|
||||
formatWord(v)
|
||||
let dict = getDefaultDict(r)
|
||||
checkRiskKey(dict, v)
|
||||
dict.id = r.id
|
||||
defaultState.word.bookList.push(dict)
|
||||
if (currentDictId === studyDictId) defaultState.word.studyIndex = defaultState.word.bookList.length - 1
|
||||
}
|
||||
}
|
||||
}
|
||||
if (currentType === 'article') {
|
||||
if (v.isCustom) {
|
||||
formatWord(v)
|
||||
let dict = getDefaultDict({custom: true})
|
||||
checkRiskKey(dict, v)
|
||||
dict.length = dict.articles.length
|
||||
defaultState.article.bookList.push(dict)
|
||||
if (currentDictId === studyDictId) defaultState.article.studyIndex = defaultState.article.bookList.length - 1
|
||||
} else {
|
||||
//当时把选中的词典的id设为随机了
|
||||
let r: any = book_list.flat().find(a => a.name === v.name)
|
||||
if (r) {
|
||||
formatWord(v)
|
||||
let dict = getDefaultDict(r)
|
||||
checkRiskKey(dict, v)
|
||||
dict.id = r.id
|
||||
defaultState.article.bookList.push(dict)
|
||||
if (currentDictId === studyDictId) defaultState.article.studyIndex = defaultState.article.bookList.length - 1
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (e) {
|
||||
console.error('升级数据失败!', e)
|
||||
}
|
||||
})
|
||||
}
|
||||
checkRiskKey(defaultState, state)
|
||||
return defaultState
|
||||
}
|
||||
@@ -264,11 +126,8 @@ export function shakeCommonDict(n: BaseState): BaseState {
|
||||
|
||||
export function isMobile(): boolean {
|
||||
// return /Mobi|Android|iPhone/i.test(navigator.userAgent)
|
||||
return (
|
||||
'ontouchstart' in window ||
|
||||
navigator.maxTouchPoints > 0 ||
|
||||
navigator.msMaxTouchPoints > 0
|
||||
);
|
||||
//@ts-ignore
|
||||
return ('ontouchstart' in window || navigator.maxTouchPoints > 0 || navigator.msMaxTouchPoints > 0);
|
||||
}
|
||||
|
||||
export async function getDictFile(url: string) {
|
||||
|
||||
Reference in New Issue
Block a user