简书Header组件开发(styled-components管理样式)

新建react项目(create-react-app脚手架工具)

可以参考:react官网-“get started”-Create React App的例子

根据文档,安装create-react-app脚手架工具、创建react项目jianshu

1
2
npm install -g create-react-app
create-react-app jianshu

create-react-app这个脚手架工具会帮我们自动安装react的环境,并构建一个react项目
新建成功

运行react项目

启动react项目:

1
2
cd jianshu
npm start

初始化完毕,弹出http://localhost:3000/
初始化完毕

删除暂时用不到的文件

留下他们即可:
留下他们即可

app.js:

1
2
3
4
5
6
7
8
9
10
11
12
13
import React, { Component } from 'react'

class App extends Component {
render(){
return (
<div>
hi
</div>
);
}
}

export default App;

index.js:

1
2
3
4
5
6
import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import App from './App';

ReactDOM.render(<App />, document.getElementById('root'));

styled-components管理CSS样式

在react项目中,只要我们在index.js中引入一次css,则所有组件中都不需要引入css则可使用样式。(例子在下方“使用index.css的效果”中)
这就会造成混乱,所以建议使用第三方模块Styled-Components对样式进行管理。

(不建议)使用index.css的效果

index.css中写样式

1
2
3
.dell{
background-color: red;
}

index.js中引入index.css:

1
import './index.css';

app.js:

1
2
3
<div className="dell">
hi
</div>

可以看到在index.js中引入的样式在全局组件中都能使用:
效果
这就会造成混乱,所以建议使用第三方模块Styled-Components对样式进行管理。

安装styled-components

在项目中安装Styled-Components:

1
yarn add styled-components

使用styled-components

引入样式

  1. index.css重命名为style.js,此时样式时放在js文件中的。
  2. index.js中引入style.js

书写样式

  • 全局布局:使用**’styled-components’的createGlobalStyle生成一个带样式的标签(组件)。**
  • 局部样式:使用**”styled-components”的styled生成带样式的标签(组件)**。【例子在下方“设置Header组件的样式(styled局部样式组件)”中】
  • 注意:全局样式组件和局部样式组件的使用有些不同,全局是自闭和标签<xxx />。而局部可以当作普通组件使用,比如:通过**styled.div生成的就是带样式的div组件,使用方法和div一样

全局样式(createGlobalStyle)

createGlobalStyle官方文档

The injectGlobal API was removed and replaced by createGlobalStyle in styled-components v4.
以前使用injectGlobal,但用官方的话来讲,就是这个API 从现在开始废除了,换成 createGlobalStyle (新的API) ,作为一个样式组件出现,按照样式组件思想,以一个标签形式被引入
(也就是说使用createGlobalStyle来生成一个带有样式的标签(组件)

1.在style.js中,用createGlobalStyle定义全局样式

1
2
3
4
5
6
7
8
import { createGlobalStyle } from 'styled-components'

// 样式组件Globalstyle
export const Globalstyle = createGlobalStyle` 
body{
  margin: 0;
  padding: 0
 }`

然后引入样式组件Globalstyle即可。

  1. App.js中导入样式,以样式组件的方式当作标签引入
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    import React, { Component,Fragment } from 'react';
    import { Globalstyle } from './style';

    class App extends Component {
    render() {
    return (
    <Fragment>
    <Globalstyle />
    </Fragment>
    );
    }
    }

    export default App;

效果


Reset.css统一默认样式

  • 做pc项目要在所有浏览器上保证默认样式的统一,我们借助Reset.css。
  • 每个浏览器对元素的默认样式时不同的,为了保证我们的项目在不同浏览器上的效果是一样的,我们需要使用Reset.css。
  • 使用Reset.css后,元素每个浏览器上的默认样式基本保持一致。

流程:
百度搜索Reset.css-进入CSS Tools:Resct CSS-复制代码-粘贴到style.js中的全局样式Globalstyle中

style.js:

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
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
import { createGlobalStyle } from 'styled-components'

export const Globalstyle = createGlobalStyle`
html, body, div, span, applet, object, iframe,
h1, h2, h3, h4, h5, h6, p, blockquote, pre,
a, abbr, acronym, address, big, cite, code,
del, dfn, em, img, ins, kbd, q, s, samp,
small, strike, strong, sub, sup, tt, var,
b, u, i, center,
dl, dt, dd, ol, ul, li,
fieldset, form, label, legend,
table, caption, tbody, tfoot, thead, tr, th, td,
article, aside, canvas, details, embed,
figure, figcaption, footer, header, hgroup,
menu, nav, output, ruby, section, summary,
time, mark, audio, video {
margin: 0;
padding: 0;
border: 0;
font-size: 100%;
font: inherit;
vertical-align: baseline;
}
/* HTML5 display-role reset for older browsers */
article, aside, details, figcaption, figure,
footer, header, hgroup, menu, nav, section {
display: block;
}
body {
line-height: 1;
}
ol, ul {
list-style: none;
}
blockquote, q {
quotes: none;
}
blockquote:before, blockquote:after,
q:before, q:after {
content: '';
content: none;
}
table {
border-collapse: collapse;
border-spacing: 0;
};
`

统一成功:
统一成功


使用styled-components完成Header组件布局(1)

  • 在项目中新建common文件夹-》再新建header文件夹,在文件夹中新建index.js放置Header组件。(注意:自定义组件 首字母大写)
  • 在src目录下的App.js中引入header组件并放到App组件中。
  • 在header文件夹下新建style.js用于存放Header组件的样式。

新建Header组件

common-header-index.js放置Header组件:

1
2
3
4
5
6
7
8
9
10
11
import React, { Component } from 'react'

class Header extends Component{
render(){
return(
<div>你好呀</div>
)
}
}

export default Header;

src-App.js引入header组件并放到App组件中:

1
2
3
4
5
6
7
8
9
10
11
12
import React, { Component } from 'react'
import Header from "./common/header"

class App extends Component {
render() {
return (
<Header />
);
}
}

export default App;

成功渲染Header组件

设置Header组件的样式

局部样式组件(styled-components的styled)

  • 全局布局:**’styled-components’的createGlobalStyle生成一个带样式的标签(组件)。**
  • 局部样式:**”styled-components”的styled生成带样式的标签(组件)**。
  • 注意:全局样式组件和局部样式组件的使用有些不同,全局是自闭和标签<xxx />。而局部可以当作普通组件使用,比如:通过**styled.div生成的就是带样式的div组件,使用方法和div一样

common-header-style.js存放Header组件的局部样式组件HeaderWrapper(相当于带样式的div组件)(记得输出):

1
2
3
4
5
6
7
import styled from "styled-components";

// 局部样式组件HeaderWrapper(带样式的div组件)
export const HeaderWrapper = styled.div`
height:56px;
background:red;
`

commmon-header-index.js中直接调用HeaderWrapper组件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
import React, { Component } from 'react'
import {
HeaderWrapper,
}from "./style";


class Header extends Component{
render(){
return(
<HeaderWrapper>你好呀</HeaderWrapper>
)
}
}

export default Header;

效果


模仿简书官网

我们可以到简书官网去看Header中各个元素的宽高,将我们需要的Logo图片保存到src下新建的statics文件夹中
简书官网

使用局部样式定义图片组件

错误示范

将图片放到局部样式组件中进行定义,特别注意:不能在样式属性值中通过url(../../statics/logo)去找图片,因为项目打包的时候样式是作为字符串被识别的,并不会去找这个图片:
错误示范
可以看到到了页面上还向上去找,可是localhost地址向上根本找不到图片。

正确示范
  1. 定义带样式的图片组件先引入图片LogoPic,再在url中通过${LogoPic}使用LogoPic。(相关语法可以参考ES6模板字符串
    • 注意:这里的图片其实是可以点击的,所以创建的是一个a标签(styled.a
  2. 使用图片组件,显示图片

注意:设置HeaderWrapper相对定位,使其脱离文档流,悬浮在页面上。再将其中的子元素设置为绝对定位时(子绝父相),子元素就会相对HeaderWrapper进行定位,方便操作。

common-header-style.js定义带样式的图片组件:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
import styled from "styled-components";
import LogoPic from "../../statics/logo.png";

export const HeaderWrapper = styled.div`
position:relative;
height:56px;
border-bottom:1px solid #f0f0f0;
`

export const Logo = styled.a`
position:absolute;
display:block;
top:0;
left:0;
height:56px;
width:100px;
background:url(${LogoPic});
// contain:把x轴拉满,y轴够长的话会平铺重复显示图片
background-size:contain;
`

common-header-index.js引入并使用Logo组件 显示图片:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
import React, { Component } from 'react'
import {
HeaderWrapper,
Logo
}from "./style";


class Header extends Component{
render(){
return(
<HeaderWrapper>
<Logo/>
</HeaderWrapper>
)
}
}

export default Header;

效果


图片组件(a标签)的href属性

实现功能:点击图片跳转首页。

  • 方法1:写在index.js中,调用组件时<Logo href="/" />定义href属性。
  • 方法2:写在style.js中,定义样式时使用styled.a.attrs({href:/})来定义href属性。
方法1:style.js中

common-header-style.js:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
import React, { Component } from 'react'
import {
HeaderWrapper,
Logo
} from "./style";


class Header extends Component {
render() {
return (
<HeaderWrapper>
<Logo href="/" />
</HeaderWrapper>
)
}
}

export default Header;
方法2:index.js中

common-header-index.js:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
import styled from "styled-components";
import LogoPic from "../../statics/logo.png";

export const HeaderWrapper = styled.div`
position:relative;
height:56px;
border-bottom:1px solid #f0f0f0;
`

export const Logo = styled.a.attrs({
href:"/"
})`
position:absolute;
display:block;
top:0;
left:0;
height:56px;
width:100px;
background:url(${LogoPic});
// contain:把x轴拉满,y轴够长的话会平铺重复显示图片
background-size:contain;
`

,