This commit is contained in:
2026-09-06 03:50:05 +07:00
parent 8e32877a64
commit e9abab3911
2 changed files with 68 additions and 176 deletions
+44 -125
View File
@@ -416,12 +416,7 @@ useSimplePolling(() => {
</Icon>
Настройки
</n-button>
<n-button
v-if="(game.teams?.length || 0) == 0"
type="error"
quaternary
@click="showDeleteGameModal = true"
>
<n-button v-if="(game.teams?.length || 0) == 0" type="error" quaternary @click="showDeleteGameModal = true">
Удалить игру
</n-button>
@@ -471,9 +466,7 @@ useSimplePolling(() => {
</div>
<n-flex justify="end">
<n-button
@click="openQR(getTeamStoryURL(team.id!, team.password!), 'Подсмотреть игру')"
>
<n-button @click="openQR(getTeamStoryURL(team.id!, team.password!), 'Подсмотреть игру')">
QR
</n-button>
<n-button @click="toTeamStory(team.id!, team.password!, true)">
@@ -483,12 +476,8 @@ useSimplePolling(() => {
</n-flex>
</n-flex>
<n-button
v-for="application in team.applications"
:key="application.name"
class="link-button"
@click="giveApplication(team, application)"
>
<n-button v-for="application in team.applications" :key="application.name" class="link-button"
@click="giveApplication(team, application)">
Выдать: {{ application.name }}
</n-button>
</div>
@@ -498,31 +487,16 @@ useSimplePolling(() => {
<!-- Окно настроек -->
<n-modal v-model:show="showSettingsModal">
<n-card
style="width: 600px"
title="Настройки игры"
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
>
<n-card style="width: 600px" title="Настройки игры" :bordered="false" size="huge" role="dialog" aria-modal="true">
<template #header-extra>
<n-button @click="closeSettings()"> x </n-button>
</template>
<n-space vertical>
<p>Название</p>
<n-input
v-model:value="settingsDraft.name"
type="text"
placeholder='Дело №0 "Следствие ведут овечки"'
/>
<n-input v-model:value="settingsDraft.name" type="text" placeholder='Дело №0 "Следствие ведут овечки"' />
<p class="settings-header">Описание</p>
<n-input
v-model:value="settingsDraft.description"
type="textarea"
placeholder="Убийство пастуха..."
/>
<n-input v-model:value="settingsDraft.description" type="textarea" placeholder="Убийство пастуха..." />
</n-space>
<template #footer>
<n-flex justify="end">
@@ -534,14 +508,7 @@ useSimplePolling(() => {
<!-- Окно выдачи улик -->
<n-modal v-model:show="showGiveApplicationModal">
<n-card
style="width: 600px"
title="Настройки игры"
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
>
<n-card style="width: 600px" title="Настройки игры" :bordered="false" size="huge" role="dialog" aria-modal="true">
<template #header-extra>
<n-button @click="showGiveApplicationModal = false"> x </n-button>
</template>
@@ -552,38 +519,22 @@ useSimplePolling(() => {
<p>Улика</p>
<h3>{{ giveApplicationApplication.name }}</h3>
<div
v-if="
applicationFileType(giveApplicationApplication) == 'image' &&
giveApplicationApplication.image
"
class="give-application-image-block"
>
<img
:src="applicationFileURL(giveApplicationApplication.image)"
class="give-application-image"
/>
<div v-if="
applicationFileType(giveApplicationApplication) == 'image' &&
giveApplicationApplication.image
" class="give-application-image-block">
<img :src="applicationFileURL(giveApplicationApplication.image)" class="give-application-image" />
</div>
<audio
v-else-if="
applicationFileType(giveApplicationApplication) == 'audio' &&
giveApplicationApplication.image
"
:src="applicationFileURL(giveApplicationApplication.image)"
controls
preload="none"
class="give-application-audio"
></audio>
<a
v-else-if="
applicationFileType(giveApplicationApplication) == 'pdf' &&
giveApplicationApplication.image
"
:href="applicationFileURL(giveApplicationApplication.image)"
target="_blank"
rel="noopener"
class="give-application-pdf-link"
>
<audio v-else-if="
applicationFileType(giveApplicationApplication) == 'audio' &&
giveApplicationApplication.image
" :src="applicationFileURL(giveApplicationApplication.image)" controls preload="none"
class="give-application-audio"></audio>
<a v-else-if="
applicationFileType(giveApplicationApplication) == 'pdf' &&
giveApplicationApplication.image
" :href="applicationFileURL(giveApplicationApplication.image)" target="_blank" rel="noopener"
class="give-application-pdf-link">
PDF
</a>
</n-space>
@@ -597,14 +548,7 @@ useSimplePolling(() => {
<!-- Окно создания команды -->
<n-modal v-model:show="showAddTeamModal">
<n-card
style="width: 600px"
title="Создание команды"
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
>
<n-card style="width: 600px" title="Создание команды" :bordered="false" size="huge" role="dialog" aria-modal="true">
<template #header-extra>
<n-button @click="showAddTeamModal = false"> x </n-button>
</template>
@@ -619,14 +563,7 @@ useSimplePolling(() => {
<!-- Окно создания команды -->
<n-modal v-model:show="showDeleteTeamModal">
<n-card
style="width: 600px"
title="Удаление команды"
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
>
<n-card style="width: 600px" title="Удаление команды" :bordered="false" size="huge" role="dialog" aria-modal="true">
<template #header-extra>
<n-button @click="showDeleteTeamModal = false"> x </n-button>
</template>
@@ -650,14 +587,7 @@ useSimplePolling(() => {
<!-- Окно удаления игры -->
<n-modal v-model:show="showDeleteGameModal">
<n-card
style="width: 600px"
title="Удаление игры"
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
>
<n-card style="width: 600px" title="Удаление игры" :bordered="false" size="huge" role="dialog" aria-modal="true">
<template #header-extra>
<n-button @click="showDeleteGameModal = false"> x </n-button>
</template>
@@ -666,11 +596,7 @@ useSimplePolling(() => {
Введите название игры
<n-text class="name-text" strong>{{ game.name }}</n-text> чтобы удалить её
</p>
<n-input
v-model:value="deletedGameName"
type="text"
placeholder='Дело №0 "Следствие ведут овечки"'
/>
<n-input v-model:value="deletedGameName" type="text" placeholder='Дело №0 "Следствие ведут овечки"' />
</n-space>
<template #footer>
@@ -685,14 +611,7 @@ useSimplePolling(() => {
<!-- Окно qr -->
<n-modal v-model:show="showQR">
<n-card
style="width: 600px"
:title="titleQR"
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
>
<n-card style="width: 600px" :title="titleQR" :bordered="false" size="huge" role="dialog" aria-modal="true">
<template #header-extra>
<n-button @click="showQR = false"> x </n-button>
</template>
@@ -708,15 +627,8 @@ useSimplePolling(() => {
<!-- Окно ответов команд и оценки -->
<n-modal v-model:show="showAnswersModal">
<n-card
style="width: min(94vw, 900px)"
title="Ответы команд"
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
:content-style="{ maxHeight: '70vh', overflow: 'auto' }"
>
<n-card style="width: min(94vw, 900px)" title="Ответы команд" :bordered="false" size="huge" role="dialog"
aria-modal="true" :content-style="{ maxHeight: '70vh', overflow: 'auto' }">
<template #header-extra>
<n-button @click="showAnswersModal = false"> x </n-button>
</template>
@@ -725,7 +637,9 @@ useSimplePolling(() => {
</div>
<div v-for="question in answersQuestions" :key="question.code" class="answers-question-block">
<p class="answers-question-title">{{ question.code }}: {{ question.text }}</p>
<p class="answers-question-answer">Правильный ответ: {{ question.answer || '—' }}</p>
<p class="answers-question-answer">
Правильный ответ:<br /><span class="correct-answer">{{ question.answer || '—' }}</span>
</p>
<div v-for="team in answersTeams" :key="team.team?.id" class="answers-team-row">
<div class="answers-team-name">
{{ team.team?.name }}
@@ -733,12 +647,9 @@ useSimplePolling(() => {
<div class="answers-team-answer">
{{ teamAnswer(team, question.code) || '—' }}
</div>
<n-input-number
:value="scores[scoreKey(team.team?.id, question.code)]"
@update:value="onScoreUpdate(scoreKey(team.team?.id, question.code), $event)"
placeholder="Балл"
class="answers-score-input"
/>
<n-input-number :value="scores[scoreKey(team.team?.id, question.code)]"
@update:value="onScoreUpdate(scoreKey(team.team?.id, question.code), $event)" placeholder="Балл"
class="answers-score-input" />
</div>
</div>
<template #footer>
@@ -851,6 +762,14 @@ useSimplePolling(() => {
margin: 0 0 10px;
}
.correct-answer {
color: gold;
display: inline-block;
font-weight: 500;
margin-top: 4px;
white-space: pre-wrap;
}
.answers-team-row {
align-items: center;
background-color: rgb(255 255 255 / 5%);
+24 -51
View File
@@ -44,52 +44,31 @@ const updateMode = (mode: string) => {
</script>
<template>
<div
v-if="mode == 'mini-add'"
class="place-block-hover show-editor-block"
@click="updateMode('add')"
>
<div v-if="mode == 'mini-add'" class="place-block-hover show-editor-block" @click="updateMode('add')">
<p class="place-image-plus">+</p>
</div>
<div v-if="mode == 'add'" class="place-block">
<n-space vertical>
<n-input-group>
<n-input
:style="{ width: '25%' }"
:value="newQuestionCode"
@update:value="updateCode"
type="text"
placeholder="В-1"
/>
<n-input
:style="{ width: '75%' }"
:value="newQuestionText"
@update:value="updateText"
type="text"
placeholder="Кто украл пастуха?"
/>
<n-input :style="{ width: '25%' }" :value="newQuestionCode" @update:value="updateCode" type="text"
placeholder="В-1" />
<n-input :style="{ width: '75%' }" :value="newQuestionText" @update:value="updateText" type="text"
placeholder="Кто украл пастуха?" />
</n-input-group>
<n-input
:value="newQuestionAnswer"
@update:value="updateAnswer"
type="textarea"
:autosize="{ minRows: 2 }"
placeholder="Правильный ответ (виден только автору и организаторам)"
/>
<n-input :value="newQuestionAnswer" @update:value="updateAnswer" type="textarea" :autosize="{ minRows: 2 }"
placeholder="Правильный ответ (виден только автору и организаторам)" />
<slot></slot>
</n-space>
</div>
<div
v-if="mode == 'show-editor'"
class="place-block-hover show-editor-block"
@click="updateMode('edit')"
>
<div v-if="mode == 'show-editor'" class="place-block-hover show-editor-block" @click="updateMode('edit')">
<div class="message-header">{{ props.question?.code }}: {{ props.question?.text }}</div>
<hr class="hr" />
<div class="message-content">
<span v-if="props.question?.answer">Ответ: {{ props.question.answer }}</span>
<span v-if="props.question?.answer">
Ответ:<br /><span class="correct-answer">{{ props.question.answer }}</span>
</span>
<span v-else class="intro-empty">Ответ не задан</span>
</div>
</div>
@@ -97,27 +76,14 @@ const updateMode = (mode: string) => {
<div v-if="mode == 'edit'" class="place-block">
<n-space vertical>
<n-input-group>
<n-input
:style="{ width: '25%' }"
v-model:value="props.question!.code"
type="text"
placeholder="В-1"
/>
<n-input
:style="{ width: '75%' }"
v-model:value="props.question!.text"
type="text"
placeholder="Кто украл пастуха?"
/>
<n-input :style="{ width: '25%' }" v-model:value="props.question!.code" type="text" placeholder="В-1" />
<n-input :style="{ width: '75%' }" v-model:value="props.question!.text" type="text"
placeholder="Кто украл пастуха?" />
</n-input-group>
<p class="settings-header">Правильный ответ</p>
<n-input
v-model:value="props.question!.answer"
type="textarea"
:autosize="{ minRows: 2 }"
placeholder="Правильный ответ (виден только автору и организаторам)"
/>
<n-input v-model:value="props.question!.answer" type="textarea" :autosize="{ minRows: 2 }"
placeholder="Правильный ответ (виден только автору и организаторам)" />
<n-text class="hint" depth="3">
Смена кода вопроса не переносит ответы команд, отправленные под старым кодом.
</n-text>
@@ -169,13 +135,20 @@ const updateMode = (mode: string) => {
.message-content {
font-weight: 500;
white-space: pre-wrap;
}
.intro-empty {
color: #777;
}
.correct-answer {
color: gold;
display: inline-block;
font-weight: 500;
margin-top: 4px;
white-space: pre-wrap;
}
.settings-header {
margin-top: 20px;
}