1

我正在尝试根据未注册用户的偏好设置网页主题,存储在localStorage. 但是,在 Nuxt.js SSR 应用程序的默认布局中这样做时,从默认主题到他们的首选主题会有一个小的闪烁。为了防止这种情况,我需要在从中提取数据之前阻止页面呈现localStorage,但我似乎无法弄清楚如何在 Nuxt 中这样做。

<template>
  <div :data-theme="theme" class="flex min-h-screen flex-col justify-between">
    <TheHeader :currentTheme="theme" @themeChange="setTheme" />
    <Nuxt />
    <TheFooter />
  </div>
</template>

<script>
export default {
  data: function () {
    return {
      theme: "light",
    };
  },
  head() {
    return {
      htmlAttrs: {
        "data-theme": this.theme,
      },
    };
  },
  beforeMount() {
    // NOTE: first check if registered user, and perhaps store in Vuex Store
    // TODO: no flicker
    if (localStorage.theme === "dark") {
      this.theme = "dark";
    } else {
      this.theme = "light";
    }
  },
  methods: {
    setTheme(theme) {
      this.theme = theme;
      localStorage.setItem("theme", theme);
    },
  },
  created() {
    // for emitted event to be called in the layout
    this.$nuxt.$on("changeTheme", (theme) => {
      this.setTheme(theme);
    });
  },
};
</script>

我正在使用daisyUI TailwindCSS,它依赖于将data-theme<html>标签的设置为其选项之一。


我试过的

  1. 创建 Nuxt 插件,因为插件在页面渲染之前运行。这还没有解决,因为我需要更新默认布局页面中的数据值。

  2. created()在-中运行初始主题更改localStorage超出了范围。

  3. 动态设置 htmlAttr ( "data-theme": localStorage.theme ? localStorage.theme : "light") - 也失败了,因为这里无法访问 localStorage。

那么有没有办法完成这个预渲染主题设置来防止闪烁呢?

4

0 回答 0