自学react有一段时间了,官网文档基础的看了一遍,然后便把之前公司做的一个vue项目用react搭建了下,顺便整理下一些知识点。

项目大概效果:

一、利用create-react-app搭建项目

1、全局安装create-react-app,执行:npm install -g create-react-app 命令进行安装

2、进入要安装项目的文件夹,执行:npx create-react-app my-app 创建一个my-app项目

3、进入项目cd my-app,执行:npm start 编译启动项目即可

二、引入公用的css和脚本(rem.js移动端适配用)

一开始我是直接在src文件夹下新建了个assets文件夹,用来放置各种资源文件,然后直接在public文件下的index.html文件中直接用link和script引入css和脚本,但是引入脚本却报错了(Uncaught SyntaxError: Unexpected token < )百度了下也没明白是什么原因,然后解决办法就是:把assets文件夹放到和index.html同级目录下再引入就可以了。

搭建页面(以首页为例)

1、在src文件夹下新建assets(放置资源文件)、component(放置公用的组件)、pages(放置页面)文件夹。

2、创建页面及对应的样式文件,并通过import '路径',直接引入,然后ClassName=“类名”来引用。

3、创建组件:可以通过es5原生方式React.createClass定义的组件,或者 es6形式的extends React.Component定义的组件(需要手动绑定this),这边采用后者来创建

//es5
const MyComponent=React.createClass({
        render:function () {
            return <h1>mycomponent</h1>
        }
    })



//es6
class MyConponent extends React.Component{
        constructor(props){
            super(props);
        }
        render() {
            return (
                <h1>mycomponent</h1>
            );
        }
    }

四、遇到的几个问题如下:

(1)import直接引入css样式的话,会导致css样式成为全局样式,容易产生类名冲突,样式互相覆盖。

解决方法:把css文件命名成xxx.module.css文件,然后通过import styles from ‘路径’ 引入,再通过styles.xxx来引用对应的类名,对于main-box之类的类名可通过styles['main-box']来引用,但是并不是很方便,所以可以使用驼峰法mainBox来命名类

import styles from './home.module.css'

<div className={styles['user-box']+' flex-h flex-hsb'}>
					<div className="flex-h flex-vc">
						<img className={styles.photo} src={require('../../assets/images/default.png')} />
						<span className={styles.user}>{this.state.username}</span>
					</div>
					<span className={styles.signin}>签到</span>
				</div>

(2)如何使用swiper轮播

解决方法:执行:npm install swiper --save 安装依赖包;然后在要使用的页面上导入对应的css文件和js文件:

import Swiper from 'swiper/dist/js/swiper.js'
import 'swiper/dist/css/swiper.min.css'

接下来就是和平时使用swiper是一样的了,html:

<div className="banner swiper-container">
				    <div className="swiper-wrapper">
				        <div className="swiper-slide"><img className="banner-img" src={require('../../assets/images/home/banner1.jpg')} /></div>
				        <div className="swiper-slide"><img className="banner-img" src={require('../../assets/images/home/banner2.jpg')} /></div>
				        <div className="swiper-slide"><img className="banner-img" src={require('../../assets/images/home/banner3.jpg')} /></div>
				    </div>
				    <div className="swiper-pagination"></div>
				</div>

初始化(在组件生命周期componentDidMount里面调用初始化):

initSwiper(){
		let banner = new Swiper ('.banner', {
		    loop: true,  //循环
		    slidesPerView: "auto",
            centeredSlides:true,
		    autoplay: {   //滑动后继续播放(不写官方默认暂停)
		        disableOnInteraction: false,
		    },
		    pagination: {  //分页器
		        el: '.swiper-pagination'
		    }
		})
	}

(3)图片的引入

解决方法:a、导入图片路径:

import Img from "./images/1.png"
<img src={Img} alt=""/>

b、直接获取图片路径:

<img src={require("./images/1.png")} alt=""/>

c、作为背景图片使用,可以直接写在css文件上或者如下

style={{background:`url(${require("./images/1.png")})` }}

首页具体代码如下:

/*首页*/
import React from 'react'
import Swiper from 'swiper/js/swiper.js'
import 'swiper/css/swiper.min.css'
import styles from './home.module.css'

import './homeSwiper.css'

import Tabbar from '../../components/tabbar/tabbar'

import activity_img from '../../assets/images/home/home_activity.png'
import menu_icon1 from '../../assets/images/home/menu_icon1.png'
import menu_icon2 from '../../assets/images/home/menu_icon2.png'
import menu_icon3 from '../../assets/images/home/menu_icon3.png'
import menu_icon4 from '../../assets/images/home/menu_icon4.png'

class Home extends React.Component{
	constructor(props){
		super(props)
		this.state = {
			username: 'Helen',
			menu: [{ 
				id: 0,
				title: '资讯快递',
				icon: menu_icon1,
				descript: '了解行业动态'
			},
			{
				id: 1,
				title: '财经要闻',
				icon: menu_icon2,
				descript: '最新财经资讯'
			},
			{
				id: 2,
				title: '新手引导',
				icon: menu_icon3,
				descript: '轻松玩转币赚'
			},
			{
				id: 3,
				title: '了解区块链',
				icon: menu_icon4,
				descript: '全球数字经济'
			}],
			notice: [1,1,1,1,1,1,1,1,1],
			usdt: []
		}
		this.initSwiper = this.initSwiper.bind(this)
	}
	
	initSwiper(){
		let banner = new Swiper ('.banner', {
		    loop: true,  //循环
		    slidesPerView: "auto",
            centeredSlides:true,
		    autoplay: {   //滑动后继续播放(不写官方默认暂停)
		        disableOnInteraction: false,
		    },
		    pagination: {  //分页器
		        el: '.swiper-pagination'
		    }
		})
	}
	
	initNoticeSwiper(){
		let banner = new Swiper ('.notice-swiper', {
		    loop: true,  //循环
		    direction : 'vertical',   
			observer:true,//修改swiper自己或子元素时,自动初始化swiper
			observeParents:true,//修改swiper的父元素时,自动初始化swiper
		    autoplay: {   //滑动后继续播放(不写官方默认暂停)
		        disableOnInteraction: false,
		    },
		})
	}
	
	getUsdtData(usdt){
		let send_data = {"event":"subscription","data":"market.price."+usdt}
		let that = this
		this.sendMsg(send_data,ev=>{
			//console.log(JSON.parse(ev.data),'订阅数字货币最新价格')
			let data = JSON.parse(ev.data);
			if(data.currency === 'BTCUSDT')
				that.state.usdt[0] = data.data
			else if(data.currency === 'ETHUSDT')
				that.state.usdt[1] = data.data
			else if(data.currency === 'LTCUSDT'){
				that.state.usdt[2] = data.data
			}
					
			if(usdt==='stop')
				return false
			that.setState({
				usdt: that.state.usdt
			})
		})
	}
	
	componentDidMount(){
		this.initSwiper()
		this.initNoticeSwiper()
		this.getUsdtData('all')
	}
	
	componentWillUnmount(){
		this.getUsdtData('stop')
	}

	render(){
		const up_color = styles['color-05AC8B'],down_color = styles['color-D94F65'];
		const is_up1 = (this.state.usdt[0]&&this.state.usdt[0].rpt.toString().indexOf('-')!=-1)?down_color:up_color;
		const is_up2 = (this.state.usdt[1]&&this.state.usdt[1].rpt.toString().indexOf('-')!=-1)?down_color:up_color;
		const is_up3 = (this.state.usdt[2]&&this.state.usdt[2].rpt.toString().indexOf('-')!=-1)?down_color:up_color;
		
		return (
			<div className={styles['home-wrap']}>
				<div className={styles['user-box']+' flex-h flex-hsb'}>
					<div className="flex-h flex-vc">
						<img className={styles.photo} src={require('../../assets/images/default.png')} />
						<span className={styles.user}>{this.state.username}</span>
					</div>
					<span className={styles.signin}>签到</span>
				</div>
				
				<div className="banner swiper-container">
				    <div className="swiper-wrapper">
				        <div className="swiper-slide"><img className="banner-img" src={require('../../assets/images/home/banner1.jpg')} /></div>
				        <div className="swiper-slide"><img className="banner-img" src={require('../../assets/images/home/banner2.jpg')} /></div>
				        <div className="swiper-slide"><img className="banner-img" src={require('../../assets/images/home/banner3.jpg')} /></div>
				    </div>
				    <div className="swiper-pagination"></div>
				</div>
				
				<div className={styles['notice-box']+' flex-h'}>
					<i className={styles['horn-icon']}></i>
					<div className={styles['notice-swiper']+' notice-swiper swiper-container swiper-no-swiping'}>
						<div className="swiper-wrapper">
							{this.state.notice.map((item,index)=>{
								return <div className="swiper-slide" key={index}><p>全球币交易全新升级,等你来体验!---{index+100}</p></div>
							})}
					    </div>
					</div>
				</div>
				
				<div className={styles['usdt-box']+' flex-h'}>
					<div className={styles['usdt-item']}>
						<p className={styles['color-fff']}>BTC/USDT</p>
						<p className={styles['font-32']+' '+is_up1}>{this.state.usdt[0]?this.state.usdt[0].p.toFixed(2):'1221.12'}</p>
						<p className={is_up1}>{this.state.usdt[0]?(this.state.usdt[0].rpt*100).toFixed(2):'0.26'}%</p>
						<p>¥{this.state.usdt[0]?this.state.usdt[0].pr.toFixed(2):'223.45'}</p>
					</div>
					<div className={styles['usdt-item']}>
						<p className={styles['color-fff']}>ETH/USDT</p>
						<p className={styles['font-32']+' '+ is_up2}>{this.state.usdt[1]?this.state.usdt[1].p.toFixed(2):'1115.22'}</p>
						<p className={is_up2}>{this.state.usdt[1]?(this.state.usdt[1].rpt*100).toFixed(2):'-0.12'}%</p>
						<p>¥{this.state.usdt[1]?this.state.usdt[1].pr.toFixed(2):'3212.11'}</p>
					</div>
					<div className={styles['usdt-item']}>
						<p className={styles['color-fff']}>LTC/USDT</p>
						<p className={styles['font-32']+' '+is_up3}>{this.state.usdt[2]?this.state.usdt[2].p.toFixed(2):'2201.13'}</p>
						<p className={is_up3}>{this.state.usdt[2]?(this.state.usdt[2].rpt*100).toFixed(2):'0.12'}%</p>
						<p>¥{this.state.usdt[2]?this.state.usdt[2].pr.toFixed(2):'323.11'}</p>
					</div>
				</div>			
				<div className={styles['activity']}><img className="wh100" src={activity_img} /></div>
				<div className={styles['notice-box']+ ' flex-h '+styles['border-none']}>
					<i className={styles['horn-icon']+' '+styles['recharge-text']}></i>
					<div className={styles['notice-swiper']+' notice-swiper swiper-container swiper-no-swiping '+styles['recharge-swiper']}>
						<div className="swiper-wrapper">
							{this.state.notice.map((item,index)=>{
								return <div className="swiper-slide" key={index}><p>相见不如怀恋 成功充值2000元---{index+10}</p></div>
							})}
					    </div>
					</div>
				</div>
				
				<div className={styles['menu-box']+' flex-h'}>
					{
						this.state.menu.map((item,index)=>{
							return <div className={styles['menu-item']+' flex-h flex-vc'} key={item.id}>
										<img className={styles['menu-icon']} src={item.icon} />
										<div>
											<p className={styles['menu-title']}>{item.title}</p>
											<p>{item.descript}</p>
										</div>
									</div>
						})
					}
				</div>
				<Tabbar />
			</div>
		)
	}
}

export default Home


.home-wrap{color: #fff; background-color: #0C1537;}
.user-box{padding: .4rem;}
.signin{
	padding: 0 .36rem;
	height: .6rem;
	line-height: .6rem;
	background-color: #3975F9;
	font-size: .28rem;
	border-radius: 27px;
}
.user{position: relative;font-size: .32rem; margin-left: .28rem;}
.user:before{
	position: absolute;
	right: -18px;
	top: 8px;
	content: '';
	width: 0;
	height: 0;
	border-width: 6px;
	border-style: solid;
	border-color: #fff transparent transparent transparent;
}
.photo{
	width: .65rem;
	height: .65rem;
	border: 2px solid #fff;
	border-radius: 50%;
}

.notice-box{
	margin: 0 .31rem;
	padding: .28rem 0;
	border-bottom: 1px solid #353F61;
}
.horn-icon{
	width: .34rem;
	height: .3rem;
	background-image: url(../../assets/images/home/icon_horn.png);
	background-repeat: no-repeat;
	background-size: 100%;
	margin-right: .28rem;
}
.notice-swiper{
	width: 90%;
	font-size: .24rem;
	color: #fff;
	height: .3rem;
	line-height: .3rem;
}
.usdt-box{
	padding-top: .5rem;
	padding-bottom: .5rem;
	font-size: .24rem;
	color: #69748D;
}
.usdt-item{
	width: 33.33%;
	text-align: center;
}
.activity{margin: 0 .2rem; height: 1.56rem;}
.recharge-text{
	width: 1.1rem;
	height: .27rem;
	background-image: url(../../assets/images/home/recharge_text.png);
}
.recharge-swiper{width: 78%;}
.border-none{border: none}
.menu-box{margin: 0 .15rem; -webkit-flex-wrap: wrap; flex-wrap: wrap;}
.menu-item{
	width: 3.4rem;
	padding: .36rem 0;
	background-color: #04092C;
	-webkit-border-radius: 8px;
	border-radius: 8px;
	font-size: .24rem;
	color: #737FA1;
	margin: 0 .1rem .2rem;
}
.menu-icon{width: .8rem; height: .8rem; margin-left: .4rem; margin-right: .3rem;}
.menu-title{font-size: .28rem; color: #fff; font-weight: bold;}

.font-32{font-size: .32rem; font-weight: bold; margin-top: .12rem;}
.color-fff{color: #fff;}
.color-05AC8B{color: #05AC8B;}
.color-D94F65{color: #D94F65;}


Logo

为开发者提供学习成长、分享交流、生态实践、资源工具等服务,帮助开发者快速成长。

更多推荐