如何在 React 中運用 CSS?
請問在ReactJs中如何有效地運用CSS?
是在component中直接插入CSS嗎? 我在github搜到了一些類庫,分別是radium和react-style,它們所用的都是inline的「CSS into JS」模式,請問這種方法好嗎? 相比傳統的與網頁分離的CSS模式,有什麼優勢和缺陷?目前Github上對這種inline CSS比較支持,我比較有疑慮。
因為CSS和網頁分離的好處是顯而易見的,可復用。 類似Radium的用法是讓React Component可復用。請前端大牛評價兩種模式的優劣。
建議 CSS in JS 寫法,雖然感覺推翻了多年的 CSS 工作進展。
主要原因還是 CSS 的全局污染。
模塊化、組件化一直是前端不斷優化追求的目標。傳統的 CSS 無法很好的進行模塊化。只能人為通過命名空間來約束這段樣式在某個模塊中,這種約束很弱的,指不定哪天來個新人不知道這個,就隨便命名產生衝突影響了其他的組件。
而 CSS in JS 的寫法,可以解決這個問題。如果有些場景實在是需要 CSS 外聯才能實現(比如 animation 的一些動畫),可以使用 Glen Maddern: Internet Pro CSS modules 來解決這個問題。最近在用styled-components: GitHub - styled-components/styled-components: Visual primitives for the component age
感覺用起來比較舒服,之前項目中使用css-module,配合各種less sass scss postcss還有全局css,也滿湊合
有一段嘗試用radium,感覺inline的寫法有局限性,動畫什麼的比較麻煩關鍵是要找到一個能和頁面設計師共同開發提高效率,學習成本不高的寫法我來寫例子吧;然後把我webpack.config.js配置信息。
react的css開發,一般採用模塊化的形式進行。一般react中css可以分為三部分,快發環境給予node.js、模塊化構建用webpack.第一:全局部分:比如base.css(用來通用的css,如:.clearfix、.mt10、.mt05之類的)。這個文件可以直接在入口文件如(index.html)中直接用&的形式直接引入第二:通用部分:比如我可以把整個webapp需要用到的按鈕樣式作為一個樣式寫到一個文件里如:common/button.css,寫法的話遵循模塊化開發的方式進行(composes);貼端代碼如下:.btn {
height: 35px;
line-height: 35px;
border-radius: 2px;
display: inline-block;
text-align: center;
user-select: none;
text-align: center;
box-sizing: border-box;
font-size: 14px;
}
.btn-primary {
composes : btn;
border: 1px solid #E0E0E0;
background-image: -webkit-linear-gradient(top, #f9f9f9, #e7e9eb);
background-repeat: repeat-x;
color: #333;
}
.btn-blue {
composes : btn;
border: 1px solid #0B62BD;
background-image: -webkit-linear-gradient(top, #0e7bef, #0d73da);
background-repeat: repeat-x;
color: #fff;
}
第二:組件內的css:比如我們寫了一個confirm的通用組件,那麼
comfirm組件的目下應該包含兩個文件comfirm.js 和 comfirm.css
在comfirm.js中用var Styles = require("./confirm.css");的形式進行引用。 在render的時候進行調用調用形式:& 寫組件完成後,比如我在一個編輯頁面中需要用到confirm組件,那麼就可以直接requre。 confirm.css如何開發呢?一般採用composes的方式進行(比如我confirm組件中有用到button,那麼就可以引用通用的button),然後可以基於composes後的進行修改,比如顏色等等。貼一段代碼如下:.btn-cancel{
composes : btn-primary from "../style/button.css";
width:100px;
margin-right: 10px;
}
.btn-confirm{
composes : btn-blue from "../style/button.css";
width:100px;
margin-left: 10px;
}
第三:就是行內樣式了,一般會用得比較少。
webpack配置信息,涉及到樣式內圖片的解析/**
* webpack 配置文件
* 配置獨立項、入口文件、輸出項信息
*/
var path = require("path");
var webpack = require("webpack");
var admin_components_dir = path.join(__dirname, "admin/script/components/");
//重定向文件
var alias= {
Login : admin_components_dir + "login/Login.js",
Layout : admin_components_dir + "layout/Layout.js",
Article : admin_components_dir + "article/Article.js",
Pager : admin_components_dir + "common/Pager/Pager.js",
Tip : admin_components_dir + "common/Tip/Tip.js",
Confirm : admin_components_dir + "common/Confirm/Confirm.js",
Select : admin_components_dir + "common/Select/Select.js",
ArticleForm : admin_components_dir + "article/ArticleForm.js",
Editor : admin_components_dir + "common/Editor/Editor.js",
CheckBox : admin_components_dir + "common/CheckBox/CheckBox.js"
};
var config = {
devtool: "inline-source-map",
entry: [
"webpack-dev-server/client?http://127.0.0.1:4000",
"webpack/hot/only-dev-server",
"./admin/script/temp.js"
],
output: {
path: path.join(__dirname, "admin/dist/"),
filename: "app.js",
publicPath: "/static/"
},
resolve: {
alias: []
},
module: {
noParse : [],
loaders: [{
test: /.jsx?$/,
loaders: ["react-hot", "babel"],
include: path.join(__dirname,"admin/script/")
},{
test: /.css$/,
exclude: [
path.resolve(__dirname, "node_modules")
],
loaders: ["style", "css?moduleslocalIdentName=[name]_[local]_[hash:base64:5]","autoprefixer?{browsers:["> 5%", "ie 9"]}"]
},{
test: /.(svg|png|jpg|jpeg|gif)$/i,
loaders: ["file", "image-webpack?bypassOnDebugoptimizationLevel=7interlaced=false"]
}
]
},
plugins: [
new webpack.HotModuleReplacementPlugin(),
new webpack.NoErrorsPlugin()
]
}
//重定向文件賦值
config.resolve.alias = alias;
module.exports = config;
webpack中有css的命名規則、css代碼自動補全(就是不用寫瀏覽器前綴了)等配置
這樣第二、第三中的css都會打包到app.js中,入口文件(如:index.html)只要用&毫無疑問是使用css-modules還有比這更好的解決方案嗎?無任何衝突,自由組合https://github.com/css-modules/css-modules
css和html分離是頁面層面的,而模塊的好處對使用第三方類庫非常重要
CSS和網頁分離的好處是顯而易見的?那要看在什麼時代。從傳統 HTML 的觀點來看,「內容」(HTML)和其渲染方式 (CSS)是可以分離的,例如同樣的文章可以被CSS渲染到不同的設備上,例如PC、手機甚至是給視覺障礙的人用的聲音設備。基於內容傳播,這樣分隔就是合理的。而今天,Web已經從相互連接的HTML變成了相互連接的 Web App。用戶看到的已經不再是整個 HTML,而是由一個一個Web組件組成的應用程序窗口。此時,CSS的全局性帶來的就不是方便,而可能是污染了。為了解決這個問題,Web Component 不得不帶來了 Shadow DOM 的新概念。React Component是適應 Web App 化的,因此很自然,inline style 的作用自然就會被加強。在需要全局 CSS 的時候,你仍然可以通過為 React Component 設置 className 屬性,來制定對應的 CSS Class。Inline style也有一些限制,只能通過 CSS 聲明(className)來實現,例如聲明偽類屬性 (a:visited)。
最近看了一篇文章,介紹了 CSS 的進化: CSS Evolution: From CSS, SASS, BEM, CSS Modules to Styled Components
這裡有各個方式的比較:styled-components/comparison
最完美的方式應該是 CSS Modules 或 styled-components 吧react就是屁事多 直接和vue一樣 js文件里支持寫style標籤 然後saas less stylus自己選。這樣多好
目前比對了幾種方案覺得最好成本最低的就是styled-components了,
前面@stevenjlho 提到的文章是styled-components作者之一寫的,非常有指導意義,我翻譯在了專欄里:https://zhuanlan.zhihu.com/p/29344146 歡迎閱讀
在項目中使用了各種寫法之後,目前採取的方案是 css-modules 和一個全局css的書寫規範(ex:BEM)組合使用,各取其所長~
uitl類型、全局類型的css放在全局
隻影響組件的、害怕污染的css放在組件內
建議使用styled-components開發,Next.js準備整合styled-component到2.0的版本,個人感覺比css module更適合用在React上
使用styled-components有以下優點:- CSS的代碼可以直接寫到jsx中,這樣就可以直接使用React的props和state。
- 不需要命名classname了,直接把CSS與Component綁定,編譯後會自動生成classname,這樣也解決了classname全局衝突的問題。
CSS Modules 用法 借鑒這種寫法。
styled-components is fucking awesome!
styled-components/styled-components
css-modules的作者https://twitter.com/glenmaddern也是styled-components的共同作者,比css-modules要方便許多。
className 不行?
react組件化了,組件復用,樣式內斂,沒必要寫全局樣式了吧
目前大部分react項目中,css是分離的。在模板html中(比如index.html)中,引入壓縮過的css文件(比如main.min.js).
jsx語法中,用className給元素添加css中對應的類名。
將react組建掛載到模板html中,聯繫就自然建立起來了。
說白了,還是以前的那一套,行為(js),結構(html),樣式(css)分離。
推薦閱讀:
※如何評價Knot.js?
※為什麼沒有人出JS版的數據結構與演算法?
※JS模塊載入器載入原理是怎麼樣的?
※HTML 標籤屬性的全稱?
※如何評價性能大幅提升的Chrome 53?
TAG:JavaScript | 前端工程師 | React |