Skill v1.0.1
currentAutomated scan100/100+3 new
version: "1.0.1" name: "panel-extension-api" description: "Deep panel infrastructure knowledge: PanelExtensionAdapter, RenderState incremental building, PanelExtensionContext API, pauseFrame backpressure, panel lifecycle, and the PanelAPI internal hooks."
Panel Extension API Skill
The panel infrastructure connects panels to the MessagePipeline and manages their lifecycle.
Architecture
MessagePipeline (zustand store)│▼PanelExtensionAdapter (per-panel bridge)│ ├── buildRenderState() (incremental state building)│ ├── pauseFrame() (backpressure mechanism)│ └── PanelExtensionContext (API exposed to panel code)▼Panel Component (renders data)
Core Files
| File | Role | |
|---|---|---|
packages/suite-base/src/components/PanelExtensionAdapter/PanelExtensionAdapter.tsx | React component, manages panel lifecycle + subscriptions | |
packages/suite-base/src/components/PanelExtensionAdapter/renderState.ts | Incrementally builds RenderState from pipeline state | |
packages/suite-base/src/context/PanelExtensionContext.ts | Context type panels consume | |
packages/suite-base/src/PanelAPI/ | Internal hooks for built-in panels |
RenderState (Incremental Building)
interface RenderState {topics?: readonly Topic[];currentFrame?: readonly MessageEvent[];allFrames?: readonly MessageEvent[]; // preloaded rangecurrentTime?: Time;parameters?: Map<string, unknown>;variables?: Map<string, unknown>;colorScheme?: "dark" | "light";appSettings?: Map<string, unknown>;}
renderState.tstracks which fields changed since the last render- Only changed fields are rebuilt (e.g. if only
currentTimechanged,topicsis reused) - Reference equality on unchanged fields enables React memo optimizations in panels
PanelExtensionContext (Core API Introduction)
interface PanelExtensionContext {subscribe(topics: SubscriptionConfig[]): void;onRender(renderState: RenderState, done: () => void): void;saveState(state: unknown): void;seekPlayback(time: Time): void;setParameter(key: string, value: unknown): void;}
This snippet is a core API introduction, not the full type surface. For the complete PanelExtensionContext definition (including read-only properties, watch/subscription APIs, publish/service methods, settings APIs, and range subscriptions), see: packages/suite/src/index.ts.
The render callback isonRender(renderState, done). The panel must calldone()when it hasfinished processing the frame — this drivespauseFramebackpressure.
pauseFrame (Backpressure)
const done = pauseFrame(panelId);// ... expensive rendering (GPU upload, chart update) ...done(); // ready for next frame
- Prevents the pipeline from pushing new data while a panel is still rendering
- Critical for the 3D panel (GPU upload) and Plot panel (chart update)
- If a panel doesn't call
done()within the timeout, the next frame is forced
Panel Lifecycle
- Mount — adapter creates the context, panel
initPanel()is called - Subscribe — panel declares topics via
context.subscribe() - Render loop — pipeline pushes a new
RenderState→onRender()fires - Config change — user edits settings → panel re-renders with new config
- Unmount — adapter unsubscribes, panel
cleanup()is called
Creating a New Panel
panels/MyPanel/├── index.tsx # registration + entry point├── MyPanel.tsx # main component├── settings.ts # settings tree definition├── types.ts # panel-specific types└── MyPanel.test.tsx
PanelAPI (Internal Hooks)
Built-in panels access data via React hooks in PanelAPI instead of the PanelExtensionContext render-callback model:
import * as PanelAPI from "@lichtblick/suite-base/PanelAPI";
useDataSourceInfo()— rarely-changing metadata (topics, datatypes, capabilities,startTime);
re-renders only when metadata changes, not during playback.
Performance Notes
- Incremental
RenderStateminimizes object creation — only changed fields are rebuilt pauseFrameprevents data flooding slow panels- Subscription scoping delivers only subscribed topics to each panel
- Profile (React DevTools Profiler / Chrome Performance) before adding memoization
Skills Reference
- For the upstream data bus: load
message-pipelineskill