Creating XMLUI HelloWorld Component & Using Smart UI for React
This document provides a complete guide on how to build and use the Smart with the XMLUI Framework. Visit the official XMLUI site
This tutorial demonstrates how to build a basic HelloWorld component using XMLUI and integrate Smart UI for React components into the same XMLUI-driven React application.
XMLUI components are made of three main parts:
- Native React component (HelloWorldNative.tsx) - The actual React implementation
- Component metadata (HelloWorld.tsx) - Describes props and integrates with XMLUI
- For visual components, a .scss file (HelloWorld.module.scss)
Prerequisites
- Node.js 20+
- React + TypeScript knowledge
- Basic understanding of XMLUI markup & Smart UI
1. Create your project folders & Install Dependencies
md xmlui-hello-world cd xmlui-hello-world
This creates a fresh project directory where you'll build your component from scratch.
npm install --save-dev xmluiNow let's update the package.json with the proper configuration for our extension:
{
"name": "xmlui-hello-world",
"version": "0.1.0",
"type": "module",
"scripts": {
"build:extension": "xmlui build-lib"
},
"devDependencies": {
"xmlui": "*"
},
"main": "./dist/xmlui-hello-world.js",
"module": "./dist/xmlui-hello-world.mjs",
"exports": {
".": {
"import": "./dist/xmlui-hello-world.mjs",
"require": "./dist/xmlui-hello-world.js"
}
},
"files": [
"dist"
]
}
Now let's install Smart UI for React.
npm install xmlui smart-webcomponents-react
Smart UI components are standard React components. To use them in XMLUI, wrap them with XMLUI metadata just like custom components.
2. Project Structure
src/ ├─ HelloWorldNative.tsx ├─ HelloWorld.tsx ├─ HelloWorld.module.scss └─ index.tsx text-app/ ├─ index.html └─ Main.xmlui
3. HelloWorld Native React Component(HelloWorldNative.tsx)
We will add the Smart.Table and Smart.Button components and enable the following Table features: Sorting, Filtering, Editing and Selection.
import React, { useState } from "react";
import styles from "./HelloWorld.module.scss";
import 'smart-webcomponents-react/source/styles/smart.default.css';
import { Button } from 'smart-webcomponents-react/button';
import { Table } from 'smart-webcomponents-react/table';
type Props = {
id?: string;
message?: string;
};
export const defaultProps = {
message: "Hello, World!",
};
export function HelloWorld({
id,
message = defaultProps.message,
}: Props) {
const [clickCount, setClickCount] = useState(0);
const handleClick = () => {
setClickCount(clickCount + 1);
};
return (
<div className={styles.container} id={id}>
<h2 className={styles.message}>{message}</h2>
<Button onClick={handleClick}>
Click me!
</Button>
<div className={styles.counter}>Clicks: {clickCount}</div>
<h3>Smart UI Table</h3>
<Table sortMode={"one"} filtering={true} filterRow={true} selection={true} editMode={"cell"}>
<table>
<thead>
<tr>
<th scope="col">Country</th>
<th scope="col">Area</th>
<th scope="col">Population_Rural</th>
<th scope="col">Population_Total</th>
<th scope="col">GDP_Total</th>
</tr>
</thead>
<tbody>
<tr>
<td>Brazil</td>
<td>8515767</td>
<td>0.15</td>
<td>205809000</td>
<td>2353025</td>
</tr>
<tr>
<td>China</td>
<td>9388211</td>
<td>0.46</td>
<td>1375530000</td>
<td>10380380</td>
</tr>
<tr>
<td>France</td>
<td>675417</td>
<td>0.21</td>
<td>64529000</td>
<td>2846889</td>
</tr>
<tr>
<td>Germany</td>
<td>357021</td>
<td>0.25</td>
<td>81459000</td>
<td>3859547</td>
</tr>
<tr>
<td>India</td>
<td>3287590</td>
<td>0.68</td>
<td>1286260000</td>
<td>2047811</td>
</tr>
<tr>
<td>Italy</td>
<td>301230</td>
<td>0.31</td>
<td>60676361</td>
<td>2147952</td>
</tr>
<tr>
<td>Japan</td>
<td>377835</td>
<td>0.07</td>
<td>126920000</td>
<td>4616335</td>
</tr>
<tr>
<td>Russia</td>
<td>17098242</td>
<td>0.26</td>
<td>146544710</td>
<td>1857461</td>
</tr>
<tr>
<td>United States</td>
<td>9147420</td>
<td>0.19</td>
<td>323097000</td>
<td>17418925</td>
</tr>
<tr>
<td>United Kingdom</td>
<td>244820</td>
<td>0.18</td>
<td>65097000</td>
<td>2945146</td>
</tr>
</tbody>
</table>
</Table>
</div>
);
}
4. Create basic styles (src/HelloWorld.module.scss)
.container {
background-color: #f5f5f5;
color: #333;
padding: 1rem;
border-radius: 8px;
text-align: center;
display: inline-block;
min-width: 200px;
}
.message {
margin: 0 0 1rem 0;
font-size: 1.5rem;
}
.button {
background-color: #4a90e2;
color: white;
border: none;
padding: 0.75rem 1.5rem;
border-radius: 4px;
cursor: pointer;
font-size: 1rem;
margin-bottom: 1rem;
&:hover {
opacity: 0.9;
}
}
.counter {
font-size: 1.2rem;
font-weight: bold;
}5. XMLUI Metadata & Renderer (HelloWorld.tsx)
import styles from "./HelloWorld.module.scss";
import { createComponentRenderer, createMetadata } from "xmlui";
import { HelloWorld, defaultProps } from "./HelloWorldNative";
const HelloWorldMd = createMetadata({
description: "`HelloWorld` is a demonstration component.",
status: "experimental",
props: {
message: {
description: "The message to display.",
isRequired: false,
type: "string",
defaultValue: defaultProps.message,
},
},
});
export const helloWorldComponentRenderer = createComponentRenderer(
"HelloWorld",
HelloWorldMd,
({ node, extractValue }) => {
return (
<HelloWorld
id={extractValue.asOptionalString(node.props?.id)}
message={extractValue.asOptionalString(node.props?.message)}
/>
);
}
);
The renderer is the glue that translates XMLUI markup into React, making sure all props are correctly extracted and defaults are applied when needed.
6. Create the extension index (src/index.tsx )
import { helloWorldComponentRenderer } from "./HelloWorld";
export default {
namespace: "XMLUIExtensions",
components: [helloWorldComponentRenderer],
};
7. Build the extension
npm run build:extension
This creates xmlui-hello-world.js in the dist folder.
8. Test the application
Create the test-app/Main.xmlui file with your component's markup
<App>
<VStack gap="2rem" padding="2rem">
<Heading>HelloWorld Component Test</Heading>
<HelloWorld message="Hello from standalone app!" />
</VStack>
</App>
Then create the index.html file
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8" /> <meta name="viewport" content="width=device-width, initial-scale=1.0" /> <title>HelloWorld Extension Test</title> <script src="https://unpkg.com/xmlui@latest/dist/standalone/xmlui-standalone.umd.js"></script> <script src="../dist/xmlui-hello-world.js"></script> </head> <body theme="dark"> </body> </html>
9. Run the app
npx -y http-server -p 3000 -c-1 -o
Summary
- XMLUI separates metadata from React logic
- Smart UI components can be wrapped and exposed to XMLUI
- You can freely mix custom and third-party UI components
You now have a clean foundation for building structured XML-driven UIs powered by React and Smart UI.
Download the test app xmlui-demo.zip