glacier-web-cli 0.5.0

Command-line tool for creating and running Glacier applications.
{% props field: Field, options: Vec<(String, String)>, label: String = "", prompt: String = "", description: String = "", source: String = "" %}
{#- The no-JS baseline, a native select; the combobox controller upgrades it to a searchable list (from `source`, an endpoint of option HTML, when given). -#}
{%- let label = if label.is_empty() { field.label.clone() } else { label } %}
{%- let note = if field.has_errors() { format!("{}-error", field.id) } else { format!("{}-description", field.id) } %}
<div class="ui-field" data-ui="combobox"{% if !source.is_empty() %} data-source="{{ source }}"{% end %}>
  <label class="ui-label" id="{{ field.id }}-label" for="{{ field.id }}">{{ label }}</label>
  <div class="ui-select-wrap">
    <select class="ui-native-select" id="{{ field.id }}" name="{{ field.name }}"{% if field.has_errors() || !description.is_empty() %} aria-describedby="{{ note }}"{% end %}{% if field.has_errors() %} aria-invalid="true"{% end %}>
      {%- if !prompt.is_empty() %}
      <option value="">{{ prompt }}</option>
      {%- end %}
      {%- for (value, text) in options.iter() %}
      <option value="{{ value }}"{% if *value == field.value %} selected{% end %}>{{ text }}</option>
      {%- end %}
    </select>
    <svg class="ui-icon" viewBox="0 0 24 24" aria-hidden="true"><path d="m7 15 5 5 5-5"/><path d="m7 9 5-5 5 5"/></svg>
  </div>
  {%- if field.has_errors() %}
  <p class="ui-field-error" id="{{ field.id }}-error">{%- for message in field.errors.iter() %}{{ label }} {{ message }}. {% end %}</p>
  {%- else %}{% if !description.is_empty() %}
  <p class="ui-field-description" id="{{ field.id }}-description">{{ description }}</p>
  {%- end %}{% end %}
</div>