title: Wait for useCallback effects on DOM
body: <p>I'm calling a <code>useCallback</code> from a <code>useEffect</code> that will make the component's height change. Then, to end the effect, I'd like to scroll the component to a specific point. The issue is that the scroll operation does not work because it fires to soon : the DOM did not update yet.</p>
  <p>If I wrap it in a <code>setTimeout</code> it does work (because it fires once the DOM updated), but it's kind of hacky.</p>
  <p>Is there a clean way to wait for the DOM to render before pursuing the effect?</p>
  <p><strong>Does not work:</strong></p>
  <pre class="lang-js prettyprint-override"><code>const viewportElement = useRef()
  cont [innerHeight, setInnerHeight] = useState(0)
  
  refreshDOM = useCallback(() =&gt; {
    setInnerHeight(500) // Will cause the DOM to refresh and the inner div to grow in height.
  }, [setInnerHeight])
  
  useLayoutEffect(() =&gt; {
    refreshDOM() // DOM updates
    viewportElement.current.scroll(0, 200) // Fires to soon: innerDiv is still too small 
  }, [refreshDOM, someOtherStuffTriggeringTheEffect])
  
  return (
    &lt;div ref={viewportElement} style={{height: 100}}&gt;
      &lt;div style={{height: innerHeight}}&gt;&lt;/div&gt;
    &lt;/div&gt;
  )
  </code></pre>
  <p><strong>Works:</strong></p>
  <pre class="lang-js prettyprint-override"><code>
  // ...
  
  useLayoutEffect(() =&gt; {
    refreshDOM() // DOM updates
    setTimeout(
      () =&gt; viewportElement.current &amp;&amp; viewportElement.current.scroll(0, 200),
      0,
    ) // DOM was refreshed, scroll operation works
  }, [refreshDOM, someOtherStuffTriggeringTheEffect])
  
  // ...
  
  </code></pre>