嗨,我正在从Logitech Media服务器,标题,艺术家,歌曲等中检索数据,并且想知道如何在歌曲名称更改时更新此服务器返回的图像。
我创建了一个组件,可以愉快地接收,显示和更新所有相关的音频子控件,但是我无法获取歌曲jpg来更新歌曲标题名称。图像的src设置为state(是刷新jpg所需的logitech媒体服务器的url)
发送到audioToolBar组件时,歌曲标题会愉快地更新
标题是在switch语句中定义的,我认为通过更新将歌曲标题置于状态并在其更改时进行更新会起作用,但是我尝试执行的任何操作都会出错,提示超出setstate的最大调用深度。
下面列出的组件的缩写(不起作用)代码
我是具有React和js的新手,因此非常感谢任何帮助。
import React, { Component } from "react";
import { withStyles } from "@material-ui/core/styles";
import Grid from "@material-ui/core/Grid";
import SwitchedComponent from "./switchedComponent";
import AudioToolBar from "./audioToolBar";
class AudioLightandHeat extends Component {
state = {imgSrc :"http://192.168.1.1:9000/music/current/cover.jpg?player=Bathroom"};
getControls = ()=>{
for (let index = 0; index < this.audioControls.length; index++) {
const element = this.audioControls[index];
switch (element.name) {
case "Title":
this.titleCont = element
let songAndArtist = (this.titleCont.statesValue.textAndIcon).split("/")
this.song = songAndArtist[0]
this.setState({songTitle:this.song})
break;
case "Volume":
this.volumeCont = element;
break;
case "Mode":
this.modeCont = element;
break;
case "Track":
this.trackCont = element;
break;
case "Play Pause":
this.playCont = element;
break;
}
}
}
}
}
}
}
}
render() {
const { classes, theme } = this.props;
this.getControls()
return (
<>
{this.hasAudioControl ? (
<img src = {this.state.imgSrc} width={300} height={300} />
) : null}
</>
);
}
}
export default withStyles(styles, { withTheme: true })(AudioLightandHeat);
好,所以我已经重构了整个组件,使其看起来像这样
import React, { Component } from "react"
import { withStyles } from "@material-ui/core/styles"
import Grid from "@material-ui/core/Grid"
import AudioToolBar from "./audioToolBar"
const styles = theme => ({
grid: {
flexGrow: 1,
},
});
class AudioLightandHeat extends Component {
render() {
const { classes, theme } = this.props;
return (
<>
{console.log(" in render")}
{this.props.componentProps ? (
<Grid container className={classes.grid}>
<img src = "http://192.168.1.1:9000/music/current/cover.jpg?player=Bathroom" width={300} height={300} />
</Grid>
) :null}
{this.props.componentProps ? (
<AudioToolBar title = {this.props.componentProps.audioLightHeatControls.titleCont}
volume={this.props.componentProps.audioLightHeatControls.volumeCont}
mode={this.props.componentProps.audioLightHeatControls.modeCont}
track={this.props.componentProps.audioLightHeatControls.trackCont}
playpause={this.props.componentProps.audioLightHeatControls.playCont}
reqStateChange={this.props.componentProps.reqStateChange}
/>
) :null}
</>
)
}
}
export default withStyles(styles, { withTheme: true })(AudioLightandHeat);
在更新道具时,title,wolume,mode,track会正确跟踪所有更新,而img会。我怀疑这是因为src url不会更改,因此即使服务器上的相同地址上有新图像,浏览器也不会再次询问它。
在渲染时如何强制React调用图像。
我尝试将date.now添加到url的末尾,即src =“ http://192.168.1.1:9000/music/current/cover.jpg?player=Bathroom” + new Date()。getTime(),但随后从服务器获取404错误,我还添加了以下内容: index.html
<meta http-equiv="cache-control" content = "max-age=0">
<meta http-equiv="cache-control" content = "no-cache">
<meta http-equiv="pragma" content = "node_modules">
但这也不起作用。
任何帮助都将不胜感激。
答案 0 :(得分:0)
有关您的反应组件的更多常规建议
您的React组件的所有状态都应处于组件状态。 ({this.song
,this.titleCont
等当前不属于组件状态,但已分配给组件的实例)
这个this.setState({ songTitle: this.song })
似乎更好,但是在setState
方法中调用的函数中调用render
通常不是一个好主意。 (很容易产生这样的无限循环...)
仅渲染一次的具体原因
注意:我猜在这里。您确实应该首先重构组件。另外,在继续之前,您可能应该阅读一下React组件的生命周期。也许this可以为您提供帮助。
当前,您的render
方法在初始渲染期间将被调用一次。在此初始渲染期间,this.getControls()
将被调用一次,但可能不会触发"Title"
情况。
在此初始渲染之后,道具和状态似乎没有改变,因此组件将不会重新渲染。因此,不会再次调用render
方法和this.getControls()
,并且不会完成setState
调用。