Quantcast
Channel: ReScript Forum - Latest posts
Viewing all articles
Browse latest Browse all 1774

How to bind to a js property that is a promise (not method)

$
0
0

Hi, I’m trying to do some bindings for the new View Transitions dom api, but I’m getting a little stuck as it has properties that are promises, but the property is not a method.

For example, the finished property is a property that needs to be awaited, but it is not a method call.
e.g. in js, it’s called like this:

  try {
    await transition.finished;
  } finally {
    document.documentElement.classList.remove("back-transition");
  }

I’m not to sure how to make this work in rescript. My code below is what I have so far, but unfortunately my code is currently calling the properties as if they were methods.


@module("react-dom") external reactFlushSync: (unit => unit) => unit = "flushSync"

type viewTransition

@send external skipTransition: (viewTransition, unit) => unit = "skipTransition"
@send external viewTransitionFinished: viewTransition => promise<unit> = "finished"
@send external viewTransitionReady: viewTransition => promise<unit> = "ready"
@send
external viewTransitionUpdateCallbackDone: viewTransition => promise<unit> = "updateCallbackDone"

@scope("document") @val
external maybeStartViewTransition: Nullable.t<(unit => unit) => viewTransition> =
  "startViewTransition"

let doViewTransition = callback => {
  switch Nullable.toOption(maybeStartViewTransition) {
  | Some(startViewTransition) =>
    // we will be using the methods that startViewTransition returns
    startViewTransition(() => {
      // This seems to be required to get view transition working with react: https://developer.chrome.com/docs/web-platform/view-transitions/#working-with-frameworks
      reactFlushSync(() => {
        callback()
      })
    })
  | None =>
    callback()
    // return an object with no-op methods for browsers that don't support the view transitions api
    %raw(`{
      skipTransition(){},
      get viewTransitionFinished(){ return Promise.resolve() },
      get viewTransitionReady(){ return Promise.resolve() },
      get viewTransitionUpdateCallbackDone(){ return Promise.resolve() },
    }`)
  }
}

let vt = doViewTransition(() => {
  // do something here
  ()
})

vt->skipTransition()

let foo = async () => {
  let finished = await vt->viewTransitionFinished
  Console.log(finished)
}

foo()->ignore

At the moment the output is:

async function foo() {
  var finished = await vt.finished();
  console.log(finished);
}

foo();

If i remove the @send it is converted to:

async function foo() {
  var finished$1 = await finished(vt);
  console.log(finished$1);
}

foo();

Which is still not right.


Viewing all articles
Browse latest Browse all 1774

Trending Articles