Skip to content

Commit

Permalink
feat: implementation summary and refactor code
Browse files Browse the repository at this point in the history
  • Loading branch information
cuixiaorui committed Jan 24, 2024
1 parent d8f3859 commit a17f3e8
Show file tree
Hide file tree
Showing 22 changed files with 4,448 additions and 7,592 deletions.
12 changes: 11 additions & 1 deletion apps/api/src/course/course.controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,17 @@ export class CourseController {
constructor(private courseService: CourseService) {}

@Get(':courseId')
getStatements(@Param('courseId') courseId: number) {
findOne(@Param('courseId') courseId: number) {
return this.courseService.find(courseId);
}

@Get('')
findAll() {
return this.courseService.findAll();
}

@Get(':courseId/next')
findNext(@Param('courseId') courseId: number) {
return this.courseService.findNext(courseId);
}
}
64 changes: 53 additions & 11 deletions apps/api/src/course/course.service.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,50 @@
import { DB, DbType } from '../global/providers/db.provider';
import { eq, asc } from 'drizzle-orm';
import { eq, asc, gt } from 'drizzle-orm';
import { statement, course } from '@earthwrom/shared';
import { Injectable, Inject } from '@nestjs/common';
import { Injectable, Inject, HttpException, HttpStatus } from '@nestjs/common';

@Injectable()
export class CourseService {
constructor(@Inject(DB) private db: DbType) {}

async findNext(courseId: number) {
const result = await this.db
.select({ id: course.id, title: course.title })
.from(course)
.where(gt(course.id, courseId))
.orderBy(asc(course.id));

if (result.length < 0) {
throw new HttpException(
'There is no next course',
HttpStatus.BAD_REQUEST,
);
}

const nextCourse = result[0];

const statementsResult = await this.findStatements(nextCourse.id);

const finalResult = {
id: nextCourse.id,
title: nextCourse.title,
statements: statementsResult,
};

return finalResult;
}

async findAll() {
const courseResult = await this.db
.select({
id: course.id,
title: course.title,
})
.from(course);

return courseResult;
}

async find(courseId: number) {
const courseResult = await this.db
.select({
Expand All @@ -16,7 +54,19 @@ export class CourseService {
.from(course)
.where(eq(course.id, courseId));

const statementsResult = await this.db
const statementsResult = await this.findStatements(courseId);

const finalResult = {
id: courseResult[0].id,
title: courseResult[0].title,
statements: statementsResult,
};

return finalResult;
}

private async findStatements(courseId) {
return await this.db
.select({
id: statement.id,
chinese: statement.chinese,
Expand All @@ -26,13 +76,5 @@ export class CourseService {
.from(statement)
.where(eq(statement.courseId, courseId))
.orderBy(asc(statement.order));

const finalResult = {
id: courseResult[0].id,
title: courseResult[0].title,
statements: statementsResult,
};

return finalResult;
}
}
9 changes: 9 additions & 0 deletions apps/client/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -73,3 +73,12 @@ bun run preview
```

Check out the [deployment documentation](https://nuxt.com/docs/getting-started/deployment) for more information.




## 开发规范

1. 不要解构 pinia 的 store
- 解构会导致响应式丢失问题(ref 类型也会变成普通类型)
- 带上 store 的话 代码可读性也更好一点 一眼就能知道数据的来源是哪里
11 changes: 9 additions & 2 deletions apps/client/api/courses.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,18 @@ import { useFetchPlus } from "~/composables/useFetch";
interface Course {
title: string;
id: number;
statements: Array<any>;
}

export async function fetchCourse(courseId: number) {
const { data: courses } = await useFetchPlus<Course[]>(
`/courses/${courseId}`
const { data: courses } = await useFetchPlus<Course>(`/courses/${courseId}`);

return courses;
}

export async function fetchNextCourse(courseId: number) {
const { data: courses } = await useFetchPlus<Course>(
`/courses/${courseId}/next`
);

return courses;
Expand Down
71 changes: 42 additions & 29 deletions apps/client/components/main/Answer.vue
Original file line number Diff line number Diff line change
Expand Up @@ -27,51 +27,64 @@

<script setup lang="ts">
import { useCoursesStore } from "~/store/courses";
import { useEnglishSound } from "~/composables/useEnglishSound";
import { registerShortcut, cancelShortcut } from "~/utils/keyboardShortcuts";
import { useMode } from "./game";
import { useSummary } from "./summary";
const emit = defineEmits(["nextQuestion"]);
const { showQuestion } = useMode();
const { showSummary } = useSummary();
const { sound } = useCurrentStatementEnglishSound();
const coursesStore = useCoursesStore();
const { currentStatement, toNextStatement } = useCoursesStore();
const { soundmark, word } = useShowInfo();
useShortcutToNext();
autoPlayEnglishSound();
const soundmark = ref("");
const word = ref("");
function useShowInfo() {
const soundmark = ref("");
const word = ref("");
onMounted(() => {
play();
});
watchEffect(() => {
soundmark.value = coursesStore.currentStatement?.soundmark;
word.value = coursesStore.currentStatement?.english;
});
const { play } = useEnglishSound(word);
return {
soundmark,
word,
};
}
watchEffect(() => {
soundmark.value = currentStatement?.soundmark!;
word.value = currentStatement?.english!;
});
function autoPlayEnglishSound() {
onMounted(() => {
sound.play();
});
}
function handleToNextStatement() {
if (coursesStore.isAllDone()) {
showSummary();
return;
}
async function handleToNextStatement() {
toNextStatement();
emit("nextQuestion");
coursesStore.toNextStatement();
showQuestion();
}
function handlePlaySound() {
play();
sound.play();
}
// TODO 后续处理
// useKeyboardShortcut()
function useKeyboardShortcut() {
const handleKeyDown = (event: KeyboardEvent) => {
if (event.key === "Enter") {
console.log("enter");
// handleToNextStatement();
}
};
function useShortcutToNext() {
function handleKeydown() {
handleToNextStatement();
}
onMounted(() => {
document.addEventListener("keydown", handleKeyDown);
registerShortcut("enter", handleKeydown);
});
onUnmounted(() => {
document.removeEventListener("keydown", handleKeyDown);
cancelShortcut("enter", handleKeydown);
});
}
</script>
21 changes: 9 additions & 12 deletions apps/client/components/main/Game.vue
Original file line number Diff line number Diff line change
Expand Up @@ -2,34 +2,31 @@
<div class="h-full w-full flex flex-col justify-center items-center">
<div class="flex-1 mb-8">
<template v-if="mode === 'question'">
<Question @bingo="handleBingo"></Question>
<Question></Question>
</template>
<template v-else-if="mode === 'answer'">
<Answer @next-question="handleNextQuestion"></Answer>
<Answer></Answer>
</template>
</div>
<div class="">
<CourseProgress></CourseProgress>
<Tips onShowAnswer="{handleShowAnswer}"></Tips>
<Tips></Tips>
</div>
<Summary></Summary>
</div>
</template>

<script setup lang="ts">
import Question from "./Question.vue";
import Answer from "./Answer.vue";
import CourseProgress from "./CourseProgress.vue";
import Tips from './Tips.vue';
import Summary from "./Summary.vue";
import Tips from "./Tips.vue";
import { useMode } from "./game";
const mode = ref<"question" | "answer">("question");
const { mode } = useMode();
function handleBingo() {
mode.value = "answer";
}
function handleNextQuestion() {
mode.value = "question";
}
const showModal = ref(false);
</script>

<style scoped></style>
24 changes: 17 additions & 7 deletions apps/client/components/main/Question.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
<template>
<div class="text-5xl text-center mb-20 mt-10">
<div class="text-fuchsia-500 dark:text-gray-50">
{{ coursesStore.currentStatement?.chinese || '生存还是毁灭,这是一个问题' }}
{{
coursesStore.currentStatement?.chinese || "生存还是毁灭,这是一个问题"
}}
</div>
<div class="code-box">
<template v-for="i in lineNum" :key="i">
Expand All @@ -19,10 +21,11 @@
</div>
</template>
<input
ref="input"
class="code-input"
type="text"
v-model="inputValue"
@keydown="handleKeyDown"
@keyup="handleKeyup"
@focus="handleInputFocus"
@blur="handleBlur"
autoFocus
Expand All @@ -33,11 +36,13 @@

<script setup lang="ts">
import { useCoursesStore } from "~/store/courses";
import { useMode } from "./game";
const emit = defineEmits(["bingo"]);
const { showAnswer } = useMode();
const coursesStore = useCoursesStore();
const coursesStore = useCoursesStore();
const input = ref<HTMLInputElement>();
const lineNum = ref(1);
const focusing = ref(true);
const inputValue = ref("");
Expand All @@ -47,7 +52,6 @@ const activeInputIndex = computed(() => {
return Math.min(words.value.length - 1, lineNum.value - 1);
});
watchEffect(() => {
lineNum.value = coursesStore.currentStatement?.english.split(" ").length || 1;
});
Expand All @@ -56,15 +60,21 @@ watchEffect(() => {
words.value = inputValue.value.trimStart().split(" ");
});
function handleKeyDown(e: KeyboardEvent) {
function handleKeyup(e: KeyboardEvent) {
if (e.code === "Enter") {
e.stopPropagation();
if (coursesStore.checkCorrect(inputValue.value.trim())) {
emit("bingo");
showAnswer();
}
inputValue.value = "";
}
}
onMounted(() => {
input.value?.focus();
});
function handleInputFocus() {
focusing.value = true;
}
Expand Down
Loading

0 comments on commit a17f3e8

Please sign in to comment.