Skip to main content
This page matches SDK 2.0.0. Makeup / reshape enums: Parameter enums.

Choose the right frame type

Set FBImageFrame.type before processImage:. There is no process-mode argument on the engine.
  • FBFrameTypeVideo (1): camera preview, live, calls — lower latency.
  • FBFrameTypeImage (0): still photos / NSImage — higher quality.

Large stills (preview vs export)

Do not feed full-resolution pixels into processImage: on every slider change, and do not throw the original away after scaling. When the photo opens, keep the full NSImage and build one preview frame (long edge about 1280–1440, createWithNSImage:). Slider changes process the preview (FBFrameTypeImage). Export processes a full-resolution frame with the same setters. Output size matches the input. Camera preview stays capture resolution + FBFrameTypeVideo.

Parameter ranges

  • Skin / makeup / filter intensity: [0.0, 1.0]. 0 turns that effect off.
  • Reshape (setReshape:intensity:): [-1.0, 1.0]. 0 is off. Positive and negative are opposite directions.
Start low on live video. Full enum meanings: Parameter enums.

One engine, one serial queue

createEngineWithConfig: returns an instance, not a process-wide singleton. Keep one engine per session and call it from a serial queue (or the GL thread when externalContext = YES).
Do not process frames on the main thread except for tiny stills. Do not share one engine across concurrent queues.

Memory

  • Prefer ARC. Drop FBImageFrame references when a frame is done.
  • Reuse camera pixel buffers (NV12 / BGRA) instead of converting every frame to RGBA.
  • Call setFilter: / setSticker: once; textures load on the next processImage:.
  • Use clearFilter, clearSticker, clearVirtualBackground, and clearChromaKey instead of creating a second engine.

External OpenGL

When the AppKit view already owns a desktop OpenGL 3.2 Core context (NSOpenGLContext / CGL):
  1. Set config.externalContext = YES.
  2. Create the engine on that GL thread (reuse the caller’s current context; do not create a second one).
  3. Wrap a GL_TEXTURE_2D with createWithTexture:width:height:stride:.
  4. Read the output with [output texture].
macOS uses desktop OpenGL, not OpenGL ES. Do not mix external textures and CVPixelBuffer on the same engine.

Monitor with getStats

Aim for avgProcessTimeMs under ~33 ms at 30 fps. Desktop GPUs can run higher resolutions; still drop effects if the UI hitchs.

Lifecycle (AppKit)

Hold the engine on the NSViewController (or a session object). Stop capture in viewWillDisappear. Pause when the window miniaturizes. Nil the engine in dealloc / applicationWillTerminate.
Use __weak in FBEngineCallbacks blocks.

macOS capture and display

  • Build frames with createWithNV12:..., createWithBGRA:..., or createWithNSImage:.
  • Front camera / user-facing preview: setMirror:@"horizontal".
  • Retina: process in pixel size (backingScaleFactor), not point size.
  • Camera: NSCameraUsageDescription. Sandboxed apps need Outgoing Connections for online auth.
  • User-picked .fbd / background images: security-scoped URLs.

Testing

  • Bind the Mac app Bundle ID (or process name for CLI tools).
  • Use a real appId / appKey or licenseToken.
  • Cover FBFrameTypeImage + createWithNSImage: and FBFrameTypeVideo.
  • Assert setter codes are FBErrorCode_Success. Universal Binary: test Intel and Apple Silicon.