【问题标题】:Nativescript Angular, changing themeNativescript Angular,不断变化的主题
【发布时间】:2019-08-29 23:45:26
【问题描述】:

我正在使用 Angular 构建一个 NativeScript 应用程序,并且我正在尝试实现主题切换,但我无法让它与 Webpack 捆绑一起使用。

我的版本:

  • 7.2.12
  • Nativescript-angular 7.2.3
  • Nativescript 主题 2.0.0
  • 打字稿3.2.2

我按照教程在 Angular 项目中实现该功能:herehere。但这些适用于非 webpack(没有 --bundle 标志)构建。使用捆绑标志(以及更改 described here),切换不再起作用,并且每个切换都会引发错误:

JS: ~/assets/themes/dark.scss
JS: Error: Css styling failed: Error: undefined:1:26: missing '{'

主题文件(位于~/assets/themes/dark.scss

ActionBar {
  background-color: #B20000;
  color: #FFFFFF;
}

.btn-primary {
  background-color: #B20000;
  color: #000000;
}

函数applyThemeCss() 应该从项目中提取样式,但这不是因为错误。 测试项目可以在here, on StackBlitz 找到(我没有使用 Nativescript 游乐场,因为它没有 package.json 和 assets 文件夹

【问题讨论】:

  • 您不能直接更新package.json,但您仍然可以在Playground 中安装插件,使用左上角的+(加号)图标并选择Add NPM Package。并且应用主题方法需要一个 CSS 文件而不是 SCSS,请确保您的 webpack 在编译时选择它。
  • 嘿@Manoj,感谢您的回复!使用 package.json 我没有地方可以添加我正在使用的脚本 (tns run android --bundle)。另外,nativescript-themes 插件文档里面有一个 scss 文件,文档错了吗? (var cssText = require('~/assets/themes/dark.scss');)
  • 我很肯定 SCSS 可能无法正常工作,但文件扩展名本身并不重要,只要它里面只有 CSS,这就是你的情况。如果您喜欢使用 SCSS 语法,则应将其预编译为 CSS。我怀疑您的 dark.scss 文件未包含在捆绑包中,但无法确定是否没有示例项目来重现该问题。
  • @Manoj,我在帖子中添加了一个项目来重现问题

标签: angular typescript sass nativescript nativescript-angular


【解决方案1】:

applyThemeCss() 期望 CSS 文本不是文件路径。在示例代码中,他使用 require 语句读取文件,然后将 CSS 文本传递给方法。

另外,如果您希望动态应用多个主题,则可能需要修改 webpack.config.js 以将 CSS 文件发送到应用程序包,如下所示。

        // Copy assets to out dir. Add your own globs as needed.
        new CopyWebpackPlugin([
            { from: { glob: "assets/**" } },
            { from: { glob: "fonts/**" } },
            { from: { glob: "**/*.jpg" } },
            { from: { glob: "**/*.png" } },
        ], { ignore: [`${relative(appPath, appResourcesFullPath)}/**`] }),

然后使用applyTheme()方法传递文件名

Themes.applyTheme(ThemeService.THEME_PATH + theme);

如果你喜欢使用applyThemeCss()然后读取文件并传递内容

Themes.applyThemeCSS(knownFolders.currentApp().getFile('assets/themes/' + theme).readTextSync(), theme);

【讨论】:

  • 我认为这可行。但我仍然有我的主题文件是使用 scss 变量的 .scss 文件的问题。所以他们需要编译。我试过用npmjs.com/package/extract-text-webpack-plugin 玩arround,但我无法让它与正则表达式/\*\.theme\.scss$/ 一起使用。在这一点上你能给我一些帮助吗?
  • 你可能不需要额外的 webpack 插件来实现这个目的。我认为如果您只是在 webpack 配置中修改/添加类似于 app.scss 的 scss 文件的条目,它将被编译并包含在包中。然后在运行时执行 require('path-to-your-scss') 应该返回 CSS 文本,就像在插件仓库的示例中一样。
  • 执行上述操作会给我运行时错误 ERROR 错误:找不到模块 '~/styles/themes/dark.scss',即使我通过导入将文件包含到包中。所以我认为不是这样(更新了 repo 中的代码)
  • 在我的代码中包含 require 语句也会引发 webpack 警告:Critical dependency: the request of a dependency is an expression。所以我不认为 require 语句是正确的解决方案。 '~styles/' 或 '~assets/' 不起作用也是有道理的,因为 Nativescript 中的整个项目结构与普通 webpack 项目中的不同(在 github 应用程序的控制台中运行 webpack --env.android='android' 以查看构建输出)
  • 单独的 require 语句不会做任何事情。正如我已经提到的,你也必须更新 webpack 配置。
【解决方案2】:

在@Manoj 的帮助下,我设法将我的 css 主题加载到我的应用程序中并切换主题。

{ from: { glob: "assets/**" } }, 行将样式表从“assets/”复制到“dist/assets”。 但由于我想将所有样式保存在同一个文件夹('styles/')中,我需要将代码更新为:{ from: { glob: "styles/themes/**" }, to: 'assets/' },

因为我使用的是 scss 而不是 css,所以我仍然需要转换样式。我们可以通过node-sassrenderSync 方法来做到这一点。 (更多信息请参见this post

当我们结合它时,我们得到以下代码:

const scss = require('node-sass');

....

new CopyWebpackPlugin([
     {
        from: { glob: "styles/themes/*.scss" },
        to: 'assets/themes/[name].css',
        transform(content, path) {
            const result = sass.renderSync({ file: path });
            return result.css.toString();
        },
     },
     {from: {glob: "fonts/**"}},
     {from: {glob: "**/*.jpg"}},
     {from: {glob: "**/*.png"}},
], {ignore: [`${relative(appPath, appResourcesFullPath)}/**`]}),

这会将主题文件从styles/themes/ 复制并编译到assets/themes/。请注意,这也会忽略位于主题文件夹中的任何子文件夹。这样我们就可以做到以下几点:

themes/
-- parts/ // <-- This folder will not be copied
---- _dark-variables.scss 
---- _light-variables.scss
-- dark.scss // <-- This will be compiled into assets/themes/dark.css
-- light.scss // <-- This will be compiled into assets/themes/light.css

【讨论】:

    猜你喜欢
    • 2018-12-08
    • 1970-01-01
    • 1970-01-01
    • 2015-08-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多