Skip to content
🎉 Angular Three v4 is here! Read the announcement

Components

Component-based API for Tweakpane provides fine-grained control through Angular directives. Use these when you need more control over the UI structure or want to leverage Angular’s template features like control flow.

Main container directive that creates the root Tweakpane panel.

import { TweakpanePane } from 'angular-three-tweakpane';
@Component({
template: `
<tweakpane-pane title="Controls">
<tweakpane-number label="Speed" [(value)]="speed" />
</tweakpane-pane>
`,
imports: [TweakpanePane, TweakpaneNumber],
})
export class Controls {
speed = signal(1);
}
<!-- Default position (top-right) -->
<tweakpane-pane title="Debug" />
<!-- Custom position -->
<tweakpane-pane title="Debug" left="8px" bottom="8px" [right]="undefined" />
<!-- Embedded in container -->
<div #container></div>
<tweakpane-pane [container]="container" title="Embedded" />
InputTypeDefaultDescription
titlestring-Pane title
topstring | number'8px'CSS top position
rightstring | number'8px'CSS right position
leftstring | number-CSS left position
bottomstring | number-CSS bottom position
widthstring | number'256px'CSS width
containerHTMLElement | ElementRef-Container to embed pane into
expandedbooleanfalseWhether pane starts expanded
OutputTypeDescription
expandedChangebooleanEmits when expanded state changes

Directive that provides an anchor point for the tweaks() function. Add to your ngt-canvas to enable declarative controls.

<ngt-canvas tweakpaneAnchor>
<app-scene-graph *canvasContent />
</ngt-canvas>

This directive is required when using the tweaks() function but not needed for the component-based API.

Creates collapsible folders to organize controls.

import { TweakpanePane, TweakpaneFolder, TweakpaneNumber } from 'angular-three-tweakpane';
@Component({
template: `
<tweakpane-pane title="Settings">
<tweakpane-folder title="Physics" [expanded]="true">
<tweakpane-number label="Gravity" [(value)]="gravity" />
<tweakpane-number label="Friction" [(value)]="friction" />
</tweakpane-folder>
<tweakpane-folder title="Appearance">
<tweakpane-color label="Color" [(value)]="color" />
</tweakpane-folder>
</tweakpane-pane>
`,
imports: [TweakpanePane, TweakpaneFolder, TweakpaneNumber, TweakpaneColor],
})
export class Controls {
gravity = signal(9.8);
friction = signal(0.5);
color = signal('#ff0000');
}
InputTypeDefaultDescription
titlestring-Folder title
expandedbooleanfalseWhether folder starts expanded
hiddenbooleanfalseWhether folder is hidden
disabledbooleanfalseWhether folder is disabled
OutputTypeDescription
expandedChangebooleanEmits when expanded state changes

Numeric input with optional slider.

<!-- Simple number input -->
<tweakpane-number label="Count" [(value)]="count" />
<!-- With slider (min/max) -->
<tweakpane-number label="Speed" [(value)]="speed" [params]="{ min: 0, max: 100, step: 0.1 }" />
<!-- With custom format -->
<tweakpane-number label="Angle" [(value)]="angle" [params]="{ min: 0, max: 360, format: formatDegrees }" />
InputTypeDefaultDescription
labelstring-Input label
valuenumber-Current value (two-way bindable)
paramsNumberInputParams{}Tweakpane number params (min, max, step, format)
hiddenbooleanfalseWhether input is hidden
disabledbooleanfalseWhether input is disabled
OutputTypeDescription
valueChangenumberEmits when value changes

Color picker control.

<tweakpane-color label="Background" [(value)]="backgroundColor" />
<!-- With alpha -->
<tweakpane-color label="Accent" [(value)]="accentColor" [params]="{ alpha: true }" />
InputTypeDefaultDescription
labelstring-Input label
valuestring-Hex color value (two-way bindable)
paramsColorInputParams{}Tweakpane color params (alpha, etc.)
hiddenbooleanfalseWhether input is hidden
disabledbooleanfalseWhether input is disabled
OutputTypeDescription
valueChangestringEmits when color changes

Boolean toggle control.

<tweakpane-checkbox label="Debug Mode" [(value)]="debugMode" />
<!-- Conditionally disabled -->
<tweakpane-checkbox label="Wireframe" [(value)]="showWireframe" [disabled]="!debugMode()" />
InputTypeDefaultDescription
labelstring-Input label
valueboolean-Current value (two-way bindable)
paramsBooleanInputParams{}Tweakpane boolean params
hiddenbooleanfalseWhether input is hidden
disabledbooleanfalseWhether input is disabled
OutputTypeDescription
valueChangebooleanEmits when value changes

Clickable button for triggering actions.

<tweakpane-button title="Reset" (click)="onReset()" />
<tweakpane-button title="Randomize" label="Action" (click)="onRandomize()" />
<tweakpane-button title="Save" [disabled]="!canSave()" (click)="onSave()" />
InputTypeDefaultDescription
titlestring-Button text
labelstring-Label next to button
hiddenbooleanfalseWhether button is hidden
disabledbooleanfalseWhether button is disabled
OutputTypeDescription
clickTpMouseEvent<ButtonApi>Emits when button is clicked

Text input control.

<tweakpane-text label="Name" [(value)]="objectName" />
<tweakpane-text label="Description" [(value)]="description" />
InputTypeDefaultDescription
labelstring-Input label
valuestring-Current value (two-way bindable)
paramsStringInputParams{}Tweakpane string params
hiddenbooleanfalseWhether input is hidden
disabledbooleanfalseWhether input is disabled
OutputTypeDescription
valueChangestringEmits when value changes

Dropdown select control.

<!-- Options as array -->
<tweakpane-list label="Mode" [(value)]="mode" [options]="['normal', 'debug', 'performance']" />
<!-- Options as object (label: value mapping) -->
<tweakpane-list label="Quality" [(value)]="quality" [options]="{ 'Low': 1, 'Medium': 2, 'High': 3, 'Ultra': 4 }" />
InputTypeDefaultDescription
labelstring-Input label
valueT-Currently selected value (two-way bindable)
optionsT[] | Record<string, T>-Options array or label-value mapping
debouncenumber-Debounce delay in ms
hiddenbooleanfalseWhether input is hidden
disabledbooleanfalseWhether input is disabled
OutputTypeDescription
valueChangeTEmits when selection changes

2D/3D/4D point input control.

<!-- 2D point -->
<tweakpane-point label="Position" [(value)]="position2D" />
<!-- 3D point with custom ranges -->
<tweakpane-point
label="Position"
[(value)]="position3D"
[params]="{
x: { min: -10, max: 10 },
y: { min: 0, max: 100 },
z: { min: -10, max: 10 }
}"
/>
<!-- 4D point (e.g., quaternion) -->
<tweakpane-point label="Rotation" [(value)]="quaternion" />

Values are accepted as tuple arrays [x, y, z?, w?].

InputTypeDefaultDescription
labelstring-Input label
value[number, number, number?, number?]-Point tuple (two-way bindable)
paramsPoint2d/3d/4dInputParams{}Per-axis config (x, y, z, w)
hiddenbooleanfalseWhether input is hidden
disabledbooleanfalseWhether input is disabled
OutputTypeDescription
valueChange[number, ...]Emits when point changes

The component-based API works seamlessly with Angular’s control flow:

@Component({
template: `
<tweakpane-pane title="Dynamic Controls">
@if (showAdvanced()) {
<tweakpane-folder title="Advanced">
<tweakpane-number label="Iterations" [(value)]="iterations" />
</tweakpane-folder>
}
@for (item of items(); track item.id) {
<tweakpane-number [label]="item.name" [(value)]="item.value" />
}
</tweakpane-pane>
`,
})
export class DynamicControls {
showAdvanced = signal(false);
iterations = signal(4);
items = signal([
{ id: 1, name: 'Item 1', value: signal(0) },
{ id: 2, name: 'Item 2', value: signal(0) },
]);
}
import { Component, signal } from '@angular/core';
import {
TweakpanePane,
TweakpaneFolder,
TweakpaneNumber,
TweakpaneColor,
TweakpaneCheckbox,
TweakpaneButton,
TweakpaneList,
} from 'angular-three-tweakpane';
@Component({
template: `
<tweakpane-pane title="Scene Controls">
<tweakpane-folder title="Transform" [expanded]="true">
<tweakpane-number label="X" [(value)]="x" [params]="{ min: -5, max: 5, step: 0.1 }" />
<tweakpane-number label="Y" [(value)]="y" [params]="{ min: -5, max: 5, step: 0.1 }" />
<tweakpane-number label="Z" [(value)]="z" [params]="{ min: -5, max: 5, step: 0.1 }" />
</tweakpane-folder>
<tweakpane-folder title="Material">
<tweakpane-color label="Color" [(value)]="color" />
<tweakpane-number label="Metalness" [(value)]="metalness" [params]="{ min: 0, max: 1 }" />
<tweakpane-checkbox label="Wireframe" [(value)]="wireframe" />
</tweakpane-folder>
<tweakpane-folder title="Rendering">
<tweakpane-list label="Quality" [(value)]="quality" [options]="{ Low: 0.5, Medium: 1, High: 2 }" />
<tweakpane-checkbox label="Shadows" [(value)]="shadows" />
</tweakpane-folder>
<tweakpane-button title="Reset All" (click)="reset()" />
</tweakpane-pane>
`,
imports: [
TweakpanePane,
TweakpaneFolder,
TweakpaneNumber,
TweakpaneColor,
TweakpaneCheckbox,
TweakpaneButton,
TweakpaneList,
],
})
export class Controls {
x = signal(0);
y = signal(0);
z = signal(0);
color = signal('#ff0000');
metalness = signal(0.5);
wireframe = signal(false);
quality = signal(1);
shadows = signal(true);
reset() {
this.x.set(0);
this.y.set(0);
this.z.set(0);
this.color.set('#ff0000');
this.metalness.set(0.5);
this.wireframe.set(false);
this.quality.set(1);
this.shadows.set(true);
}
}