Created
May 31, 2024 16:00
-
-
Save audinue/b3b8920d436dfbeb7c4c3d5e14c54e8d to your computer and use it in GitHub Desktop.
local state for immediate stuff
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
function create_group($symbols, $prefix) | |
{ | |
return (object) [ | |
'tag' => 'group', | |
'symbols' => $symbols, | |
'prefix' => $prefix, | |
'key' => 0, | |
'used' => [] | |
]; | |
} | |
function current_group() | |
{ | |
global $stack; | |
return $stack[count($stack) - 1]; | |
} | |
function next_key() | |
{ | |
$group = current_group(); | |
return $group->prefix . $group->key++; | |
} | |
function clean_current_group() | |
{ | |
$group = current_group(); | |
foreach ($group->symbols as $key => $value) { | |
if (!in_array($key, $group->used)) { | |
unset($group->symbols->$key); | |
} | |
} | |
} | |
function &use_state($factory) | |
{ | |
$group = current_group(); | |
$key = next_key(); | |
$group->used[] = $key; | |
if (!isset($group->symbols->$key)) { | |
$group->symbols->$key = $factory(); | |
} | |
return $group->symbols->$key; | |
} | |
function begin_group($key = null) | |
{ | |
global $stack; | |
$group = current_group(); | |
if ($key === null) { | |
$key = next_key(); | |
} | |
$group->used[] = $key; | |
if (!isset($group->symbols->$key)) { | |
$group->symbols->$key = create_group( | |
(object) [], | |
$key . '-' | |
); | |
} | |
$stack[] = &$group->symbols->$key; | |
} | |
function end_group() | |
{ | |
global $stack; | |
clean_current_group(); | |
array_pop($stack); | |
} | |
function is_group($value) | |
{ | |
return is_object($value) && isset($value->tag) && $value->tag == 'group'; | |
} | |
function sleep_group($group) | |
{ | |
$symbols = (object) []; | |
foreach ($group->symbols as $key => $value) { | |
if (is_group($value)) { | |
$symbols->$key = sleep_group($value); | |
} else { | |
$symbols->$key = $value; | |
} | |
} | |
return (object) [ | |
'tag' => 'group', | |
'symbols' => $symbols | |
]; | |
} | |
function wake_group($group, $prefix = '') | |
{ | |
$symbols = (object) []; | |
foreach ($group->symbols as $key => $value) { | |
if (is_group($value)) { | |
$symbols->$key = wake_group($value, $prefix . $key . '-'); | |
} else { | |
$symbols->$key = (array) $value; | |
} | |
} | |
return create_group($symbols, $prefix); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
require 'runtime.php'; | |
function counter($action) | |
{ | |
extract(use_state(fn () => ['id' => uniqid(), 'count' => 0]), EXTR_REFS); | |
if ($action == 'increment-' . $id) { | |
$count++; | |
} | |
?> | |
<button name="action" value="increment-<?= $id ?>"><?= $count ?></button> | |
<?php | |
} | |
function render($action) | |
{ | |
extract(use_state(fn () => ['show' => false]), EXTR_REFS); | |
if ($action == 'toggle') { | |
$show = !$show; | |
} | |
?> | |
<button name="action" value="toggle">Toggle</button> | |
<?php counter($action) ?> | |
<?php begin_group() ?> | |
<?php if ($show) : ?> | |
<?php counter($action) ?> | |
<?php endif ?> | |
<?php end_group() ?> | |
<?php counter($action) ?> | |
<?php | |
} | |
function tick() | |
{ | |
global $stack; | |
$root = wake_group(json_decode($_POST['state'] ?? '{"symbols":{}}')); | |
$stack = [$root]; | |
?> | |
<form method="post"> | |
<?php render($_POST['action'] ?? '') ?> | |
<?php clean_current_group() ?> | |
<input type="hidden" name="state" value="<?= htmlspecialchars(json_encode(sleep_group($root))) ?>"> | |
</form> | |
<?php | |
} | |
tick(); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment