티스토리 뷰

NuxtPage 컴포넌트는 pages 디렉토리에 있는 컴포넌트를 화면에 표시하는데 사용된다.

VueRouter의 <RouterView> 컴포넌트를 둘러싼 래퍼이다. 동일한 name과 porps를 허용한다.

 

실습

이전강의와 다음강의를 불러서 footer에 넣을 것이다.

import type { CourseWithPath } from '~/types/course';

interface CourseReturn {
  course: Maybe<CourseWithPath>; // Course | null | undefined
  prevCourse: Maybe<CourseWithPath>; // Course | null | undefined
  nextCourse: Maybe<CourseWithPath>; // Course | null | undefined
}

export const useCourse = (courseSlug: string): CourseReturn => {
  const { courses } = useCourses();
  // const course = courses.find(
  //   (course: any) => course.courseSlug === courseSlug,
  // );
  const index = courses.findIndex(
    (course: any) => course.courseSlug === courseSlug,
  );
  const course = courses[index];
  const prevCourse = index <= 0 ? null : courses[index - 1];
  const nextCourse = index >= courses.length - 1 ? null : courses[index + 1];
  return { course, prevCourse, nextCourse };
};

 

pages의 렌더링 페이지

<template>
  <div class="q-pa-xl">
    <AppCard>
      <template #header>
        <div class="text-h5 text-weight-medium">{{ course?.title }}</div>
        <div class="flex q-gutter-x-sm items-center q-mt-sm text-grey-8">
          <span class="flex items-center">
            <q-icon name="star" size="16px" color="orange" />
            <span>{{ course?.rating }}</span>
          </span>
          <span>{{ course?.reviewsCount }}</span>
          <span>&middot;</span>
          <span>{{ course?.studentCount }}</span>
          <q-space />
          <a class="text-bold" :href="course?.reviewsUrl" target="_blank">
            수강평 보기
          </a>
        </div>
      </template>
      <div class="q-mb-md">
        <VideoPlayer :src="course?.video" />
      </div>
      <div class="row q-col-gutter-md">
        <div class="col-6">
          <q-btn
            label="인프런에서 수강하기"
            unelevated
            class="full-width"
            color="primary"
            :href="course?.inflearnUrl"
            target="_blank"
          />
        </div>
        <div class="col-6">
          <q-btn
            label="짐코딩 클럽에서 수강하기"
            unelevated
            class="full-width"
            color="red"
            :href="course?.gymcodingUrl"
            target="_blank"
          />
        </div>
      </div>
      <p class="q-mt-lg text-grey-8">
        {{ course?.content }}
      </p>
      <template #footer>
        <q-btn
          v-if="prevCourse"
          label="이전 강의"
          color="primary"
          unelevated
          :to="prevCourse.path"
        />
        <q-space />
        <q-btn
          v-if="nextCourse"
          label="다음 강의"
          color="primary"
          unelevated
          :to="nextCourse.path"
        />
      </template>
    </AppCard>
  </div>
</template>

<script setup lang="ts">
const route = useRoute();
const courseSlug = route.params.courseSlug as string;
const { course, prevCourse, nextCourse } = useCourse(courseSlug);
</script>

<style scoped></style>

 

q-btn에서 :to를 이용해 path를 넣을 수 있고 클릭할 수 있게 된다.

 

NuxtPage와 RouterView여기서 차이점이 나오는데

 

app.vue를 클릭해본다.

<template>
  <NuxtLayout>
    <!-- <NuxtPage /> -->
    <RouterView />
    <!--layouts>default.vue의 slot부분-->
  </NuxtLayout>
</template>
<script setup lang="ts"></script>

NuxtPage를 RouterView로 넣어본다.

 

그럼

다음 강의를 눌러도 url만 변경되고 페이지는 이동되지 않는다. 그 이유는 pages렌더링 페이지는 이미 렌더링이 끝났기 때문에

재 렌더링이 되지 않는 것이다.

 

인프런 - nuxt 강의 짐코딩

 

RouterView를 사용하면 watcher API나 navigate 같은 것을 사용해야한다.

하지만 NuxtPage는 편하게 패스만 변경되도 재렌더링이 된다.

 

인프런 - nuxt 강의 짐코딩

page-key 속성을 이용하면 한번만 렌더링이 된다.

동적인 키로도 사용이 가능하다.

 

동적인 키가 뭐가 필요한가?

NuxtPage 컴포넌트는 url의 파라미터가 변경된다고 해도 변경되지 않는다.

테스트 소스로 path는 유지하고 쿼리파라미터를 추가해보았다.

        <q-btn
          v-if="prevCourse"
          label="쿼리추가"
          color="primary"
          unelevated
          :to="{ path: $route.path, query: { timestamp: Date.now() } }"
        />
        <q-space />

 

역시 변경되지 않는다.

 

그런데 이런 쿼리파라미터에서도 다시 렌더링하고 싶다면?

app.vue

<template>
  <NuxtLayout>
    <NuxtPage :page-key="(route) => route.fullPath" />
    <!-- <RouterView /> -->
    <!--layouts>default.vue의 slot부분-->
  </NuxtLayout>
</template>
<script setup lang="ts"></script>

이렇게 fullpath를 nuxtPage의 page-key속성에 동적으로 넣어주면된다.

 

인프런 - nuxt 강의 짐코딩

 

하지만 공식문서에도 route를 사용하면 안된다고 적혀있다.

 

사용하고자 하는 페이지에

<script setup lang="ts">
const route = useRoute();
const courseSlug = route.params.courseSlug as string;
const { course, prevCourse, nextCourse } = useCourse(courseSlug);

definePageMeta({
  key: (route) => route.fullPath,
});
</script>

definePageMeta를 사용하기를 권장한다.

 

 

'dev_공부일지 > Nuxt' 카테고리의 다른 글

auto-imports.. Composables , types, emit 만들기  (0) 2024.05.15
vue3 with TypsScript  (0) 2024.05.15
라우팅 기본 : 파일 기본 라우팅  (0) 2024.05.15
Nuxt 컴포넌트 계층  (0) 2024.05.13
Quasar Ui Framwork 설치  (0) 2024.05.13
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
«   2024/10   »
1 2 3 4 5
6 7 8 9 10 11 12
13 14 15 16 17 18 19
20 21 22 23 24 25 26
27 28 29 30 31
글 보관함