我在一个模态中使用 UploadCare,该模态现在通过 Portal(来自 React 16)呈现。 UploadCare 在模式中运行良好,直到我创建了一个 React 门户,然后发生了以下错误:
Error: No DOM elements found matching selector
▶ 2 stack frames were collapsed.
UploadCare.componentDidMount
src/components/UploadCare.js:8
5 | class UploadCare extends Component {
6 | componentDidMount() {
7 | const { onChange } = this.props;
> 8 | const widget = uploadcare.Widget(`#${this.id}`);
我正在这样创建我的门户:https://codepen.io/gaearon/pen/yzMaBd
UploadCare 需要一个 DOM 选择器,我在其中使用了一个名为 id 的选择器。代码如下:
class UploadCare extends Component {
componentDidMount() {
const { onChange } = this.props;
const widget = uploadcare.Widget(`#${id}`);
if (onChange && typeof onChange === "function") {
widget.onChange(file => {
if (file) {
file.done(info => onChange(info.cdnUrl)).fail(() => onChange(null));
} else {
onChange(null);
}
});
}
}
render() {
const { id, name } = this.props;
return (
<input
type="hidden"
name={name}
id={id}
data-public-key={process.env.REACT_UPLOADCARE_PUBLIC_KEY}
/>
);
}
}
我已经使用 ref 修复了错误,但我不明白为什么会发生错误。有人可以向我解释门户网站对 DOM 和我的 CSS 选择器有何影响,以及为什么它要求我现在使用 ref 来查找 DOM 元素? 谢谢!
最佳答案
使用 ref 是正确的方法。 Official documentation of React建议使用 ref 与第三方 DOM 库(如 Uploadcare Widget)集成。所以,这个正确的代码:
class UploadCare extends Component {
componentDidMount() {
const { onChange } = this.props;
const widget = uploadcare.Widget(this.uploader);
if (onChange && typeof onChange === "function") {
widget.onChange(file => {
if (file) {
file.done(info => onChange(info.cdnUrl)).fail(() => onChange(null));
} else {
onChange(null);
}
});
}
}
render() {
const { id, name } = this.props;
return (
<input
type="hidden"
ref={input => this.uploader = input}
name={name}
id={id}
data-public-key={process.env.REACT_UPLOADCARE_PUBLIC_KEY}
/>
);
}
}
id
呢?因此,在您的代码中,您在一处使用了 ${id}
const widget = uploadcare.Widget(`#${id}`);
和${this.id}
在另一个地方
> 8 | const widget = uploadcare.Widget(`#${this.id}`);
但是,在 componentDidMount
的范围内,这些变量是未定义的。
尝试使用 Prop
const { onChange, id } = this.props;
const widget = uploadcare.Widget(`#${id}`);
或
const { onChange } = this.props;
const widget = uploadcare.Widget(`#${this.props.id}`);
无论如何,使用 ref 更好。
谢谢!我更新了https://github.com/uploadcare/uploadcare-widget-react-demo/
关于css - 创建 React Portal 后,UploadCare 无法找到匹配选择器的 DOM 元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46577248/