0

I'm searching for a way to add a JSX element programmatically in React Native. Not conditionally.

It needs to be independent function, so far I couldn't find anything about this. Let me give you code example;

const appendJSX = () => { 
  
 const jsx = <Text> Hello! </Text>

  append(jsx) // <---- can we do something like this?
 } 

let's say I call this function with useEffect and it should add whatever jsx I have inside the function. Up until this point I always see things like pushing inside of an array or something like that.

UPDATE

Equivalent behaviour that works on web;

 useEffect(() => {
 const div = document.createElement("div");
 div.innerText = "appended div"
 document.body.append(div)
 }, [])

As you can see we don't have to touch any JSX in application. Reaching document.body and appending whatever we want is possible in React Web. But how can we achieve this in React Native?

İlker
  • 1,872
  • 1
  • 12
  • 28
  • JSX element is just a normal JS object, you can save it in an array and render it normally. Whats the context of this question? How you intend to use it? [How to create a Minimal, Reproducible Example](https://stackoverflow.com/help/minimal-reproducible-example) – Dennis Vash Oct 08 '21 at 12:07
  • @DennisVash Let's say we created a react native library, developers should be able to import a function from my library (maybe on top level App.tsx), and when it's called, it should add something like alert. – İlker Oct 08 '21 at 12:10
  • Please write a reproducible example in the question itself. Your "library" suppose to render something to the screen, hence a single function without a mounting point won't be enough. – Dennis Vash Oct 08 '21 at 12:14
  • I don't know if you can do something like this with react/ jsx. Let me add this, where would the jsx be appended to? You're example above simple states "append this element", but where is it being appended to? Not saying it's impossible but you would need some heavy abstraction and you would like need to have an element already on the dom that you can append to. Think about having a ref to that dom element and an append function on that ref, something like `ref.append(jsx)` – b.stevens.photo Oct 08 '21 at 17:40
  • @t_killah yes and what I thought was do we have a reference for global View for example? Wrapper of all elements so we can append it, without having to use useRef ? – İlker Oct 09 '21 at 08:59
  • Replying to your edit; the code snippet mixes the react api with the javascript dom api which is a web technology, as far as I know (could be wrong) there's no equivalent in react native. Pretty verbose description of react native's virtual dom https://stackoverflow.com/questions/41804855/does-react-native-have-a-virtual-dom – b.stevens.photo Oct 11 '21 at 20:13
  • @t_killah I see something like UIManager.showPopUp() for example. It provides you a pop up menu, that would work fine if there was an option for ios as well. What I'm looking for is exactly like that. – İlker Oct 12 '21 at 07:11

1 Answers1

2

Not quite sure what you want to do, but as for to add a JSX manually. Here's the answer.

JSX is already part of the language in most of the cases.

  const a = <Text />
  export default a

Will translates into:

  const a = createElement(Text, null, null)
  export default a

Therefore in most of common cases, if you continue using React somewhere else, then the variable a holds a React element without any compilation error.

You might wonder what a actually really holds, it's an object:

  const a = { 
    $$typeof: Symbol(ReactElement), 
    props: null, 
    type: Text 
  }

So you can see the only dependencies in above piece is Text and the ReactElement Symbol. As long as you can resolve them, you are good to export this to anywhere. The latter is normally taken care by Babel.

NOTE:

There's a difference between Text and <Text />. If you just want to export a Text which is a function component, there'll tutorial online, also you can dig into any third party library, because essentially that's what they do, export Text so other people can use it.

windmaomao
  • 7,120
  • 2
  • 32
  • 36