Skip to main content
ClaudeWave
Skill618 repo starsupdated 8d ago

matlab-build-app

The matlab-build-app skill creates interactive MATLAB desktop applications using class-based code, constructing graphical interfaces with uifigure, grid layouts, and UI components like buttons, sliders, and dropdowns. Use this skill when users need to build GUIs, dashboards, data exploration tools, or embed HTML/JavaScript components, but not for simple plots or editing existing binary .mlapp files.

Install in Claude Code
Copy
git clone --depth 1 https://github.com/matlab/matlab-agentic-toolkit /tmp/matlab-build-app && cp -r /tmp/matlab-build-app/skills-catalog/matlab-app-building/matlab-build-app ~/.claude/skills/matlab-build-app
Then start a new Claude Code session; the skill loads automatically.

SKILL.md

# App Builder

Build MATLAB desktop apps entirely in code using `uifigure` and `uigridlayout`. Since `.mlapp` files are binary and cannot be created or edited as text, all apps are built as class-based `.m` files.

## When to Use

- User asks to create a GUI, app, dashboard, or interactive tool
- User wants buttons, sliders, dropdowns, or other UI controls
- User needs a visual interface for data exploration or parameter tuning
- User wants to embed HTML/CSS/JavaScript components via `uihtml`

## When NOT to Use

- User needs a simple plot or figure without interactive controls (just use `figure` + `plot`)
- User wants to edit an existing `.mlapp` file (binary format — cannot be text-edited)
- User needs a web app deployed to MATLAB Web App Server (use deployment skills)

## Workflow

1. **Define requirements** — What components, what layout, what data flows
2. **Create the app class** — `handle` class with `uifigure`, `uigridlayout`, component properties
3. **Build the layout** — Grid-based, using `'fit'` and `'1x'` for responsive sizing
4. **Add components** — Place in grid cells, wire callbacks
5. **Implement callbacks** — Respond to user interaction, update display
6. **Verify** — Run the app via `evaluate_matlab_code` to confirm it launches and renders correctly

## Key Components

| Component | Constructor | Key callback |
|-----------|------------|-------------|
| Button | `uibutton(parent)` | `ButtonPushedFcn` |
| Edit field (numeric) | `uieditfield(parent, 'numeric')` | `ValueChangedFcn` |
| Edit field (text) | `uieditfield(parent, 'text')` | `ValueChangedFcn` |
| Dropdown | `uidropdown(parent)` | `ValueChangedFcn` |
| Slider | `uislider(parent)` | `ValueChangedFcn` |
| Checkbox | `uicheckbox(parent)` | `ValueChangedFcn` |
| Label | `uilabel(parent)` | — |
| Axes | `uiaxes(parent)` | — |
| Table | `uitable(parent)` | `CellEditCallback` |
| Panel | `uipanel(parent)` | — |
| Tab group | `uitabgroup(parent)` | `SelectionChangedFcn` |
| HTML | `uihtml(parent)` | `DataChangedFcn` |

## Patterns

### Standard App Template

Every app follows this structure: a `handle` class that creates all components in a dedicated method.

```matlab
classdef MyApp < handle
    %MyApp Short description of the app.

    properties (Access = private)
        UIFigure     matlab.ui.Figure
        GridLayout   matlab.ui.container.GridLayout
        InputField   matlab.ui.control.NumericEditField
        RunButton    matlab.ui.control.Button
        ResultLabel  matlab.ui.control.Label
        PlotAxes     matlab.ui.control.UIAxes
    end

    methods (Access = public)
        function app = MyApp()
            createComponents(app);
            if nargout == 0
                clear app
            end
        end

        function delete(app)
            delete(app.UIFigure);
        end
    end

    methods (Access = private)
        function createComponents(app)
            app.UIFigure = uifigure('Name', 'My App', ...
                'Position', [100 100 640 480]);

            app.GridLayout = uigridlayout(app.UIFigure, [2 2]);
            app.GridLayout.RowHeight = {'fit', '1x'};
            app.GridLayout.ColumnWidth = {'fit', '1x'};

            app.InputField = uieditfield(app.GridLayout, 'numeric', ...
                'Value', 10, ...
                'Limits', [1 100]);
            app.InputField.Layout.Row = 1;
            app.InputField.Layout.Column = 1;

            app.RunButton = uibutton(app.GridLayout, ...
                'Text', 'Run', ...
                'ButtonPushedFcn', @(~,~) runAnalysis(app));
            app.RunButton.Layout.Row = 1;
            app.RunButton.Layout.Column = 2;

            app.PlotAxes = uiaxes(app.GridLayout);
            app.PlotAxes.Layout.Row = 2;
            app.PlotAxes.Layout.Column = [1 2];
            title(app.PlotAxes, 'Output');
            xlabel(app.PlotAxes, 'X');
            ylabel(app.PlotAxes, 'Y');
        end

        function runAnalysis(app)
            n = app.InputField.Value;
            x = linspace(0, 2*pi, n);
            plot(app.PlotAxes, x, sin(x), 'LineWidth', 1.5);
        end
    end
end
```

### Grid Layout Sizing

Use `'fit'` for rows/columns that should size to content and `'1x'` for those that fill remaining space:

```matlab
gl = uigridlayout(fig, [4 3]);
gl.RowHeight   = {'fit', '1x', '1x', 'fit'};   % toolbar, content, content, statusbar
gl.ColumnWidth = {200, '1x', '1x'};             % sidebar(px), main, main
gl.Padding     = [10 10 10 10];
gl.RowSpacing  = 5;
gl.ColumnSpacing = 5;
```

### Spanning Rows and Columns

```matlab
ax = uiaxes(gl);
ax.Layout.Row = [2 3];       % span rows 2-3
ax.Layout.Column = [2 3];    % span columns 2-3
```

### Callback Patterns

```matlab
% Inline — short logic
btn.ButtonPushedFcn = @(~,~) disp("Clicked");

% Method reference — preferred for anything non-trivial
slider.ValueChangedFcn = @(src, event) sliderChanged(app, event);

function sliderChanged(app, event)
    newValue = event.Value;
    previousValue = event.PreviousValue;
    % Update display
    app.ResultLabel.Text = sprintf('Value: %.1f', newValue);
end
```

### Web Components with uihtml

For rich UI elements beyond native MATLAB components, embed HTML/CSS/JavaScript:

```matlab
h = uihtml(gl);
h.HTMLSource = fullfile(pwd, 'components', 'chart.html');

% Send data from MATLAB to JavaScript
h.Data = struct('values', [1 2 3 4 5], ...
    'labels', {{'A', 'B', 'C', 'D', 'E'}});

% Receive data from JavaScript
h.DataChangedFcn = @(src, ~) handleWebEvent(app, src.Data);
```

**HTML side — minimal template:**

```html
<!DOCTYPE html>
<html>
<head>
  <style>
    body { font-family: system-ui; margin: 0; padding: 16px; }
  </style>
</head>
<body>
  <div id="app"></div>
  <script>
    function setup(htmlComponent) {
      htmlComponent.addEventListener("DataChanged", function() {
        var data = htmlComponent.Data;
        document.getElementById('app').textContent = JSON.stringify(data);
      });
    }
    setup(document.querySe
matlab-train-networkSkill

>

matlab-driving-data-importerSkill

Import recorded driving sensor data (GPS, camera, lidar, actor tracks, lanes) into scenariobuilder.* objects (GPSData, CameraData, LidarData, ActorTrackData, Trajectory, laneData) and run preprocessing — synchronize, offset correction, crop, normalizeTimestamps, convertTimestamps. Also: compute actor tracks from lidar when no annotations exist, attach camera/lidar mounting + intrinsics, export to MAT/workspace/timetable/script. Use for raw driving dataset files (KITTI, nuScenes, Waymo, Pandaset, ROS/ROS2 bags, .mat, .csv, .mp4) or driving/vehicle/sensor logs that need wrapping. drivingLogAnalyzer (DLA) is OPT-IN ONLY — invoke only on explicit user request ('DLA', 'open in DLA', 'inspect/explore/analyze the recording') or reported sensor problem (sync drift, timestamp mismatch, overlay misalignment). NEVER auto-launch DLA after wrapping (Rule 0). For 'build scenario / export to RoadRunner / drivingScenario / OpenSCENARIO / Unreal / simulate', hand off to matlab-scenario-builder.

matlab-scenario-builderSkill

Generate driving scenes, scenarios, road surfaces, and 3D content from already-wrapped scenariobuilder.* sensor data (GPS, camera, lidar, actor tracks) using Scenario Builder for Automated Driving Toolbox. Use to BUILD, EXPORT, or AUGMENT a virtual scenario/scene/map: ego or actor trajectories, trajectory smoothing, OpenCRG road-surface extraction, 3D asset generation, static-object placement, point-cloud georeferencing + elevation, lane-based ego localization, sensor-fusion tracking, scenario-event extraction (cut-ins, hard brakes, near-misses, ADAS disengagements), or export to RoadRunner, drivingScenario, OpenDRIVE, OpenCRG, OpenSCENARIO, or Unreal Engine. Also: log-to-scenario, scenario harvesting, accident/near-miss reconstruction, SOTIF (ISO 21448) and ISO 26262 scenario coverage, USGS-aerial-lidar scene augmentation, traffic-sign placement from camera+lidar logs. NOT for raw-data import or multi-sensor sync/crop/offset/timestamp normalization — route those to matlab-driving-data-importer.

roadrunner-asset-mappingSkill

>

roadrunner-convert-lanelet2-to-rrhdSkill

>

roadrunner-import-sceneSkill

>

roadrunner-rrhd-authoringSkill

>

matlab-build-simbiology-modelSkill

Build, modify, and diagram SimBiology models — API reference, helper functions, and layout patterns. Use when constructing or editing models programmatically or visually.