7.0 KiB
Dial Tutorial: Using dial-cli
Dial CLI Tutorialdial-cliv0.0.22 This tutorial will guide you through using the dial-cli tool to generate UI controls from TypeScript interfaces with Dial annotations.
Using the dial-cli Tool
The dial-cli is now available as a standalone package for generating Dial schemas from TypeScript files, providing a cleaner installation experience without UI dependencies.
Installation
# Install globally (recommended for CLI tools)
npm install -g @vuer-ai/dial-cli
# or
pnpm install -g @vuer-ai/dial-cli
# Check CLI is available
dial-cli --help
Basic Usage
# Generate schemas from a TypeScript file
dial-cli <input-file> [input-file2...]
# Examples:
dial-cli ./src/components/Box.tsx
# Creates schema.dial in ./metadata directory
dial-cli ./src/components/Box.tsx -o ./schemas
# Outputs to specified directory
# Process multiple files
dial-cli Component1.tsx Component2.tsx
# Specify output directory
dial-cli -o ./metadata MyComponent.tsx
What the CLI Does
The dial-cli tool will:
-
Parse your TypeScript file using the TypeScript compiler API
-
Extract all interfaces and types with Dial annotations
-
Process JSDoc comments following the
@dialconvention -
Generate JSON schema files that can be directly used with DialPanel
Output Files
The CLI generates files with a clean directory structure:
Main Output:
schema.dial- Combined schemas for all components, ready for UI generation
Debug Output (verbose mode only):
-
debug/component-raw.json- Raw output from react-docgen-typescript -
debug/component-combined.json- Enhanced metadata with dial schema information -
debug/component-schemas.json- Individual component schemas for debugging
Local Script
This documentation includes a convenience script for generating metadata:
# From the dial directory
./generate-dial-metadata.sh
This will process the BoxExample.tsx file and output metadata to the metadata/ directory.
Using Generated Schemas
Once you've generated schemas using dial-cli, you can use them in your application. The Dial system consists of three main components:
-
DialProvider - Manages state for all controls
-
DialPanel - Converts schemas to UI components
-
Input Components - Individual control types (number, vector, boolean, etc.)
Component API
DialPanel accepts the following props:
interface DialPanelProps {
schemas: DialSchema[]; // Array of control schemas
groups?: DialGroupConfig[]; // Optional group configurations
}
Usage:
// Basic usage with just schemas
<DialPanel schemas={schemas} />
// With group configuration for layout control
<DialPanel schemas={schemas} groups={groups} />
TypeScript Interfaces
The Dial system uses the following main interfaces:
// Schema for individual controls
interface DialSchema {
name: string;
dtype: string;
value?: DialValue;
min?: number;
max?: number;
step?: number;
options?: Array<string | number | { label: string; value: string | number }>;
// ... other properties
tags?: {
grouping?: string;
col?: boolean | number;
row?: number;
layout?: string;
labelPosition?: LabelPositionT;
noWrap?: boolean;
};
}
// Group configuration for styling and layout
interface DialGroupConfig {
name: string;
noWrap?: boolean;
[key: string]: unknown;
}
// Complete schema with groups (output from dial-cli)
interface DialSchemaGroup {
component: string;
schema: DialSchema[];
groups?: DialGroupConfig[];
}
// Valid value types
type DialValue = string | number | boolean | number[] | string[] | null | undefined;
import { DialProvider, DialPanel } from './dial';
const schemas = [
{
name: 'position',
dtype: 'vector3',
value: [0, 0, 0],
min: -10,
max: 10,
tags: { grouping: 'transform', col: true }
},
// ... more schemas
];
function MyComponent() {
const handleValueChange = (name, value) => {
console.log(`${name} changed to`, value);
};
return (
<DialProvider
schemas={schemas}
onValueChange={handleValueChange}
>
<DialPanel schemas={schemas} />
</DialProvider>
);
}
Complete Example with dial-cli
- Create a TypeScript file with Dial annotations:
// Box.tsx
interface BoxProps {
/**
* Transform properties displayed on single line
* @dial transform @dial-no-wrap
*/
/** @dial transform @dial-dtype vector3 */
position: [number, number, number];
/** @dial transform @dial-dtype euler */
rotation: [number, number, number];
/**
* Box dimensions
* @dial geometry
* @dial-dtype vector3
* @dial-min 0.1
* @dial-max 10
* @dial-step 0.1
*/
size: [number, number, number];
/**
* Box color
* @dial appearance
* @dial-dtype color
*/
color: string;
}
export const Box: React.FC<BoxProps> = ({ size, position, rotation, color }) => {
// Component implementation
};
- Generate the schema:
dial-cli Box.tsx -o ./schemas
# Creates schemas/schema.dial with groups configuration
The generated schema includes group-level settings:
{
"component": "Box",
"schema": [
{ "name": "position", "dtype": "vector3", "tags": { "grouping": "transform", "noWrap": true } },
{ "name": "rotation", "dtype": "euler", "tags": { "grouping": "transform", "noWrap": true } },
{ "name": "size", "dtype": "vector3", "tags": { "grouping": "geometry" } },
{ "name": "color", "dtype": "color", "tags": { "grouping": "appearance" } }
],
"groups": [
{ "name": "transform", "noWrap": true }
]
}
- Use the generated schema in your app:
import { DialProvider, DialPanel, DialSchemaGroup, DialValue } from '@vuer-ai/vuer-uikit';
import allSchemas from './schemas/schema.dial';
// Get the Box component schema from the combined schema file
const boxSchema = allSchemas.find(s => s.component === 'Box');
function App() {
const [boxProps, setBoxProps] = useState({
position: [0, 0, 0],
rotation: [0, 0, 0],
size: [1, 1, 1],
color: '#ff0000'
});
const handleValueChange = (name: string, value: DialValue) => {
setBoxProps(prev => ({ ...prev, [name]: value }));
};
return (
<DialProvider
schemas={[boxSchema]}
onValueChange={handleValueChange}
>
<div style={{ display: 'flex' }}>
{/* Your 3D scene */}
<Box {...boxProps} />
{/* Auto-generated controls with group configuration */}
<DialPanel schemas={[boxSchema]} />
</div>
</DialProvider>
);
}
Next Steps
-
Learn more about Dial Annotation Syntax in the overview
-
Explore all Input Types available in Dial
-
See Controlled Dials for advanced usage
-
Check out the API Notes for detailed reference
-
Read the CLI Details for advanced CLI options