切换列表底部的详情内容修改
非父组件通信可以用三种方式实现非父组件通信-状态提升,开发-订阅模式,context方案。具体如下实现代码如下:
1.非父组件通信-状态提升
(1)父组件
import React, { Component } from 'react'
import axios from 'axios'
import ReasonLi from './components/ReasonLi'
import ReasonDetails from './components/ReasonDetails'
import './css/index.css'
export default class app extends Component {
state = {
"titleCn": "",
"titleEn": "",
"list": [],
"info": ""
}
constructor() {
super()
axios.get("/test.json").then(res => {
this.setState({
"titleCn": res.data[0].titleCn,
"titleEn": res.data[1].titleEn,
"list": res.data[2].list
})
})
}
render() {
return (
<div className="w-warp">
<div className="business-why">
<h4 className="business-h4">{this.state.titleCn}</h4>
<h5 className="business-h5">{this.state.titleEn}</h5>
<div className='business-ul'>
{
this.state.list.map((item, index) =>
<ReasonLi key={index} {...item} onEvent={(value) =>
this.setState({
info:value
})
}></ReasonLi>
)
}
</div>
<ReasonDetails content={this.state.info} />
</div>
</div>
)
}
}
(2)子组件 列表
import React, { Component } from 'react'
import './../css/index.css'
export default class ReasonLi extends Component {
render() {
let {name,url,content}=this.props
return (
<div className='business-product' onClick={() => { this.props.onEvent(content) }}>
<div className='business-img'><img src={url} alt={name} /></div>
<h5>{name}</h5>
</div>
)
}
}
(3)子组件 详情
import React, { Component } from 'react'
import './../css/index.css'
export default class app extends Component {
render() {
let {content}=this.props
return (
<div className='business-product-details' >
{content}
</div>
)
}
}
(4)index.css
h4,h5,h6{padding:0;margin:0;}
.w-warp {
width: 1200px;
margin: 0px auto;
}
.business-why {
background: #f2f2f2;
padding: 40px 0;
margin: 50px auto;
}
.business-h4 {
text-align: center;
font-size: 40px;
color: #484848;
font-family: "黑体";
font-weight: normal;
margin-top: 20px;
}
.business-h5 {
text-align: center;
font-size: 16px;
color: #999;
font-weight: normal;
margin-bottom: 30px;
margin-top: 10px;
}
.business-h6 {
text-align: center;
font-size: 14px;
color: #999;
font-weight: normal;
margin-bottom: 10px;
line-height: 1.5em;
}
.business-ul {
display: flex;
padding-left: 40px;
padding-top: 30px;
padding-bottom: 30px;
}
.business-product {
flex: 1;
background: #fff;
margin-right: 40px;
cursor: pointer;
transition: 1s ease;
}
.business-product h5 {
color: #00ab84;
font-size: 16px;
text-align: center;
margin-top: 10px;
margin-bottom:10px;
}
.business-product-details {
background: #f2f2f2;
padding: 40px 0;
color: #333333;
font-size: 14px;
padding: 10px;
line-height: 2em;
text-indent: 2em;
}
.business-img {
width: 250px;
height: 280px;
}
.business-img img {
width: 100%;
}
.business-product:hover {
transform: scale(1.2);
opacity: 0.8;
background: #00ab84;
color: #fff;
}
.business-product:hover h5 {
color: #fff;
}
.business-product:hover p {
color: #fff;
}
(4)test.json 可以放到public公共文件夹
[
{"titleCn":"为什么选择美品多?" },
{"titleEn":"Why DO YOU CHOOSE MEIPINDUO?"},
{"list": [
{
"name": "成熟的系统工具",
"url": "https://www.meipinshu.com/images/business/bussiness-pro1.png",
"content": "美品树具备一套完整成熟的B2B2C信息化系统工具,ERP+WMS+分销系统+直播系统+业务管理系统,支持2B、2C、直播等技术,可为合作商做好销售工具的有力支持"
},
{
"name": "强大的金融支持",
"url": "https://www.meipinshu.com/images/business/bussiness-pro2.png",
"content": " 义乌美品树具备国资数亿元专项金融资金优势,可为广大合作商提供低息、高额的专项经营性资金"
},
{
"name": "品牌升级服务",
"url": "https://www.meipinshu.com/images/business/bussiness-pro3.png",
"content": " 在美品树强大的商品、市场、技术、金融支持下,可助合作商快速进行渠道巩固、商品品类丰富、商品品牌升级、自身服务品牌加强等"
},
{
"name": "一站式优选供应链",
"url": "https://www.meipinshu.com/images/business/bussiness-pro4.png",
"content": "义乌商城集团产业链强大的商业支持下,美品树具备极强的商品供应链优势,可一站式供应日百系列,满足合作商家日百品类补充"
}
]
}
]
2. 非父组件通信-订阅发布模式
import React, { Component } from 'react'
import axios from 'axios'
import './css/index.css'
//调度中心
var bus = {
list:[],
//订阅
subscribe(callback) {
this.list.push(callback)
},
//发布
publish(text) {
//遍历所以的list,将回调函数执行
this.list.forEach(callback => {
callback &&callback(text)
})
}
}
class ReasonLi extends Component {
render() {
let {name,url,content}=this.props
return (
<div className='business-product' onClick={() => { bus.publish(content); }}>
<div className='business-img'><img src={url} alt={name} /></div>
<h5>{name}</h5>
</div>
)
}
}
class ReasonDetails extends Component {
state = {
info:""
}
constructor() {
super()
bus.subscribe((value) => {
this.setState({info:value})
})
}
render() {
let {content}=this.props
return (
<div className='business-product-details' >
{this.state.info}
</div>
)
}
}
export default class app extends Component {
state = {
"titleCn": "",
"titleEn": "",
"list": []
}
constructor() {
super()
axios.get("/test.json").then(res => {
this.setState({
"titleCn": res.data[0].titleCn,
"titleEn": res.data[1].titleEn,
"list": res.data[2].list
})
})
}
render() {
return (
<div className="w-warp">
<div className="business-why">
<h4 className="business-h4">{this.state.titleCn}</h4>
<h5 className="business-h5">{this.state.titleEn}</h5>
<div className='business-ul'>
{
this.state.list.map((item, index) =>
<ReasonLi key={index} {...item} ></ReasonLi>
)
}
</div>
<ReasonDetails />
</div>
</div>
)
}
}
3. 非父组件通信-context方案也叫跨组件通信
import React, { Component } from 'react'
import axios from 'axios'
import './css/index.css'
const GlobalContext = React.createContext()
export default class app extends Component {
state = {
"list": [],
'info':""
}
constructor() {
super()
axios.get("/test.json").then(res => {
this.setState({
"list": res.data[2].list
})
})
}
render() {
return (
<GlobalContext.Provider value={{
info: this.state.info, changeInfo: (value) => {
this.setState({
info:value
})
}
}}>
<div className="w-warp">
<div className="business-why">
<div className='business-ul'>
{
this.state.list.map((item, index) =>
<ReasonLi key={index} {...item} ></ReasonLi>
)
}
</div>
<ReasonDetails />
</div>
</div>
</GlobalContext.Provider>
)
}
}
class ReasonLi extends Component {
render() {
let { name, url, content } = this.props
return (
<GlobalContext.Consumer>
{
(value) => {
return <div className="business-product" onClick={() => { value.changeInfo(content); }}>
<div className='business-img'><img src={url} alt={name} /></div>
<h5>{name}</h5>
</div>
}
}
</GlobalContext.Consumer>
)
}
}
class ReasonDetails extends Component {
constructor() {
super()
}
render() {
let { content } = this.props
return (
<GlobalContext.Consumer>
{
(value) => <div className='business-product-details' >
{value.info}
</div>
}
</GlobalContext.Consumer>
)
}
}
网友评论