fix.
This commit is contained in:
1
src/components.d.ts
vendored
1
src/components.d.ts
vendored
@@ -43,7 +43,6 @@ declare module '@vue/runtime-core' {
|
||||
IEpLoading: typeof import('~icons/ep/loading')['default']
|
||||
IEpSelect: typeof import('~icons/ep/select')['default']
|
||||
IEpSemiSelect: typeof import('~icons/ep/semi-select')['default']
|
||||
IEpVideoPlay: typeof import('~icons/ep/video-play')['default']
|
||||
RouterLink: typeof import('vue-router')['RouterLink']
|
||||
RouterView: typeof import('vue-router')['RouterView']
|
||||
}
|
||||
|
||||
14
src/main.ts
14
src/main.ts
@@ -3,12 +3,13 @@ import { createPinia } from "pinia"
|
||||
import "normalize.css"
|
||||
import loader from "@monaco-editor/loader"
|
||||
|
||||
import storage from "utils/storage"
|
||||
import { STORAGE_KEY } from "utils/constants"
|
||||
|
||||
import { routes } from "./routes"
|
||||
import App from "./App.vue"
|
||||
|
||||
import storage from "./utils/storage"
|
||||
import routes from "./routes"
|
||||
import { STORAGE_KEY } from "./utils/constants"
|
||||
import { useLoginStore } from "./shared/store/login"
|
||||
import { useLoginStore } from "~/shared/store/login"
|
||||
|
||||
const router = createRouter({
|
||||
history: createWebHistory(),
|
||||
@@ -31,6 +32,11 @@ router.beforeEach((to, from, next) => {
|
||||
|
||||
const pinia = createPinia()
|
||||
|
||||
Promise.all([loader.init(), fetch("/dracula.json")]).then(([monaco, dark]) => {
|
||||
window.monaco = monaco
|
||||
dark.json().then((data) => monaco.editor.defineTheme("dark", data))
|
||||
})
|
||||
|
||||
loader.config({
|
||||
paths: { vs: "https://cdn.staticfile.org/monaco-editor/0.34.1/min/vs" },
|
||||
"vs/nls": { availableLanguages: { "*": "zh-cn" } },
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
import { useAxios } from "@vueuse/integrations/useAxios"
|
||||
import http from "./../utils/http"
|
||||
import { getACRate } from "./../utils/functions"
|
||||
import { DIFFICULTY } from "./../utils/constants"
|
||||
import { Problem, SubmitCodePayload, Submission } from "./../utils/types"
|
||||
import http from "utils/http"
|
||||
import { getACRate } from "utils/functions"
|
||||
import { DIFFICULTY } from "utils/constants"
|
||||
import { Problem, SubmitCodePayload, Submission } from "utils/types"
|
||||
|
||||
function filterResult(result: Problem) {
|
||||
const newResult: any = {
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
<script lang="ts" setup>
|
||||
import { LANGUAGE_LABEL, SOURCES } from "../../../utils/constants"
|
||||
import { Problem } from "../../../utils/types"
|
||||
import { useCodeStore } from "../../store/code"
|
||||
import { submissionExists } from "../../api"
|
||||
import { SOURCES } from "utils/constants"
|
||||
import { Problem } from "utils/types"
|
||||
import Monaco from "~/shared/Monaco/index.vue"
|
||||
import { useCodeStore } from "oj/store/code"
|
||||
import { submissionExists } from "oj/api"
|
||||
import { TabsPaneContext } from "element-plus"
|
||||
|
||||
import Monaco from "../../../shared/Monaco/index.vue"
|
||||
import SubmitPanel from "./SubmitPanel.vue"
|
||||
import TestcasePanel from "./TestcasePanel.vue"
|
||||
|
||||
@@ -54,12 +54,9 @@ function onTab(pane: TabsPaneContext) {
|
||||
<el-form inline>
|
||||
<el-form-item label="语言" label-width="60">
|
||||
<el-select v-model="code.language" class="language">
|
||||
<el-option
|
||||
v-for="item in problem.languages"
|
||||
:key="item"
|
||||
:value="item"
|
||||
:label="LANGUAGE_LABEL[item]"
|
||||
>
|
||||
<el-option v-for="item in problem.languages" :key="item" :value="item">
|
||||
<img class="logo" :src="`/${item}.svg`" alt="logo" />
|
||||
<span>{{ item }}</span>
|
||||
</el-option>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
@@ -82,10 +79,14 @@ function onTab(pane: TabsPaneContext) {
|
||||
|
||||
<style scoped>
|
||||
.language {
|
||||
width: 100px;
|
||||
width: 110px;
|
||||
}
|
||||
|
||||
.editor {
|
||||
min-height: 200px;
|
||||
}
|
||||
|
||||
.logo {
|
||||
width: 12px;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
<script setup lang="ts">
|
||||
import { Problem } from "../../../utils/types"
|
||||
import { Flag, CloseBold, Select } from "@element-plus/icons-vue"
|
||||
import { useCodeStore } from "../../store/code"
|
||||
import { SOURCES } from "../../../utils/constants"
|
||||
import { createTestSubmission } from "../../../utils/judge"
|
||||
import { useCodeStore } from "oj/store/code"
|
||||
import { SOURCES } from "utils/constants"
|
||||
import { Problem } from "utils/types"
|
||||
import { createTestSubmission } from "utils/judge"
|
||||
|
||||
interface Props {
|
||||
problem: Problem
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<script setup lang="ts">
|
||||
import { DIFFICULTY } from "../../../utils/constants"
|
||||
import { getACRate, getTagColor, parseTime } from "../../../utils/functions"
|
||||
import { isDesktop } from "../../../utils/breakpoints"
|
||||
import { Problem } from "../../../utils/types"
|
||||
import { DIFFICULTY } from "utils/constants"
|
||||
import { getACRate, getTagColor, parseTime } from "utils/functions"
|
||||
import { isDesktop } from "utils/breakpoints"
|
||||
import { Problem } from "utils/types"
|
||||
|
||||
interface Props {
|
||||
problem: Problem
|
||||
|
||||
18
src/oj/problem/components/SubmissionList.vue
Normal file
18
src/oj/problem/components/SubmissionList.vue
Normal file
@@ -0,0 +1,18 @@
|
||||
<script setup lang="ts">
|
||||
import Pagination from "~/shared/Pagination/index.vue"
|
||||
|
||||
const query = reactive({
|
||||
page: 1,
|
||||
limit: 10,
|
||||
})
|
||||
const total = ref(100)
|
||||
</script>
|
||||
<template>
|
||||
<el-table max-height="calc(100vh - 171px)"></el-table>
|
||||
<Pagination
|
||||
:total="total"
|
||||
v-model:limit="query.limit"
|
||||
v-model:page="query.page"
|
||||
/>
|
||||
</template>
|
||||
<style scoped></style>
|
||||
@@ -1,20 +1,13 @@
|
||||
<script setup lang="ts">
|
||||
import party from "party-js"
|
||||
import { Ref } from "vue"
|
||||
import {
|
||||
SOURCES,
|
||||
JUDGE_STATUS,
|
||||
SubmissionStatus,
|
||||
} from "../../../utils/constants"
|
||||
import {
|
||||
submissionMemoryFormat,
|
||||
submissionTimeFormat,
|
||||
} from "../../../utils/functions"
|
||||
import { Problem, Submission, SubmitCodePayload } from "../../../utils/types"
|
||||
import { getSubmission, submitCode } from "../../api"
|
||||
import { SOURCES, JUDGE_STATUS, SubmissionStatus } from "utils/constants"
|
||||
import { submissionMemoryFormat, submissionTimeFormat } from "utils/functions"
|
||||
import { Problem, Submission, SubmitCodePayload } from "utils/types"
|
||||
import { getSubmission, submitCode } from "oj/api"
|
||||
import { useCodeStore } from "oj/store/code"
|
||||
|
||||
import SubmissionResultTag from "../../components/SubmissionResultTag.vue"
|
||||
import { useCodeStore } from "../../store/code"
|
||||
|
||||
const problem = inject<Ref<Problem>>("problem")
|
||||
const { code } = useCodeStore()
|
||||
@@ -198,7 +191,12 @@ defineExpose({ submit })
|
||||
<el-scrollbar v-if="msg" height="354" class="result" noresize>
|
||||
<div>{{ msg }}</div>
|
||||
</el-scrollbar>
|
||||
<el-table v-if="infoTable.length" height="354" :data="infoTable" stripe>
|
||||
<el-table
|
||||
v-if="infoTable.length"
|
||||
max-height="354"
|
||||
:data="infoTable"
|
||||
stripe
|
||||
>
|
||||
<el-table-column prop="test_case" label="测试用例" align="center" />
|
||||
<el-table-column label="测试状态" width="120" align="center">
|
||||
<template #default="scope">
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<script setup lang="ts">
|
||||
import { createTestSubmission } from "../../../utils/judge"
|
||||
import { useCodeStore } from "../../store/code"
|
||||
import { createTestSubmission } from "utils/judge"
|
||||
import { useCodeStore } from "oj/store/code"
|
||||
|
||||
const input = ref("")
|
||||
const result = ref("")
|
||||
|
||||
@@ -2,8 +2,9 @@
|
||||
import Editor from "./components/Editor.vue"
|
||||
import ProblemContent from "./components/ProblemContent.vue"
|
||||
import ProblemInfo from "./components/ProblemInfo.vue"
|
||||
import { getProblem } from "../api"
|
||||
import { isDesktop, isMobile } from "../../utils/breakpoints"
|
||||
import SubmissionList from "./components/SubmissionList.vue"
|
||||
import { getProblem } from "oj/api"
|
||||
import { isDesktop, isMobile } from "utils/breakpoints"
|
||||
|
||||
interface Props {
|
||||
problemID: string
|
||||
@@ -32,11 +33,13 @@ provide("problem", readonly(problem))
|
||||
<el-tab-pane v-if="isMobile" label="代码编辑" lazy>
|
||||
<Editor :problem="problem" />
|
||||
</el-tab-pane>
|
||||
<el-tab-pane label="提交列表" lazy>
|
||||
<SubmissionList />
|
||||
</el-tab-pane>
|
||||
<el-tab-pane label="比赛信息" v-if="props.contestID" lazy></el-tab-pane>
|
||||
<el-tab-pane label="题目信息" lazy>
|
||||
<el-tab-pane label="统计信息" lazy>
|
||||
<ProblemInfo :problem="problem" />
|
||||
</el-tab-pane>
|
||||
<el-tab-pane label="提交列表">3</el-tab-pane>
|
||||
</el-tabs>
|
||||
</el-col>
|
||||
<el-col v-if="isDesktop" :span="12">
|
||||
|
||||
@@ -1,8 +1,10 @@
|
||||
<script setup lang="ts">
|
||||
import { useUserStore } from "../../shared/store/user"
|
||||
import { filterEmptyValue, getTagColor } from "../../utils/functions"
|
||||
import { isDesktop } from "../../utils/breakpoints"
|
||||
import { getProblemList, getProblemTagList, getRandomProblemID } from "../api"
|
||||
import { useUserStore } from "~/shared/store/user"
|
||||
import { filterEmptyValue, getTagColor } from "utils/functions"
|
||||
import { isDesktop } from "utils/breakpoints"
|
||||
import { getProblemList, getProblemTagList, getRandomProblemID } from "oj/api"
|
||||
|
||||
import Pagination from "~/shared/Pagination/index.vue"
|
||||
|
||||
const difficultyOptions = [
|
||||
{ label: "全部", value: "" },
|
||||
@@ -182,35 +184,15 @@ onMounted(listProblems)
|
||||
/>
|
||||
<el-table-column v-if="isDesktop" prop="rate" label="通过率" width="100" />
|
||||
</el-table>
|
||||
<el-pagination
|
||||
class="right margin"
|
||||
:layout="isDesktop ? 'prev,pager,next,sizes' : 'prev,next,sizes'"
|
||||
background
|
||||
<Pagination
|
||||
:total="total"
|
||||
:page-sizes="[10, 20, 30]"
|
||||
:pager-count="5"
|
||||
v-model:page-size="query.limit"
|
||||
v-model:current-page="query.page"
|
||||
v-model:limit="query.limit"
|
||||
v-model:page="query.page"
|
||||
/>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.margin {
|
||||
margin-top: 24px;
|
||||
}
|
||||
.right {
|
||||
float: right;
|
||||
}
|
||||
.pointer {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.panel {
|
||||
width: 400px;
|
||||
padding: 0 4px;
|
||||
}
|
||||
|
||||
.panel-tag {
|
||||
margin: 4px;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { Code } from "../../utils/types"
|
||||
import { Code } from "utils/types"
|
||||
|
||||
export const useCodeStore = defineStore("code", () => {
|
||||
const code = reactive<Code>({
|
||||
|
||||
@@ -1,55 +1,54 @@
|
||||
import Home from "./oj/index.vue"
|
||||
import Problems from "./oj/problem/list.vue"
|
||||
|
||||
const routes = [
|
||||
export const routes = [
|
||||
{
|
||||
path: "/",
|
||||
component: Home,
|
||||
component: () => import("~/shared/layout/default.vue"),
|
||||
children: [
|
||||
{ path: "", component: Problems },
|
||||
{ path: "/learn/:step*", component: () => import("./learn/index.vue") },
|
||||
{ path: "", component: () => import("oj/problem/list.vue") },
|
||||
{
|
||||
path: "problem/:problemID",
|
||||
component: () => import("./oj/problem/detail.vue"),
|
||||
component: () => import("oj/problem/detail.vue"),
|
||||
props: true,
|
||||
name: "ProblemDetail",
|
||||
},
|
||||
{
|
||||
path: "status",
|
||||
component: () => import("./oj/status/list.vue"),
|
||||
meta: { requiresAuth: true },
|
||||
component: () => import("oj/status/list.vue"),
|
||||
},
|
||||
{
|
||||
path: "status/:statusID",
|
||||
component: () => import("./oj/status/detail.vue"),
|
||||
component: () => import("oj/status/detail.vue"),
|
||||
props: true,
|
||||
},
|
||||
{
|
||||
path: "contest",
|
||||
component: () => import("./oj/contest/list.vue"),
|
||||
component: () => import("oj/contest/list.vue"),
|
||||
meta: { requiresAuth: true },
|
||||
},
|
||||
{
|
||||
path: "contest/:contestID",
|
||||
component: () => import("./oj/contest/detail.vue"),
|
||||
component: () => import("oj/contest/detail.vue"),
|
||||
props: true,
|
||||
},
|
||||
{
|
||||
path: "contest/:contestID/problem/:problemID",
|
||||
component: () => import("./oj/problem/detail.vue"),
|
||||
component: () => import("oj/problem/detail.vue"),
|
||||
props: true,
|
||||
name: "ContestProblemDetail",
|
||||
},
|
||||
{
|
||||
path: "rank",
|
||||
component: () => import("./oj/rank/list.vue"),
|
||||
},
|
||||
{
|
||||
path: "/admin",
|
||||
component: () => import("./admin/index.vue"),
|
||||
component: () => import("oj/rank/list.vue"),
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
path: "/learn",
|
||||
component: () => import("~/shared/layout/default.vue"),
|
||||
children: [{ path: ":step*", component: () => import("learn/index.vue") }],
|
||||
},
|
||||
{
|
||||
path: "/admin",
|
||||
component: () => import("~/shared/layout/admin.vue"),
|
||||
children: [{ path: "", component: () => import("admin/index.vue") }],
|
||||
},
|
||||
]
|
||||
|
||||
export default routes
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<script setup lang="ts">
|
||||
import { useLoginStore } from "../store/login"
|
||||
import { useSignupStore } from "../../oj/store/signup"
|
||||
import { useUserStore } from "../store/user"
|
||||
import { useSignupStore } from "~/shared/store/signup"
|
||||
import { logout } from "../api"
|
||||
import { useUserStore } from "../store/user"
|
||||
|
||||
const loginStore = useLoginStore()
|
||||
const signupStore = useSignupStore()
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<script setup lang="ts">
|
||||
import { FormInstance } from "element-plus"
|
||||
import { useSignupStore } from "../../oj/store/signup"
|
||||
import { useSignupStore } from "~/shared/store/signup"
|
||||
import { login } from "../api"
|
||||
import { useLoginStore } from "../store/login"
|
||||
import { useUserStore } from "../store/user"
|
||||
|
||||
@@ -1,9 +1,8 @@
|
||||
<script setup lang="ts">
|
||||
import type * as Monaco from "monaco-editor"
|
||||
import loader from "@monaco-editor/loader"
|
||||
import { LANGUAGE_VALUE } from "../../utils/constants"
|
||||
import { LANGUAGE } from "../../utils/types"
|
||||
import { isMobile } from "../../utils/breakpoints"
|
||||
import { LANGUAGE_VALUE } from "utils/constants"
|
||||
import { LANGUAGE } from "utils/types"
|
||||
import { isMobile } from "utils/breakpoints"
|
||||
|
||||
interface Props {
|
||||
value: string
|
||||
@@ -25,20 +24,18 @@ const emit = defineEmits<{
|
||||
}>()
|
||||
|
||||
const monacoEditorRef = ref()
|
||||
let editor: Monaco.editor.IStandaloneCodeEditor | null
|
||||
let editor: Monaco.editor.IStandaloneCodeEditor
|
||||
|
||||
onMounted(async function () {
|
||||
const monaco = await loader.init()
|
||||
|
||||
const model = monaco.editor.createModel(
|
||||
onMounted(function () {
|
||||
const model = window.monaco.editor.createModel(
|
||||
props.value,
|
||||
LANGUAGE_VALUE[props.language],
|
||||
monaco.Uri.parse(`file:///root/${Date.now()}.${ext()}`)
|
||||
window.monaco.Uri.parse(`file:///root/${Date.now()}.${ext()}`)
|
||||
)
|
||||
|
||||
editor = monaco.editor.create(monacoEditorRef.value, {
|
||||
editor = window.monaco.editor.create(monacoEditorRef.value, {
|
||||
model,
|
||||
theme: "vs-dark", // 官方自带三种主题vs, hc-black, or vs-dark
|
||||
theme: "dark", // 官方自带三种主题vs, hc-black, or vs-dark
|
||||
minimap: {
|
||||
enabled: false,
|
||||
},
|
||||
@@ -47,6 +44,15 @@ onMounted(async function () {
|
||||
tabSize: 4,
|
||||
fontSize: isMobile.value ? 20 : 24, // 字体大小
|
||||
scrollBeyondLastLine: false,
|
||||
lineDecorationsWidth: 0,
|
||||
scrollBeyondLastColumn: 0,
|
||||
glyphMargin: false,
|
||||
scrollbar: {
|
||||
useShadows: false,
|
||||
vertical: "hidden",
|
||||
horizontal: "hidden",
|
||||
},
|
||||
overviewRulerLanes: 0,
|
||||
})
|
||||
|
||||
model.onDidChangeContent(() => {
|
||||
@@ -64,7 +70,7 @@ onMounted(async function () {
|
||||
})
|
||||
|
||||
watchEffect(() => {
|
||||
monaco.editor.setModelLanguage(model, LANGUAGE_VALUE[props.language])
|
||||
window.monaco.editor.setModelLanguage(model, LANGUAGE_VALUE[props.language])
|
||||
})
|
||||
|
||||
watchEffect(() => {
|
||||
|
||||
42
src/shared/Pagination/index.vue
Normal file
42
src/shared/Pagination/index.vue
Normal file
@@ -0,0 +1,42 @@
|
||||
<script setup lang="ts">
|
||||
import { isDesktop } from "utils/breakpoints"
|
||||
interface Props {
|
||||
total: number
|
||||
limit: number
|
||||
page: number
|
||||
}
|
||||
|
||||
const props = withDefaults(defineProps<Props>(), {
|
||||
limit: 10,
|
||||
page: 1,
|
||||
})
|
||||
|
||||
const emit = defineEmits(["update:limit", "update:page"])
|
||||
|
||||
const limit = ref(props.limit)
|
||||
const page = ref(props.page)
|
||||
|
||||
watch(limit, () => emit("update:limit", limit))
|
||||
watch(page, () => emit("update:page", page))
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<el-pagination
|
||||
class="right margin"
|
||||
:layout="isDesktop ? 'prev,pager,next,sizes' : 'prev,next,sizes'"
|
||||
background
|
||||
:total="props.total"
|
||||
:page-sizes="[10, 20, 30]"
|
||||
:pager-count="5"
|
||||
v-model:page-size="limit"
|
||||
v-model:current-page="page"
|
||||
/>
|
||||
</template>
|
||||
<style scoped>
|
||||
.margin {
|
||||
margin-top: 24px;
|
||||
}
|
||||
.right {
|
||||
float: right;
|
||||
}
|
||||
</style>
|
||||
@@ -1,5 +1,5 @@
|
||||
<script setup lang="ts">
|
||||
import { useSignupStore } from "../../oj/store/signup"
|
||||
import { useSignupStore } from "../store/signup"
|
||||
const store = useSignupStore()
|
||||
</script>
|
||||
|
||||
|
||||
@@ -36,7 +36,6 @@
|
||||
import Resizer from "./Resizer.vue"
|
||||
import Pane from "./Pane.vue"
|
||||
import { computed, ref } from "vue"
|
||||
import { classNameToArray } from "element-plus/es/utils"
|
||||
|
||||
interface Props {
|
||||
minPercent?: number
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { useAxios } from "@vueuse/integrations/useAxios"
|
||||
import http from "../utils/http"
|
||||
import http from "utils/http"
|
||||
|
||||
export function login(data: { username: string; password: string }) {
|
||||
return useAxios("login", { method: "post", data }, http, {
|
||||
|
||||
11
src/shared/layout/admin.vue
Normal file
11
src/shared/layout/admin.vue
Normal file
@@ -0,0 +1,11 @@
|
||||
<script setup lang="ts"></script>
|
||||
|
||||
<template>
|
||||
<el-container>
|
||||
<el-main>
|
||||
<router-view></router-view>
|
||||
</el-main>
|
||||
</el-container>
|
||||
</template>
|
||||
|
||||
<style scoped></style>
|
||||
@@ -1,24 +1,24 @@
|
||||
<script setup lang="ts">
|
||||
import Login from "../shared/Login/index.vue"
|
||||
import Signup from "../shared/Signup/index.vue"
|
||||
import Header from "../shared/Header/index.vue"
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<el-container>
|
||||
<el-header class="header">
|
||||
<Header />
|
||||
</el-header>
|
||||
<el-main>
|
||||
<router-view></router-view>
|
||||
</el-main>
|
||||
<Login />
|
||||
<Signup />
|
||||
</el-container>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.header {
|
||||
display: flex;
|
||||
}
|
||||
</style>
|
||||
<script setup lang="ts">
|
||||
import Login from "../Login/index.vue"
|
||||
import Signup from "../Signup/index.vue"
|
||||
import Header from "../Header/index.vue"
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<el-container>
|
||||
<el-header class="header">
|
||||
<Header />
|
||||
</el-header>
|
||||
<el-main>
|
||||
<router-view></router-view>
|
||||
</el-main>
|
||||
<Login />
|
||||
<Signup />
|
||||
</el-container>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.header {
|
||||
display: flex;
|
||||
}
|
||||
</style>
|
||||
@@ -1,9 +1,8 @@
|
||||
<script setup lang="ts">
|
||||
import type * as Monaco from "monaco-editor"
|
||||
import loader from "@monaco-editor/loader"
|
||||
import { LANGUAGE_VALUE } from "../../utils/constants"
|
||||
import { LANGUAGE } from "../../utils/types"
|
||||
import { isMobile } from "../../utils/breakpoints"
|
||||
import { LANGUAGE_VALUE } from "utils/constants"
|
||||
import { LANGUAGE } from "utils/types"
|
||||
import { isMobile } from "utils/breakpoints"
|
||||
|
||||
interface Props {
|
||||
value: string
|
||||
@@ -25,20 +24,18 @@ const emit = defineEmits<{
|
||||
}>()
|
||||
|
||||
const monacoEditorRef = ref()
|
||||
let editor: Monaco.editor.IStandaloneCodeEditor | null
|
||||
let editor: Monaco.editor.IStandaloneCodeEditor
|
||||
|
||||
onMounted(async function () {
|
||||
const monaco = await loader.init()
|
||||
|
||||
const model = monaco.editor.createModel(
|
||||
onMounted(function () {
|
||||
const model = window.monaco.editor.createModel(
|
||||
props.value,
|
||||
LANGUAGE_VALUE[props.language],
|
||||
monaco.Uri.parse(`file:///root/${Date.now()}.${ext()}`)
|
||||
window.monaco.Uri.parse(`file:///root/${Date.now()}.${ext()}`)
|
||||
)
|
||||
|
||||
editor = monaco.editor.create(monacoEditorRef.value, {
|
||||
editor = window.monaco.editor.create(monacoEditorRef.value, {
|
||||
model,
|
||||
theme: "vs-dark", // 官方自带三种主题vs, hc-black, or vs-dark
|
||||
theme: "dark", // 官方自带三种主题vs, hc-black, or vs-dark
|
||||
minimap: {
|
||||
enabled: false,
|
||||
},
|
||||
@@ -47,6 +44,15 @@ onMounted(async function () {
|
||||
tabSize: 4,
|
||||
fontSize: isMobile.value ? 20 : 24, // 字体大小
|
||||
scrollBeyondLastLine: false,
|
||||
lineDecorationsWidth: 0,
|
||||
scrollBeyondLastColumn: 0,
|
||||
glyphMargin: false,
|
||||
scrollbar: {
|
||||
useShadows: false,
|
||||
vertical: "hidden",
|
||||
horizontal: "hidden",
|
||||
},
|
||||
overviewRulerLanes: 0,
|
||||
})
|
||||
|
||||
model.onDidChangeContent(() => {
|
||||
@@ -64,7 +70,7 @@ onMounted(async function () {
|
||||
})
|
||||
|
||||
watchEffect(() => {
|
||||
monaco.editor.setModelLanguage(model, LANGUAGE_VALUE[props.language])
|
||||
window.monaco.editor.setModelLanguage(model, LANGUAGE_VALUE[props.language])
|
||||
})
|
||||
|
||||
watchEffect(() => {
|
||||
|
||||
@@ -36,7 +36,6 @@
|
||||
import Resizer from "./Resizer.vue"
|
||||
import Pane from "./Pane.vue"
|
||||
import { computed, ref } from "vue"
|
||||
import { classNameToArray } from "element-plus/es/utils"
|
||||
|
||||
interface Props {
|
||||
minPercent?: number
|
||||
|
||||
@@ -1,9 +1,5 @@
|
||||
import {
|
||||
PROBLEM_PERMISSION,
|
||||
STORAGE_KEY,
|
||||
USER_TYPE,
|
||||
} from "../../utils/constants"
|
||||
import storage from "../../utils/storage"
|
||||
import { PROBLEM_PERMISSION, STORAGE_KEY, USER_TYPE } from "utils/constants"
|
||||
import storage from "utils/storage"
|
||||
import { getUserInfo } from "../api"
|
||||
|
||||
export const useUserStore = defineStore("user", () => {
|
||||
|
||||
8
src/shims.d.ts
vendored
8
src/shims.d.ts
vendored
@@ -1,3 +1,5 @@
|
||||
import type * as Monaco from "monaco-editor"
|
||||
|
||||
declare module "element-plus/dist/locale/zh-cn.mjs"
|
||||
|
||||
declare module "*.md" {
|
||||
@@ -5,3 +7,9 @@ declare module "*.md" {
|
||||
const Component: ComponentOptions
|
||||
export default Component
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface Window {
|
||||
monaco: Monaco
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,81 +0,0 @@
|
||||
:root {
|
||||
font-family: Inter, Avenir, Helvetica, Arial, sans-serif;
|
||||
font-size: 16px;
|
||||
line-height: 24px;
|
||||
font-weight: 400;
|
||||
|
||||
color-scheme: light dark;
|
||||
color: rgba(255, 255, 255, 0.87);
|
||||
background-color: #242424;
|
||||
|
||||
font-synthesis: none;
|
||||
text-rendering: optimizeLegibility;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
-webkit-text-size-adjust: 100%;
|
||||
}
|
||||
|
||||
a {
|
||||
font-weight: 500;
|
||||
color: #646cff;
|
||||
text-decoration: inherit;
|
||||
}
|
||||
a:hover {
|
||||
color: #535bf2;
|
||||
}
|
||||
|
||||
body {
|
||||
margin: 0;
|
||||
display: flex;
|
||||
place-items: center;
|
||||
min-width: 320px;
|
||||
min-height: 100vh;
|
||||
}
|
||||
|
||||
h1 {
|
||||
font-size: 3.2em;
|
||||
line-height: 1.1;
|
||||
}
|
||||
|
||||
button {
|
||||
border-radius: 8px;
|
||||
border: 1px solid transparent;
|
||||
padding: 0.6em 1.2em;
|
||||
font-size: 1em;
|
||||
font-weight: 500;
|
||||
font-family: inherit;
|
||||
background-color: #1a1a1a;
|
||||
cursor: pointer;
|
||||
transition: border-color 0.25s;
|
||||
}
|
||||
button:hover {
|
||||
border-color: #646cff;
|
||||
}
|
||||
button:focus,
|
||||
button:focus-visible {
|
||||
outline: 4px auto -webkit-focus-ring-color;
|
||||
}
|
||||
|
||||
.card {
|
||||
padding: 2em;
|
||||
}
|
||||
|
||||
#app {
|
||||
max-width: 1280px;
|
||||
margin: 0 auto;
|
||||
padding: 2rem;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
@media (prefers-color-scheme: light) {
|
||||
:root {
|
||||
color: #213547;
|
||||
background-color: #ffffff;
|
||||
}
|
||||
a:hover {
|
||||
color: #747bff;
|
||||
}
|
||||
button {
|
||||
background-color: #f9f9f9;
|
||||
}
|
||||
}
|
||||
@@ -212,16 +212,6 @@ export const DEAD_RESULTS = {
|
||||
},
|
||||
}
|
||||
|
||||
export const LANGUAGE_LABEL = {
|
||||
C: "C",
|
||||
"C++": "C++",
|
||||
Java: "Java",
|
||||
Python2: "Python2",
|
||||
Python3: "Python",
|
||||
JavaScript: "JS",
|
||||
Golang: "Go",
|
||||
}
|
||||
|
||||
export const LANGUAGE_VALUE = {
|
||||
C: "c",
|
||||
"C++": "cpp",
|
||||
|
||||
Reference in New Issue
Block a user