Skip to main content
This guide will help you create your first LiveCodes playground using the SDK.

Basic Setup

1. Create a Container Element

First, add a container element to your HTML:
<div id="container"></div>

2. Import and Initialize

Import the SDK and create a playground:
import { createPlayground } from 'livecodes';

const playground = await createPlayground('#container', {
  config: {
    markup: {
      language: 'html',
      content: '<h1>Hello, LiveCodes!</h1>',
    },
  },
});

Your First Playground

Here’s a complete example with HTML, CSS, and JavaScript:
import { createPlayground } from 'livecodes';

const playground = await createPlayground('#container', {
  config: {
    markup: {
      language: 'html',
      content: '<div id="app">Hello, World!</div>',
    },
    style: {
      language: 'css',
      content: `#app {
  font-family: sans-serif;
  padding: 20px;
  color: #333;
}`,
    },
    script: {
      language: 'javascript',
      content: `console.log('Hello from LiveCodes!');

document.querySelector('#app').addEventListener('click', () => {
  alert('You clicked me!');
});`,
    },
  },
});

// Run the code
await playground.run();

Container Options

You can specify the container in multiple ways:

CSS Selector (String)

const playground = await createPlayground('#container', options);
const playground = await createPlayground('.my-playground', options);
const playground = await createPlayground('[data-playground]', options);

HTMLElement

const element = document.getElementById('container');
const playground = await createPlayground(element, options);

Headless Mode (No Container)

In headless mode, you can omit the container:
const playground = await createPlayground({
  headless: true,
  config: {
    markup: { language: 'html', content: '<h1>Headless</h1>' },
  },
});

Embed Options

Customize the playground behavior with embed options:
const playground = await createPlayground('#container', {
  // Configuration object
  config: {
    markup: { language: 'markdown', content: '# Hello' },
    autoupdate: true,
  },
  
  // Load a starter template
  template: 'react',
  
  // Loading strategy
  loading: 'lazy', // 'lazy' | 'click' | 'eager'
  
  // App URL (for self-hosted instances)
  appUrl: 'https://livecodes.io',
  
  // Import from external source
  import: 'https://github.com/username/repo',
});

Loading Strategies

Lazy Loading (Default)

The playground loads when it enters the viewport:
const playground = await createPlayground('#container', {
  loading: 'lazy',
  config: { /* ... */ },
});

Click-to-Load

Shows a “Click to load” screen:
const playground = await createPlayground('#container', {
  loading: 'click',
  config: { /* ... */ },
});

// Later, load manually
await playground.load();

Eager Loading

Loads immediately:
const playground = await createPlayground('#container', {
  loading: 'eager',
  config: { /* ... */ },
});

Using Templates

Start with a pre-configured template:
const playground = await createPlayground('#container', {
  template: 'react',
});

Interacting with the Playground

Once created, you can interact with the playground:
const playground = await createPlayground('#container', {
  template: 'javascript',
});

// Run the code
await playground.run();

// Get the current code
const code = await playground.getCode();
console.log(code.script.content);

// Get the configuration
const config = await playground.getConfig();
console.log(config.markup.language);

// Format the code
await playground.format();

// Get a share URL
const shareUrl = await playground.getShareUrl();
console.log('Share URL:', shareUrl);

Watching Events

Listen to playground events:
const playground = await createPlayground('#container', {
  template: 'javascript',
});

// Watch for code changes
const codeWatcher = playground.watch('code', ({ code, config }) => {
  console.log('Code changed!');
  console.log('Script content:', code.script.content);
});

// Watch for console output
const consoleWatcher = playground.watch('console', ({ method, args }) => {
  console[method](...args);
});

// Watch for when playground is ready
playground.watch('ready', ({ config }) => {
  console.log('Playground ready with config:', config);
});

// Remove watchers when done
codeWatcher.remove();
consoleWatcher.remove();

Styling the Container

By default, the container gets some default styles. You can customize them:
<div 
  id="container"
  style="height: 500px; border: 2px solid #ddd;"
  data-default-styles="false"
></div>
Or set the height via data attribute:
<div id="container" data-height="600px"></div>

Complete Example

Here’s a complete HTML page with an embedded playground:
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>LiveCodes Playground</title>
  <style>
    #container {
      height: 80vh;
      margin: 20px;
    }
  </style>
</head>
<body>
  <div id="container"></div>

  <script type="module">
    import { createPlayground } from 'https://cdn.jsdelivr.net/npm/livecodes';

    const playground = await createPlayground('#container', {
      config: {
        markup: {
          language: 'html',
          content: '<h1>Welcome to LiveCodes!</h1>',
        },
        style: {
          language: 'css',
          content: 'h1 { color: #4A90E2; font-family: sans-serif; }',
        },
        script: {
          language: 'javascript',
          content: 'console.log("LiveCodes is ready!");',
        },
      },
    });

    // Auto-run when loaded
    playground.watch('ready', async () => {
      await playground.run();
    });
  </script>
</body>
</html>

Next Steps

API Reference

Explore all available SDK methods and options

Methods

Learn about all playground methods

Events

Understand the event system

Types

Browse TypeScript type definitions

Build docs developers (and LLMs) love