Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

两个页面不能共用一个公共组件 #8168

Closed
Roderick-cc opened this issue Dec 1, 2020 · 18 comments · Fixed by #13983
Closed

两个页面不能共用一个公共组件 #8168

Roderick-cc opened this issue Dec 1, 2020 · 18 comments · Fixed by #13983
Labels
F-react Framework - React question Further information is requested T-weapp Target - 编译到微信小程序 V-3 Version - 3.x
Milestone

Comments

@Roderick-cc
Copy link

相关平台

微信小程序

复现仓库

https://github.com/shide-L/taro
小程序基础库: 2.14.0
使用框架: React

复现步骤

都是微信小程序下

  1. 2个页面 pageA,pageB,都使用同一个组件的话,另外一个pageB页面会非正常显示,scss没有加载
  2. demo部分的页面都引入同一个组件,非正常显示了,只要注释其中一个即可

期望结果

能实现组件跨页面复用

实际结果

不能复用,非正常显示或者是打包的时候没有把sacc中的样式

环境信息

 Taro CLI 3.0.13 environment info:
    System:
      OS: macOS 10.14.5
      Shell: 5.3 - /bin/zsh
    Binaries:
      Node: 10.16.3 - /usr/local/bin/node
      Yarn: 1.19.1 - /usr/local/bin/yarn
      npm: 6.14.8 - /usr/local/bin/npm
    npmPackages:
      @tarojs/components: 3.0.13 => 3.0.13
      @tarojs/mini-runner: 3.0.13 => 3.0.13
      @tarojs/react: 3.0.13 => 3.0.13
      @tarojs/runtime: 3.0.13 => 3.0.13
      @tarojs/taro: 3.0.13 => 3.0.13
      @tarojs/webpack-runner: 3.0.13 => 3.0.13
      babel-preset-taro: 3.0.13 => 3.0.13
      eslint-config-taro: 3.0.13 => 3.0.13
      react: ^16.10.0 => 16.14.0
      taro-ui: ^3.0.0-alpha.3 => 3.0.0-alpha.3
    npmGlobalPackages:
      typescript: 3.6.4
@taro-bot2 taro-bot2 bot added F-react Framework - React T-weapp Target - 编译到微信小程序 V-3 Version - 3.x labels Dec 1, 2020
@Chen-jj Chen-jj added this to the 3.0.18 milestone Dec 2, 2020
@myxmxy1234
Copy link

同样的问题, 但是我是两个页面元素都不显示, 变成空白页面了 taro3.0.17

@Chen-jj
Copy link
Contributor

Chen-jj commented Dec 3, 2020

@shide-L @myxmxy1234 使用 demo 在 3.0.17 中一开始复现了,后续不断修改若干次代码后突然好了,然后把代码恢复最初,再没有复现了,可以试试重新编译,或重启开发者工具试试。

image
image

截图只是把这两处注释取消后运行得出:

image

@Chen-jj Chen-jj removed this from the 3.0.18 milestone Dec 3, 2020
@Chen-jj Chen-jj added the question Further information is requested label Dec 3, 2020
@leeenx
Copy link
Contributor

leeenx commented Dec 12, 2020

@Chen-jj , @shide-L 我今天也遇到这个问题的。然后分析了一下:

  1. 单页面引用组件时,组件的样式会直接被写入到页面的 wxss 中;
  2. 多页面引用组件时,组件的样式会被抽成公共样式并被放在 common.wxss 中;

然后出现「多页面引用同一组件后,组件样式失效」的原因是「common.wxss」这个文件并不是微信小程序的「公共样式」!!!!微信小程序的公共样式是「app.wxss」。

然后这里的问题来了,为什么 Taro 要把公共样式放在「common.wxss」上,而不是「app.wxss」呢?
这个只能找「Taro之父」聊聊了。

说一下解决怎么解决这个问题的方法其实很简单:在 src 下创建 app.scss ,然后在 app.tsx/app.jsx 中引用这个文件就好了,如下:

// app.jsx
import './app.scss';
// app.scss
.global-app {};

结论与建议

这个问题可能跟开发的习惯有关,有些开发会有引入公共样式的习惯,有些开发没有。如果没有引用公共样式的话,又有代码洁癖的人会把 app.jsx 上引入 的 「import './app.scss」删除,然后问题就会出现。Taro 是在编译后在「app.wxss」用「@import './common.wxss」引入。但是如果我们在 app.jsx 中没有「import './index.scss」,Taro 在编译后也不会生成「app.wxss」,结果就是「common.wxss」也没有被引入了。

建议 Taro 默认都生成一个「app.wxss」避免类似问题

@maroon1
Copy link

maroon1 commented Jan 6, 2022

@Chen-jj , @shide-L 我今天也遇到这个问题的。然后分析了一下:

  1. 单页面引用组件时,组件的样式会直接被写入到页面的 wxss 中;
  2. 多页面引用组件时,组件的样式会被抽成公共样式并被放在 common.wxss 中;

然后出现「多页面引用同一组件后,组件样式失效」的原因是「common.wxss」这个文件并不是微信小程序的「公共样式」!!!!微信小程序的公共样式是「app.wxss」。

然后这里的问题来了,为什么 Taro 要把公共样式放在「common.wxss」上,而不是「app.wxss」呢? 这个只能找「Taro之父」聊聊了。

说一下解决怎么解决这个问题的方法其实很简单:在 src 下创建 app.scss ,然后在 app.tsx/app.jsx 中引用这个文件就好了,如下:

// app.jsx
import './app.scss';
// app.scss
.global-app {};

结论与建议

这个问题可能跟开发的习惯有关,有些开发会有引入公共样式的习惯,有些开发没有。如果没有引用公共样式的话,又有代码洁癖的人会把 app.jsx 上引入 的 「import './app.scss」删除,然后问题就会出现。Taro 是在编译后在「app.wxss」用「@import './common.wxss」引入。但是如果我们在 app.jsx 中没有「import './index.scss」,Taro 在编译后也不会生成「app.wxss」,结果就是「common.wxss」也没有被引入了。

建议 Taro 默认都生成一个「app.wxss」避免类似问题

找了2天样式失效的问题,终于找到了,太坑了
感谢🙏

@lxsunbin
Copy link

lxsunbin commented Feb 8, 2022

@Chen-jj , @shide-L 我今天也遇到这个问题的。然后分析了一下:

  1. 单页面引用组件时,组件的样式会直接被写入到页面的 wxss 中;
  2. 多页面引用组件时,组件的样式会被抽成公共样式并被放在 common.wxss 中;

然后出现「多页面引用同一组件后,组件样式失效」的原因是「common.wxss」这个文件并不是微信小程序的「公共样式」!!!!微信小程序的公共样式是「app.wxss」。

然后这里的问题来了,为什么 Taro 要把公共样式放在「common.wxss」上,而不是「app.wxss」呢? 这个只能找「Taro之父」聊聊了。

说一下解决怎么解决这个问题的方法其实很简单:在 src 下创建 app.scss ,然后在 app.tsx/app.jsx 中引用这个文件就好了,如下:

// app.jsx
import './app.scss';
// app.scss
.global-app {};

结论与建议

这个问题可能跟开发的习惯有关,有些开发会有引入公共样式的习惯,有些开发没有。如果没有引用公共样式的话,又有代码洁癖的人会把 app.jsx 上引入 的 「import './app.scss」删除,然后问题就会出现。Taro 是在编译后在「app.wxss」用「@import './common.wxss」引入。但是如果我们在 app.jsx 中没有「import './index.scss」,Taro 在编译后也不会生成「app.wxss」,结果就是「common.wxss」也没有被引入了。

建议 Taro 默认都生成一个「app.wxss」避免类似问题

使用css modules如何操作呢,这种方法还是不奏效。。

@lxsunbin
Copy link

lxsunbin commented Feb 8, 2022

@maroon1 请问一下使用css module如何处理这种情况呢?

@maroon1
Copy link

maroon1 commented Feb 9, 2022

@lxsunbin 我使用的是 CSS in JS 方案,所以不确定 CSS Module 方案是否有什么不一样,不过请确保代码中按以下方法做了

在 src 下创建 app.scss ,然后在 app.tsx/app.jsx 中引用这个文件

可以看看代码生成结果中是否正确引用了 common.wxss 以确定我们遇到的是同样问题

@lxsunbin
Copy link

lxsunbin commented Feb 9, 2022

@lxsunbin 我使用的是 CSS in JS 方案,所以不确定 CSS Module 方案是否有什么不一样,不过请确保代码中按以下方法做了

在 src 下创建 app.scss ,然后在 app.tsx/app.jsx 中引用这个文件

可以看看代码生成结果中是否正确引用了 common.wxss 以确定我们遇到的是同样问题

以确定这些都正常,就是样式没有生效。。

@maroon1
Copy link

maroon1 commented Feb 9, 2022

@lxsunbin 最好可以提供一个最小的可复现的代码

@xiaotianmei
Copy link

我这里遇到Taro混编到支付宝小程序中,多个页面不能用同一个组件的问题。各位大佬有解决吗?

@1oo1
Copy link

1oo1 commented Mar 16, 2022

在原生支付宝小程序项目里混编时也遇到了相同的问题。taro 3.4.2

我们的解决方案是在支付宝项目的 app.acss 里引入 taro 的 app.acss

@import "taro/app.acss"

@lxsunbin
Copy link

这个官方是不是可以修复一下@Chen-jj

@JoshYuJump
Copy link

没有使用 common 的方式,只是正常将一个 component 被 2 个 page 引用,就空白了。

@ranmeizi
Copy link

ranmeizi commented Sep 5, 2022

写了一个plugin暂时程序添加一下引用,对小程序插件开发影响很大啊,插件根本没有app.wxss- -

const { ConcatSource } = require('webpack-sources')
const Regexp = /(?<=plugin\/(components|pages))\/.+\.wxss/g

class WxssImportPlugin {
  apply(compiler) {
    compiler.hooks.emit.tapAsync(
      'WxssImportPlugin',
      (compilation, callback) => {
        // Do something async...
        // 寻找 plugin/page 文件下 的wxss文件
        for (let [name, assets] of Object.entries(compilation.assets)) {
          if (Regexp.test(name)) {
            // 找路径下有几个/
            const times = name.split('/').length - 2
            // 创建首行引用语句 @import '../../common.wxss'
            const firstLine = `@import '${Array(times).fill('../').join('') + 'common.wxss'}';\n`
            compilation.assets[name] = new ConcatSource(firstLine + assets.source())
          }
        }

        callback()
      }
    );
  }
}

module.exports = WxssImportPlugin

@Linjovi
Copy link

Linjovi commented Feb 20, 2023

同样的问题, 但是我是两个页面元素都不显示, 变成空白页面了 taro3.0.17

同样的问题,请问有解决方案了嘛

Chen-jj added a commit that referenced this issue Jun 8, 2023
1.  buildNativeComp 模式下,为各组件自动引入 common 公共样式
2. 当开发者没有全局样式文件时,仍能正确引入 common 公共样式

---------

Co-authored-by: BarryYang <[email protected]>
@Chen-jj Chen-jj added this to the 3.6.8 milestone Jun 8, 2023
@Chen-jj
Copy link
Contributor

Chen-jj commented Jun 8, 2023

Taro v3.6.8 修复:

  1. buildNativeComp 模式下,为各组件自动引入 common 公共样式
  2. 当开发者没有全局样式文件时,仍能正确引入 common 公共样式

@Chen-jj Chen-jj closed this as completed Jun 8, 2023
@github-project-automation github-project-automation bot moved this from Todo to Done in Mini Program Jun 8, 2023
xuanzebin pushed a commit that referenced this issue Jun 8, 2023
1.  buildNativeComp 模式下,为各组件自动引入 common 公共样式
2. 当开发者没有全局样式文件时,仍能正确引入 common 公共样式

---------

Co-authored-by: BarryYang <[email protected]>
@forsakesoul
Copy link

没有使用 common 的方式,只是正常将一个 component 被 2 个 page 引用,就空白了。

+1 解决了吗

@forsakesoul
Copy link

没有使用 common 的方式,只是正常将一个 component 被 2 个 page 引用,就空白了。

已解决。我使用的 less 构建样式表,组件内使用 xxx.less 顶部使用了 @import (once) 'xxx.less' 去掉 once 就可以正常加载了。虽然不知道原因是什么

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
F-react Framework - React question Further information is requested T-weapp Target - 编译到微信小程序 V-3 Version - 3.x
Projects
Archived in project
Development

Successfully merging a pull request may close this issue.