Dynamic Global Modal React Native 动态全局模态 React Native

huangapple go评论60阅读模式
英文:

Dynamic Global Modal React Native

问题

我尝试构建一个全局的动态模态框/弹出通知组件,该组件在React Native中可访问,也可以在组件上下文之外使用,我可以传递文本和按钮的点击处理程序的回调。

我尝试使用上下文API和Hooks构建它,但现在无法从React组件外访问它。

我考虑使用Redux构建它,这样我可以在React之外调用它,也可以在组件中调用它,但我希望模态框是动态的。
因此,我需要在负载中传递一个回调函数并将其保存到状态中。但函数无法序列化,不应保存到Redux存储中。

你会怎样处理这个问题?
在React Native中是否有门户的概念,可以在React组件之外使用?
这里还有哪些可行的方法?

英文:

I'm trying to build a global dynamic modal / toast notification component that is accessible in react-native and also outside of a component context, where I can pass text and also callbacks to the buttons onClick handlers.

I tried building it with context api and hooks, but now I cannot access it from outside of a react component.

I thought about building it with redux, so I can call it from outside of react and also in components but I want the modal to be dynamic.
So I would need to pass a callback function in the payload and save it to the state. But a function is non-serializeable and should not be saved to the redux store.

How would you deal with this?
Are portals a thing in react-native and usable outside of react components?
What other approaches are viable options here?

答案1

得分: 1

以下是您要求的代码部分的中文翻译:

// 首先,在您的应用程序的根部渲染动态模态框。
<YourModalComponent
  ref={ref => DataHandler.setYourModalComponentRef(ref)}
/>

// 如上代码所示,我们获取组件引用并将其保存在DataHandler文件中。

// 您的DataHandler文件代码将类似于以下内容:
let modalRef = null;

export function setYourModalComponentRef(ref) {
  modalRef = ref;
}

export function getYourModalComponentRef() {
  return modalRef;
}

// 现在您拥有了对组件的引用,可以通过getYourModalComponentRef函数从任何地方调用它。

// 例如:
DataHandler.getYourModalComponentRef().show(
  { /* 任何数据 */ },
  () => { /* 如果需要的回调函数 */ }
);

// 现在主要问题是组件如何了解该show方法。以下是您的模态组件的代码示例:

import React, { useImperativeHandle, useState } from 'react';
import { Modal, Button, Text } from 'react-native';

const YourModalComponent = (props, forwardedRef) => {
  const [visible, setVisible] = useState(false);
  const [data, setData] = useState([]);
  const [callback, setCallback] = useState({});

  useImperativeHandle(forwardedRef, () => ({
    show: (newData, cb) => {
      setData(newData);
      setCallback(cb);
      setVisible(true);
    },
    hide: () => {
      hideModal();
    },
  }));

  const hideModal = () => {
    setVisible?.(false);
  };

  return (
    <Modal visible={visible} onRequestClose={hideModal}>
      <Text>{data.title}</Text> {/* 访问传递的数据。 */}
      <Text>{data.message}</Text>
      <Button title="完成" onPress={() => callback()} />
    </Modal>
  );
};

export default React.forwardRef(YourModalComponent);

希望这个解决方案对您有所帮助。如果您有任何疑问,请随时询问!

英文:

There is one solution that I used to show Modal also from the outside of the React Component without using redux or context API.

First of all, render your dynamic modal at the root of your application.

   &lt;YourModalComponent
ref={ref =&gt; DataHandler.setYourModalComponentRef(ref)}
/&gt;

As you can see in the above code we are taking the component ref and saving it in our DataHandler file.

Your DataHandler file code will look something like this.

let modalRef = null
export setYourModalComponentRef(ref) {
modalRef = ref;
},
export getYourModalComponentRef() {
return modalRef;
},

Now you have a reference to your component which you can call from anywhere with getYourModalComponentRef function.

Example:

 DataHandler.getYourModalComponentRef().show(
{ // any data //},
() =&gt; {// callback function if needed //}
);

Now the main part is how your Component knows about that show method. So here is the code example for your modal component.

import React, { useImperativeHandle, useState } from &#39;react&#39;;
import { Modal, Button, Text } from &#39;react-native&#39;;
const YourModalComponent = (props, forwardedRef) =&gt; {
const [visible, setVisisble] = useState(false);
const [data, setData] = useState([]);
const [callback, setCallback] = useState({});
useImperativeHandle(forwardedRef, () =&gt; ({
show: (newData, cb) =&gt; {
setData(newData);
setCallback(cb);
setVisisble(true);
},
hide: () =&gt; {
hideModal();
},
}));
const hideModal = () =&gt; {
setVisisble?.(false);
};
return (
&lt;Modal visible={visible} onRequestClose={hideModal}&gt;
&lt;Text&gt;{data.title}&lt;/Text&gt; // accessed the passed data.
&lt;Text&gt;{data.message}&lt;/Text&gt;
&lt;Button title=&quot;Done&quot; onPress={() =&gt; callback()} /&gt;
&lt;/Modal&gt;
);
};
export default React.forwardRef(YourModalComponent);

By using this approach you can use any type of modal and from anywhere in the app.

I hope this solution helps you out. Feel free to ask if you have any queries!!!

huangapple
  • 本文由 发表于 2023年5月10日 15:57:08
  • 转载请务必保留本文链接:https://go.coder-hub.com/76216128.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定