Skip to content
Lucent
SEARCH LUCENT

Search guides, APIs, and examples.

GitHub

Very early and experimental. The language, the generated native code and every package API change without notice. Do not use Lucent in production.

Present a view controller

present() from lucent:ios shows a view controller or a system sheet and resolves with its result.

share.lucent.ts
import { PLATFORM } from "lucent:platform";
import { UIActivityViewController } from "lucent:ios/UIKit";
import { onAppEvent, present } from "lucent:ios";
export async function share(text: string, signal?: AbortSignal): Promise<boolean> {
if (PLATFORM !== "ios") return false;
return present<boolean>((resolve) => {
const sheet = new UIActivityViewController([text], null);
sheet.completionHandler = (_type, completed) => resolve(completed);
return sheet;
}, signal);
}
let stop: (() => void) | null = null;
export function onForeground(listener: () => void): void {
if (PLATFORM === "ios") {
if (stop) stop();
stop = onAppEvent("willEnterForeground", listener);
}
}

present() from lucent:ios shows the view controller its function returns, from the scene the person is using, and resolves with what you pass to resolve. The function runs on the main thread, so UIKit works there: make the view controller, and call resolve or reject from its completion handler or delegate.

  • It settles once. Settling dismisses the view controller if it's still shown.
  • It rejects with an AbortError when the signal aborts, when the person swipes the sheet away, or when the scene goes away.
  • It rejects with an InvalidStateError when the app is in the background, or when UIKit won't present it, for example during another presentation.

onAppEvent() and onSceneEvent() call a function on each of UIKit's lifecycle notifications, such as "willEnterForeground" or a scene's "didActivate", on the main thread. Each returns the function that stops it. Your app delegate stays yours.