Reactjs 获取offsettop和offsetheight属性不会出错
我正在获取选项。值属性没有错误不确定,但我认为这是关于引用的。我正在共享我的代码。请建议我做什么 代码:2Reactjs 获取offsettop和offsetheight属性不会出错,reactjs,typescript,Reactjs,Typescript,我正在获取选项。值属性没有错误不确定,但我认为这是关于引用的。我正在共享我的代码。请建议我做什么 代码:2 onClick={() => this.change(option.value)} key={option.value} 错误显示:2 (参数)选项:选项PropType “number”类型的参数不能分配给“string”类型的参数。ts 代码:3 <div className="dropdown-label">{current.l
onClick={() => this.change(option.value)}
key={option.value}
错误显示:2(参数)选项:选项PropType “number”类型的参数不能分配给“string”类型的参数。ts 代码:3
<div className="dropdown-label">{current.label}</div>
{current.label}
错误显示:3
恒定电流:选项PropType |未定义
对象可能为“未定义”。ts
下拉列表.tsx
import _ from "lodash";
import React, { Component, createRef } from "react";
import DropdownArrow from "../../assets/dropdown-arrow.svg";
import "./Dropdown.scss";
type OptionsPropType = {
value: number;
label: string;
};
interface IProps {
value: any;
height: number;
options: Array<OptionsPropType>;
onChange: (value: string) => void;
}
interface IState {
isOpen: boolean;
value: string;
}
export class Dropdown extends Component<IProps, IState> {
private readonly listRef: React.RefObject<HTMLDivElement>;
private readonly containerRef: React.RefObject<HTMLDivElement>;
constructor(props:IProps) {
super(props);
this.state = {
isOpen: false,
value: props.value
};
this.listRef = createRef();
this.containerRef = createRef();
}
change(value:string) {
this.setState({ value });
this.props.onChange(value);
this.close();
}
onOutsideClicked = (e?:any) => {
// only outside clicks allowed
if (
this.containerRef.current &&
this.containerRef.current.contains(e.target)
) {
return;
}
document.removeEventListener("mousedown", this.onOutsideClicked);
this.close();
};
toggle() {
const isOpen = !this.state.isOpen;
this.setState({ isOpen });
if (isOpen) {
document.addEventListener("mousedown", this.onOutsideClicked);
}
}
close() {
this.setState({ isOpen: false });
}
componentDidRecieveProps(props:any) {
if (props.value !== this.state.value) {
this.setState({ value: props.value });
}
}
componentDidUpdate() {
if (this.listRef.current) {
const option = this.refs["option-" + this.props.value];
this.listRef.current.scrollTop =
option.offsetTop - (this.props.height - option.offsetHeight) / 2;
}
}
render() {
const { value, isOpen } = this.state;
const current = _.find(this.props.options, (option) => {
// HACK because select returns string
return option.value.toString() === value.toString();
});
const list = _.map(this.props.options, (option) => (
<div
ref={`option-${option.value}`}
className={`dropdown-option ${
value.toString() === option.value.toString()
? "dropdown-option--selected"
: ""
}`}
onClick={() => this.change(option.value)}
key={option.value}
>
{option.label}
</div>
));
return (
<div
className={`dropdown ${isOpen ? "dropdown--open" : ""}`}
onClick={() => this.toggle()}
ref={this.containerRef}
>
<div className="dropdown-label">{current.label}</div>
<div className="dropdown-arrow">
<img src={DropdownArrow} />
</div>
{/* <select onChange={(e) => this.change(e.target.value)} defaultValue={value}>{list}</select> */}
{isOpen ? (
<div
className="dropdown-list"
style={{ maxHeight: this.props.height + "px" }}
ref={this.listRef}
>
{list}
</div>
) : null}
</div>
);
}
}
从“lodash”导入;
从“React”导入React,{Component,createRef};
从“../../assets/dropdown arrow.svg”导入下拉箭头;
导入“/Dropdown.scss”;
类型选项PropType={
值:数字;
标签:字符串;
};
接口IProps{
价值:任何;
高度:数字;
选项:阵列;
onChange:(值:string)=>void;
}
界面状态{
等参:布尔;
值:字符串;
}
导出类下拉列表扩展组件{
私有只读listRef:React.reObject;
私有只读容器ref:React.reObject;
建造师(道具:IProps){
超级(道具);
此.state={
伊索彭:错,
价值:道具价值
};
this.listRef=createRef();
this.containerRef=createRef();
}
更改(值:字符串){
this.setState({value});
this.props.onChange(值);
这个。关闭();
}
onOutsideClicked=(e?:any)=>{
//只允许外部点击
如果(
此为.containerRef.current&&
this.containerRef.current.contains(e.target)
) {
返回;
}
document.removeEventListener(“mousedown”,this.onOutsideClicked);
这个。关闭();
};
切换(){
常量isOpen=!this.state.isOpen;
this.setState({isOpen});
if(等参线){
document.addEventListener(“mousedown”,this.onOutsideClicked);
}
}
关闭(){
this.setState({isOpen:false});
}
ComponentDiReceiveProps(道具:任意){
if(props.value!==this.state.value){
this.setState({value:props.value});
}
}
componentDidUpdate(){
如果(此.listRef.current){
const option=this.refs[“option-”+this.props.value];
this.listRef.current.scrollTop=
option.offsetTop-(this.props.height-option.offsetHeight)/2;
}
}
render(){
const{value,isOpen}=this.state;
const current=uu.find(this.props.options,(option)=>{
//HACK,因为select返回字符串
返回选项.value.toString()==value.toString();
});
const list=\uu.map(this.props.options,(option)=>(
this.change(option.value)}
键={option.value}
>
{option.label}
));
返回(
this.toggle()}
ref={this.containerRef}
>
{current.label}
{/*this.change(e.target.value)}defaultValue={value}>{list}*/}
{isOpen(
{list}
):null}
);
}
}
完整项目链接
这是我在最后一个问题上没有为您解决的部分,因为这是一个非常麻烦的问题。他们在每个
选项上设置了一个ref,这些选项是存储在dictionary对象中的字符串ref,他们通过查找其键来访问ref。错误告诉您需要将它们更新为较新的引用,因为不支持string
ref。与我们为列表和容器设置一个ref不同,我们需要一个记录refs对象,每个选项一个。:(还有其他方法吗?@LindaPaisteconst option:any=this.refs[“option-”+this.props.value];
此解决方案工作正常请给出代码:2和代码:3的解决方案