filters-and-postfx
Use this skill when applying visual filters or post-processing effects in Phaser 4. Covers bloom, blur, glow, color matrix, barrel distortion, displacement, custom shaders, and the filter pipeline. Triggers on: filter, post-processing, shader, bloom, blur, glow, color effects.
What this skill does
# Phaser 4 Filters and Post-FX
## Quick Start
Add a glow effect to a sprite:
```js
// In your Scene's create() method:
const sprite = this.add.sprite(400, 300, 'player');
// Step 1: Enable the filter system on the game object (WebGL only)
sprite.enableFilters();
// Step 2: Add filters via .filters.internal or .filters.external
sprite.filters.internal.addGlow(0xff00ff, 4, 0, 1);
```
Add a blur to the camera:
```js
// Cameras have filters enabled by default - no enableFilters() needed
const camera = this.cameras.main;
camera.filters.internal.addBlur(0, 2, 2, 1);
```
---
## Core Concepts
### How Filters Work in v4
Filters are GPU-based post-processing effects applied after an object or camera renders to a texture. Each filter runs a shader pass over that texture, producing the final visual output. Filters are WebGL only.
The rendering pipeline for a camera with filters:
1. Objects render to a texture the size of the camera.
2. **Internal filters** process that texture, applying effects in object/camera local space.
3. The texture is drawn to a context-sized texture, applying camera transformations (position, rotation, zoom).
4. **External filters** process that context texture, applying effects in screen space.
5. The final texture is composited into the output.
### Internal vs External Filters
Every `FilterList` exposes two sub-lists: `filters.internal` and `filters.external`. The distinction controls **when** the filter runs relative to the camera/object transform:
- **Internal** -- applied before the camera transform. Effects operate in the object's local coordinate space. A horizontal blur on a rotated object appears rotated with the object. Internal filters only cover the object/camera region, so they are cheaper.
- **External** -- applied after the camera transform. Effects operate in screen space. A horizontal blur on a rotated object always blurs horizontally on screen. External filters are full-screen and more expensive.
Use internal filters wherever possible for better performance.
### FilterList
`FilterList` (`Phaser.GameObjects.Components.FilterList`) is the container that holds filter controllers. It provides:
- `add(filter, index)` -- add a Controller instance at an optional index
- `remove(filter, forceDestroy)` -- remove and destroy a filter
- `clear()` -- remove and destroy all filters
- `getActive()` -- return all filters where `active === true`
- `list` -- the raw array of Controllers (safe to reorder)
- Convenience factory methods: `addBlur()`, `addGlow()`, `addMask()`, etc.
### Filter Controllers
Every filter is a `Phaser.Filters.Controller` subclass. Common Controller properties:
| Property | Type | Description |
|---|---|---|
| `active` | boolean | Toggle the filter on/off without removing it |
| `camera` | Camera | The camera that owns this filter |
| `renderNode` | string | The render node ID for the shader |
| `paddingOverride` | Rectangle | Override automatic padding calculation |
| `ignoreDestroy` | boolean | If true, the filter survives when its FilterList is destroyed (for reuse) |
Key methods: `setActive(bool)`, `setPaddingOverride(left, top, right, bottom)`, `getPadding()`, `destroy()`.
### Enabling Filters on Game Objects
Cameras have filters available by default. Game objects do not -- you must call `enableFilters()` first:
```js
const sprite = this.add.sprite(400, 300, 'hero');
sprite.enableFilters();
// Now sprite.filters is available
sprite.filters.internal.addGlow();
sprite.filters.external.addVignette();
```
`enableFilters()` creates an internal `filterCamera` on the game object that handles rendering the object to a texture for filter processing. It returns `this` for chaining.
Related properties on game objects after enabling:
| Property | Default | Description |
|---|---|---|
| `filterCamera` | null -> Camera | The internal camera used for filter rendering |
| `filters` | null -> {internal, external} | Access to the FilterList pair |
| `renderFilters` | true | Master toggle for all filter rendering |
| `filtersAutoFocus` | true | Auto-adjust camera to follow the object |
| `filtersFocusContext` | false | Focus on the rendering context instead of the object bounds |
| `filtersForceComposite` | false | Always draw to a framebuffer even with no active filters |
| `maxFilterSize` | null -> Vector2 | Maximum texture size for filter framebuffers |
Use `willRenderFilters()` to check if any active filters will actually render.
---
## Common Patterns
### Adding Filters to Game Objects
```js
const sprite = this.add.sprite(400, 300, 'enemy');
sprite.enableFilters();
// Add a glow
const glow = sprite.filters.internal.addGlow(0x00ff00, 4);
// Modify at runtime
glow.outerStrength = 8;
glow.color = 0xff0000;
// Temporarily disable
glow.setActive(false);
// Remove and destroy
sprite.filters.internal.remove(glow);
```
### Camera Filters
```js
const camera = this.cameras.main;
// Internal: effect in camera-local space
const blur = camera.filters.internal.addBlur(0, 2, 2, 1);
// External: effect in screen space
const vignette = camera.filters.external.addVignette(0.5, 0.5, 0.5, 0.5);
// Color grading via ColorMatrix
const cm = camera.filters.internal.addColorMatrix();
cm.colorMatrix.sepia();
```
### Chaining Multiple Filters
Filters execute in list order. Each filter receives the output of the previous one:
```js
const cam = this.cameras.main;
// First: apply color grading
const cm = cam.filters.internal.addColorMatrix();
cm.colorMatrix.brightness(0.2);
// Second: apply blur to the color-graded result
cam.filters.internal.addBlur(1, 2, 2, 1);
// Third: add a vignette on top
cam.filters.external.addVignette(0.5, 0.5, 0.5, 0.8);
```
### Masks via Filters
Masks in v4 are implemented as filters. They use the alpha channel of a texture or game object to control visibility:
```js
// Mask with a static texture
sprite.enableFilters();
sprite.filters.internal.addMask('maskTexture');
// Mask with a game object (renders to DynamicTexture automatically)
const maskShape = this.add.circle(0, 0, 100, 0xffffff);
sprite.enableFilters();
const mask = sprite.filters.internal.addMask(maskShape);
// Invert the mask
mask.invert = true;
// Control auto-updating for game object masks
mask.autoUpdate = true; // default: re-renders each frame
mask.needsUpdate = true; // force a one-time update
// Use a specific camera for viewing the mask object
sprite.filters.external.addMask(maskShape, false, this.cameras.main);
```
Internal masks match the object being filtered. External masks match the camera context. Use a `viewCamera` parameter to control which camera renders the mask game object.
### Wipe / Reveal Transitions
```js
const camera = this.cameras.main;
const wipe = camera.filters.external.addWipe(0.1, 0, 0);
// Animate via tween
this.tweens.add({
targets: wipe,
progress: 1,
duration: 2000,
ease: 'Linear'
});
// Direction helpers
wipe.setLeftToRight();
wipe.setTopToBottom();
wipe.setRevealEffect(); // reveal mode
wipe.setWipeEffect(); // wipe mode
// Wipe to another texture (for scene transitions)
wipe.setTexture('nextSceneCapture');
```
### ParallelFilters (Custom Bloom and Compositing)
ParallelFilters splits the input into two paths, processes each independently, then blends the results. This replaces the dedicated Bloom filter from v3:
```js
const camera = this.cameras.main;
const pf = camera.filters.internal.addParallelFilters();
// Top path: threshold bright areas, then blur them
pf.top.addThreshold(0.5, 1);
pf.top.addBlur();
// Configure the blend (how top combines onto bottom)
pf.blend.blendMode = Phaser.BlendModes.ADD;
pf.blend.amount = 0.5;
// Bottom path: left empty = uses original input
```
### CaptureFrame for Scene-Level Effects
`CaptureFrame` captures the current render state at the point it appears in the display list. Objects rendered before it are captured; objects after it are not:
```js
// Requires composite mode on the camera
this.cameraRelated in General
modeling-omnistudio-epc-catalog
IncludedSalesforce Industries CME EPC product-modeling skill for Product2-based catalog creation. Use when creating EPC products, configuring product attributes, building offer bundles with Product Child Items, or reviewing EPC DataPack JSON metadata for product catalog changes. TRIGGER when: user creates or updates Product2 EPC records, AttributeAssignment payloads, AttributeMetadata/AttributeDefaultValues, Offer bundles, or ProductChildItem relationships. DO NOT TRIGGER when: designing OmniScripts/FlexCards/Integration Procedures (use building-omnistudio-omniscript, building-omnistudio-flexcard, or building-omnistudio-integration-procedure), implementing Apex business logic (use generating-apex), or troubleshooting deployment pipelines (use deploying-metadata).
relationship-science-coach
IncludedUse this skill for direct, practical adult relationship coaching: couples conflict, repair, trust, marriage, dating, flirting, attachment patterns, emotional connection, sex, desire differences, eroticism, kink negotiation, affection, love languages, breakups, and long-term passion. Draw on Gottman, EFT and Hold Me Tight, attachment science, modern sex research, Perel, Nagoski, Kerner, Schnarch, Love and Stosny, and flexible love-language tools. Be concrete and low-hedge. Redirect only for imminent danger, abuse, coercive control, minors, non-consent, self-harm, stalking, or medical/legal/psychiatric decisions.
building-sf-integrations
IncludedSalesforce integration architecture and runtime plumbing with 120-point scoring. Use this skill to set up Named Credentials, External Credentials, External Services, REST/SOAP callout patterns, Platform Events, and Change Data Capture. TRIGGER when: user sets up Named Credentials, External Services, REST/SOAP callouts, Platform Events, CDC, or touches .namedCredential-meta.xml files. DO NOT TRIGGER when: Connected App/OAuth config (use configuring-connected-apps), Apex-only logic (use generating-apex), or data import/export (use handling-sf-data).
venue-templates
IncludedAccess comprehensive LaTeX templates, formatting requirements, and submission guidelines for major scientific publication venues (Nature, Science, PLOS, IEEE, ACM), academic conferences (NeurIPS, ICML, CVPR, CHI), research posters, and grant proposals (NSF, NIH, DOE, DARPA). This skill should be used when preparing manuscripts for journal submission, conference papers, research posters, or grant proposals and need venue-specific formatting requirements and templates.
let-fate-decide
IncludedDraws the 12 Houses of the Zodiac Tarot spread to inject entropy into planning when prompts are vague, ambiguous, or casually delegated. Interprets the spread to guide next steps. Use when the user says 'let fate decide', 'YOLO', 'whatever', 'idk', or other nonchalant phrases, makes Yu-Gi-Oh references, or when you are about to arbitrarily pick between multiple reasonable approaches. Prefer over ask-questions-if-underspecified when the user's tone is casual or playful rather than precision-seeking.
net-ops
IncludedCross-platform network troubleshooting (Windows, macOS, Linux) via local or remote shell. Use for: DNS broken, can't resolve hostnames, nslookup/dig works but apps fail, NRPT, WFP, scutil, /etc/resolver, systemd-resolved, /etc/resolv.conf, NetworkManager, VPN DNS leak residue (ProtonVPN/Mullvad/WireGuard/AnyConnect), AV/firewall blocking DNS or DoH, Tailscale DNS interaction, intermittent connectivity, remote diagnostics over SSH.