Control Flow Directives
Control flow directives wrap an element in a conditional or loop. Only one control-flow directive can appear on a single element. Use <s-template> when you want control flow without adding a wrapper element.
Directives
s:if- Render when a condition is true.s:unless- Render when a condition is false.s:isset- Render when a variable is set.s:empty- Render when a value is empty.s:foreach- Loop over an iterable.s:forelse- Loop with an empty fallback.s:while- Loop while a condition is true.s:times- Loop a fixed number of times.s:switch- Switch/case rendering.s:ifcontent- Render wrappers only if they contain output.s:try- Wrap output in a try block with optional finally.s:finally- Optional sibling for s:try cleanup.
Examples
s:if
Render the element only when the expression evaluates to true.
<div s:if="$isReady">Ready</div><div s:if="!$isReady">Loading...</div>s:unless
Render the element only when the expression evaluates to false.
For more about empty/false checks, see Empty Checking.
<div s:unless="$isReady">Loading...</div>s:isset
Render the element when the variable is set (not null and defined).
<div s:isset="$user">Welcome, <?= $user->name ?></div>s:empty
Render the element when the value is empty.
For more about empty/false checks, see Empty Checking.
<div s:empty="$items">No items found</div>s:foreach
Repeat the element for every item in an iterable.
For full loop metadata details, see Loop Metadata.
<ul s:foreach="$items as $item">
<li><?= $item ?></li>
</ul><dl s:foreach="$stats as $label => $value">
<dt><?= $label ?></dt>
<dd><?= $value ?></dd>
</dl><ul s:foreach="$items as $item">
<li s:class="['first' => $loop->first, 'last' => $loop->last, 'odd' => $loop->odd]">
<?= $item ?> (<?= $loop->iteration ?> of <?= $loop->count ?>)
</li>
</ul>s:forelse
Loop over items and fall back to an s:empty sibling when empty.
For full loop metadata details, see Loop Metadata.
For more about empty/false checks, see Empty Checking.
<ul s:forelse="$items as $item">
<li><?= $item ?></li>
</ul>
<div s:empty>No items found</div><ul s:forelse="$items as $item">
<li s:class="['odd' => $loop->odd, 'even' => $loop->even]">
<?= $item ?> (<?= $loop->iteration ?>)
</li>
</ul>
<div s:empty>No items found</div>s:while
Repeat the element while a condition remains true.
<div s:while="$poller->hasNext()">
<?= $poller->next() ?>
</div>s:times
Repeat the element a fixed number of times.
<span s:times="3">*</span><span s:times="5 as $i">#<?= $i ?></span>s:switch
Choose between s:case and s:default children based on a value.
<div s:switch="$role">
<span s:case="'admin'">Administrator</span>
<span s:default>User</span>
</div><div s:switch="$status">
<span s:case="'open'">Open</span>
<span s:case="'closed'">Closed</span>
<span s:default>Unknown</span>
</div><div s:switch="$role">
<span s:case="'admin'">Administrator</span>
<span s:case="'moderator'">Moderator</span>
<span s:default>User</span>
</div>s:ifcontent
Render the wrapper only when it would contain output.
<div s:ifcontent class="card">
<?php if ($showContent): ?>
<p>Some content here</p>
<?php endif; ?>
</div>s:try / s:finally
Wrap output in a try block with an optional finally sibling. There is no s:catch directive; if s:finally is omitted, Sugar emits a catch that returns null to keep the PHP valid and silently stop output on errors.
<div s:try>
<?= $content ?>
</div>
<div s:finally>
<?php $logger->flush(); ?>
</div>