Example Apps
These are all working apps that persist their state on Hyperclay - they change the DOM and the DOM saves itself automatically.
We include jQuery versions as a familiar, easy-to-understand first example, but encourage you to explore the often much simpler Hyperclay-native syntax.
Counter
With jQuery
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
</head>
<body>
<div style="padding: 20px; text-align: center;">
<h1>Counter: <span class="counter">0</span></h1>
<button class="increment">+</button>
<button class="decrement">-</button>
</div>
<script type="module">
import { hyperclay } from 'https://hyperclay.com/js/hyperclay-starter-kit.js';
$('.increment').on('click', function() {
$('.counter').text((i, text) => +text + 1);
});
$('.decrement').on('click', function() {
$('.counter').text((i, text) => +text - 1);
});
</script>
</body>
</html>
With hyperclay.js
<!DOCTYPE html>
<html>
<head>
<script src="https://hyperclay.com/js/hyperclay-starter-kit.js" type="module"></script>
</head>
<body>
<div style="padding: 20px; text-align: center;">
<h1>Counter: <span class="counter">0</span></h1>
<button onclick="this.nearest.counter.textContent++">+</button>
<button onclick="this.nearest.counter.textContent--">-</button>
</div>
</body>
</html>
Todo List
With jQuery
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
</head>
<body>
<h1>My Todos</h1>
<ul class="todo-list">
<li class="task template" style="display:none">
<input type="checkbox" class="task-checkbox">
<span class="task-text">New task</span>
<button class="delete-btn" style="display: none;">×</button>
</li>
</ul>
<button class="add-task" style="display: none;">Add Task</button>
<script type="module">
import { hyperclay } from 'https://hyperclay.com/js/hyperclay-starter-kit.js';
const isEditMode = document.documentElement.getAttribute('editmode') === 'true';
if (isEditMode) {
$('.delete-btn, .add-task').show();
$('.task-text').attr('contenteditable', 'true');
Sortable.create($('.todo-list')[0], {
animation: 150
});
hyperclay.beforeSave(() => {
$('.delete-btn, .add-task').hide();
$('.task-text').attr('contenteditable', 'false');
});
}
$('.add-task').on('click', function() {
const $newTask = $('.task.template').clone();
$newTask.removeClass('template').show();
$newTask.find('.task-text').attr('contenteditable', isEditMode);
if (isEditMode) {
$newTask.find('.delete-btn').show();
}
$('.todo-list').append($newTask);
});
$(document).on('click', '.delete-btn', function() {
$(this).closest('.task').remove();
});
$(document).on('change', '.task-checkbox', function() {
if ($(this).prop('checked')) {
$(this).attr('checked', 'checked');
} else {
$(this).removeAttr('checked');
}
});
</script>
</body>
</html>
With hyperclay.js
<!DOCTYPE html>
<html>
<head>
<script src="https://hyperclay.com/js/hyperclay-starter-kit.js" type="module"></script>
</head>
<body>
<h1>My Todos</h1>
<ul sortable>
<li class="task" style="display:none" onclone="this.style.display='block'">
<input type="checkbox" persist>
<span edit-mode-contenteditable>New task</span>
<button option:editmode="true" onclick="this.nearest.task.remove()">×</button>
</li>
</ul>
<button option:editmode="true" onclick="this.nearest.task.before(this.nearest.task.cloneNode(true))">Add Task</button>
</body>
</html>
Note Pad
With jQuery
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<style>
textarea { width: 100%; height: 400px; padding: 10px; font-family: monospace; }
</style>
</head>
<body>
<h1>My Notes</h1>
<textarea class="notepad" placeholder="Start typing..."></textarea>
<script type="module">
import { hyperclay } from 'https://hyperclay.com/js/hyperclay-starter-kit.js';
const isEditMode = document.documentElement.getAttribute('editmode') === 'true';
const $notepad = $('.notepad');
if (!isEditMode) {
$notepad.attr('readonly', true);
} else {
$notepad.on('input', function() {
this.setAttribute('value', this.value);
});
hyperclay.beforeSave(() => {
$notepad.each(function() {
this.textContent = this.getAttribute('value') || this.value;
this.removeAttribute('value');
});
$notepad.attr('readonly', true);
});
}
</script>
</body>
</html>
With hyperclay.js
<!DOCTYPE html>
<html>
<head>
<script src="https://hyperclay.com/js/hyperclay-starter-kit.js" type="module"></script>
<style>
textarea { width: 100%; height: 400px; padding: 10px; font-family: monospace; }
</style>
</head>
<body>
<h1>My Notes</h1>
<textarea persist edit-mode-input placeholder="Start typing..."></textarea>
</body>
</html>
Timer
With jQuery
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/easytimer.min.js"></script>
</head>
<body>
<div style="text-align: center; padding: 50px;">
<h1 class="display">00:00</h1>
<button class="start-btn">Start</button>
<button class="stop-btn">Stop</button>
<button class="reset-btn">Reset</button>
</div>
<script type="module">
import { hyperclay } from 'https://hyperclay.com/js/hyperclay-starter-kit.js';
const timer = new easytimer.Timer();
timer.addEventListener('secondsUpdated', function (e) {
$('.display').text(timer.getTimeValues().toString(['minutes', 'seconds']));
});
$('.start-btn').on('click', function() {
timer.start();
});
$('.stop-btn').on('click', function() {
timer.pause();
});
$('.reset-btn').on('click', function() {
timer.stop();
$('.display').text('00:00');
});
</script>
</body>
</html>
With hyperclay.js
<!DOCTYPE html>
<html>
<head>
<script src="https://hyperclay.com/js/hyperclay-starter-kit.js" type="module"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/easytimer.min.js"></script>
</head>
<body>
<div style="text-align: center; padding: 50px;">
<h1 id="display">00:00</h1>
<button onclick="timer.start()">Start</button>
<button onclick="timer.pause()">Stop</button>
<button onclick="timer.stop(); display.textContent = '00:00'">Reset</button>
</div>
<script>
const timer = new easytimer.Timer();
timer.addEventListener('secondsUpdated', function (e) {
display.textContent = timer.getTimeValues().toString(['minutes', 'seconds']);
});
</script>
</body>
</html>
”These aren’t apps, they’re just HTML pages you can modify!!”
Yes :)
Advanced Example Apps
Ready-to-use applications that demonstrate Hyperclay’s full potential. Each can be cloned and customized for your needs.
Dev Log
A software developer’s work log for tracking daily progress and debugging sessions.
- Features: Sortable entries, project categorization, monospace aesthetic
- Use case: Technical journaling, development notes, team updates
- Key patterns: DOM-based data storage, sortable lists, inline editing, category toggling
Writer
A beautiful WYSIWYG editor for creating formatted documents.
- Features: Rich text editing, image imports, syntax highlighting
- Use case: Blog posts, documentation, formatted notes
- Key patterns: Script as JSON database
Kanban
A Trello-style project management board with drag-and-drop functionality.
- Features: Draggable cards and columns, inline editing
- Use case: Project tracking, workflow management, task organization
- Key patterns: Template cloning
Landing
A professional landing page template that’s ready to customize.
- Features: Responsive design, markdown content, fill-in-the-blanks
- Use case: Product launches, marketing pages, startups
- Key patterns: Edit-mode popovers, undo/redo support
Last updated on