reactjs - 嵌套组件失去对第一个 onchange 的关注
问题描述
我有以下 3 个组件,第一个更改输入字段使其失去焦点。我试过提供输入字段和 div 键,但它没有解决我的问题。我是 React 的新手,所以我可能做错了一些基本的事情。我没有在渲染方法中创建新函数,这是 stackoverflow 中记录的大多数失去焦点问题的原因。因此,新职位的原因。
索引.tsx
import * as React from "react";
import { IQuery, Queries } from "./components/Queries/Queries";
interface IManageResponseState {
primaryQuery: IQuery;
alternateQueries: IQuery[];
}
export class ManageResponse extends React.Component<any, IManageResponseState> {
constructor(props: any) {
super(props);
this.state = {
primaryQuery: {
queryText: "This is my primary query text",
id: 0
}, alternateQueries: [{
queryText: "this is my alternate query text 1",
id: 1
},
{
queryText: "this is my alternate query text 2",
id: 2
}]
};
this.addFunc = this.addFunc.bind(this);
this.removeFunc = this.removeFunc.bind(this);
this.primaryChangedFunc = this.primaryChangedFunc.bind(this);
this.alternateChangedFunc = this.alternateChangedFunc.bind(this);
}
public addFunc(text: string) {
const newQueries = this.state.alternateQueries.filter(q => true);
newQueries.push({ id: 0, queryText: text });
this.setState({ alternateQueries: newQueries });
};
public removeFunc(index: number) {
this.setState({ alternateQueries: this.state.alternateQueries.splice(index, 1) });
console.log("Remove called:" + index);
};
public primaryChangedFunc(text: string) {
const query = {
queryText: text,
id: 0
};
this.setState({ primaryQuery: query });
console.log("changed primary called:" + text);
}
public alternateChangedFunc(index: number, text: string) {
const item = this.state.alternateQueries[index];
const newQueries = this.state.alternateQueries.filter(q => true);
newQueries[index] = {
queryText: text,
id: item.id
};
this.setState({ alternateQueries: newQueries })
console.log("changed alternate called:" + text);
}
public render() {
return (
<React.Fragment>
<Queries primaryQuery={this.state.primaryQuery} alternateQueries={this.state.alternateQueries} onAddQuery={this.addFunc} onRemoveQuery={this.removeFunc} onPrimaryChanged={this.primaryChangedFunc} onAlternateQueryChanged={this.alternateChangedFunc} />
</React.Fragment>
);
}
}
查询.tsx
import * as classnames from 'classnames';
import * as React from "react";
import { AlternateQueryItem } from "../AlternateQueryItem/AlternateQueryItem";
import './Queries.scss'
export interface IQuery {
queryText: string;
id: number;
}
export interface IQueryProps {
primaryQuery: IQuery;
alternateQueries: IQuery[];
onPrimaryChanged: (queryText: string) => void;
onAlternateQueryChanged: (index: number, queryText: string) => void;
onAddQuery: (queryText: string) => void;
onRemoveQuery: (atIndex: number) => void;
}
interface IQueryState {
primaryQueryInvalid: boolean;
}
class Queries extends React.Component<IQueryProps, IQueryState> {
constructor(props: IQueryProps) {
super(props);
this.onPrimaryQueryChanged = this.onPrimaryQueryChanged.bind(this);
this.state = { primaryQueryInvalid: false };
}
public render() {
return (
<main className="query-main-container">
<div className="primary-query-container">
<div className="form-group">
<h5 className={classnames("primary-query-header", { 'invalid': this.state.primaryQueryInvalid })}>Primary query</h5>
<div className="primary-query">
<div>{ "hello " + this.state.primaryQueryInvalid }</div>
<input type="text" value={this.props.primaryQuery.queryText} onChange={this.onPrimaryQueryChanged} className="form-control"/>
</div>
</div>
</div>
<div>
<h5 className="query-header">Query variations</h5>
<hr />
</div>
<div className="query-container">
{this.props.alternateQueries && this.props.alternateQueries.map((q, i) => this.renderQuery(q, i))}
</div>
</main>
);
}
public renderQuery(query: IQuery, key: number) {
return (
<AlternateQueryItem onChanged={this.props.onAlternateQueryChanged} query={query} key={key} index={key} />
);
}
private onPrimaryQueryChanged = (ev: React.FormEvent<HTMLInputElement>) => {
this.setState({ primaryQueryInvalid: ev.currentTarget.value === ""})
this.props.onPrimaryChanged(ev.currentTarget.value)
}
}
export { Queries };
AlternateQueryItem.tsx
import * as React from "react";
import { IQuery } from "../Queries/Queries";
export interface IAlternateQueryProps {
query: IQuery;
onChanged: (index: number, queryText: string) => void;
index: number;
}
class AlternateQueryItem extends React.Component<IAlternateQueryProps> {
constructor(props: IAlternateQueryProps) {
super(props);
this.onItemChanged = this.onItemChanged.bind(this);
}
public render() {
return (
<div className="form-group">
<div className="alternate-query">
<input type="text" value={this.props.query.queryText} onChange={this.onItemChanged} className="form-control" />
</div>
</div>
);
}
public onItemChanged = (ev: any) => {
this.props.onChanged(this.props.index, ev.currentTarget.value)
}
}
export { AlternateQueryItem };
解决方案
推荐阅读
- flutter - 在颤动中自动滚动到 ListView 的底部
- linker - 防止链接器将节定位到特定的内存区域,TASKING ARM 工具链
- node.js - 我如何使用 console.table 而不是 stderr?
- c# - ASP.NET CORE 将 Razor 视图渲染为带有控制器参数的字符串
- flutter - Flutter Firebase Cloud Messaging 在 Ios 上不显示徽章编号
- biztalk - 在发送端口中使用 WCF 自定义适配器的 Wshttpsbinding。获取多个名为“NotUnderstood”的标头
- java - 如何将其他背包放在主背包上?
- node.js - AMQP + NodeJS 等待通道
- angular - Angular / Typescript,如何重用类型
- javascript - Javascript - 为对象属性使用多个变量