VirtualCamera

A single shot that competes for the screen.

A virtual camera describes one shot. Its pieces decide where the camera is and where it looks, and its priority decides when it's on screen.

Choosing the winner

  • The active camera with the highest priority wins.
  • On a tie, the camera that was added, or set active, most recently wins.
  • To switch shots, change priority, or turn a camera on or off. Either one triggers a blend.

Members

MemberDescription
body, aimThe Body and Aim. Setting one replaces the previous.
setBody(piece), setAim(piece)The same, returning a function that removes the piece.
addExtension(piece), addNoise(piece)Adds an Extension or Noise. They stack, in the order added, with a few Extensions running earlier, see Extensions. Each returns a function that removes it.
name, priority, active, hintsThe settings below, changeable at any time.
stateThe camera's own shot, written by its pieces every frame.

Settings

SettingDescriptionDefault
nameUnique name. Used by custom blends and events.required
priorityThe active camera with the highest priority is on screen.0
activeWhether this camera takes part at all. false also stops its pieces from running. Turning it back on starts it fresh.true
hintsChanges the shape of blends in and out of this camera. See Blend hints.BlendHints.none
initialStateStarting pose, applied once. See below.the real camera's pose
standbyUpdateHow this camera updates while another one is on screen: 'always', 'roundRobin' or 'never'. See below.'roundRobin'

initialState

Sets where the camera starts. Useful for a camera without a Body or Aim, since whatever you set here simply stays put.

It takes any camera state field, most commonly position, quaternion and fov. Pieces with damping ease in from it on the camera's first activation instead of snapping. In three.js and React, vectors also accept a Vector3 or a single number, and quaternion a Quaternion.

standbyUpdate

Cameras off screen don't need to update every frame: nobody sees them. By default they take turns, so many cameras cost about as much as two:

ValueOff screen, the camera
'roundRobin'takes turns with the other 'roundRobin' cameras: one of them updates per frame.
'always'updates every frame.
'never'waits until it wins.

The camera the shot heads to always updates, and one that skipped frames catches up with the time it missed, so switching to it is smooth. While a camera is off screen, its state is only as fresh as its last update: use 'always' for a camera whose state you read every frame, like one shown with a frustum helper.

Usage

import { FollowBody, HardLookAtAim, targetPose, VirtualCamera } from '@pmndrs/klipp';

const player = targetPose.create(); // keep player.position and player.rotation up to date

const follow = new VirtualCamera('follow', { priority: 10 });
klipp.add(follow);
follow.body = new FollowBody(player, { offset: [0, 3, 8] });
follow.aim = new HardLookAtAim(player);

const map = new VirtualCamera('map', { priority: 20, active: false });
klipp.add(map);
map.active = mapOpen;

initialState

klipp.add(new VirtualCamera('fixed', { priority: 10, initialState: { position: [0, 10, 10], fov: 35 } }));

standbyUpdate

klipp.add(new VirtualCamera('security-cam', { priority: 5, standbyUpdate: 'never' }));