Add more useful examples

This commit is contained in:
Ilia Ross
2026-09-07 15:13:53 +02:00
parent 75902910fc
commit 63d8d66f48
4 changed files with 88 additions and 8 deletions

View File

@@ -164,6 +164,12 @@ unlike(main::ui_page_start({ 'scheme' => 'bogus"' }),
qr/\bvalue=""/, 'toggle preserves an explicitly empty submitted value');
}
# Column tables take extra class names for the theme, such as no-hover
like(main::ui_columns_start([ 'A' ], undef, 0, undef, undef, 0, 'no-hover'),
qr/class='ui_columns no-hover'/, 'ui_columns_start adds the class argument');
like(main::ui_columns_start([ 'A' ]), qr/class='ui_columns'/,
'ui_columns_start without the class argument is unchanged');
# Search boxes carry the client-side filter target
like(main::ui_search({ 'name' => 'q', 'filter' => '#rows' }),
qr/data-ui-filter="#rows"/, 'search filter selector emitted');

View File

@@ -14,13 +14,13 @@ Every tab of `index.cgi` is built by one function in `ui-demo-pages.pl` :
|------------|-----------------------|------------------------------------------------------------------|
| Cards | `demo_cards_tab` | `ui_card` in its variations : buttons inside a card, header actions and footer, state accents with icon titles, a two-column `ui_dl`, a flush list filtered by a `ui_search` in the header, a standard table inside a card, a metric card with `ui_stat` and inline `ui_progress`, a card printed with `ui_card_start`/`ui_card_end`; `ui_stats`; `ui_grid` with the `template` option |
| Elements | `demo_elements_tab` | a `ui_dl` with help bubbles and HTML values, `ui_stats` with icons and links, `ui_feed` with an HTML event, `ui_empty_state`, then badges with their icon, dot and title options, chips, `ui_code`, `ui_note`, `ui_help`, `ui_tip`, every `ui_progress` variation and the ring gauges, and `ui_svg_icon` |
| Forms | `demo_forms_tab` | the usual `ui_table_start` / `ui_table_row` form with `ui_toggle`, `ui_search`, the date chooser and password fields; a second form of choosers : `file_chooser_button` for files and directories, `ui_user_textbox`, `ui_group_textbox`, `ui_users_textbox`, `ui_groups_textbox`, and an `hlink` help link |
| Forms | `demo_forms_tab` | the usual `ui_table_start` / `ui_table_row` form with `ui_toggle`, `ui_search`, the date chooser, password fields and a table of inputs inside one row built with `ui_columns_start` / `ui_columns_row` with the `no-hover` class, as the Nginx module's URL rewrites; a second form of choosers : `file_chooser_button` for files and directories, `ui_user_textbox`, `ui_group_textbox`, `ui_users_textbox`, `ui_groups_textbox`, and an `hlink` help link |
| Choices | `demo_choices_tab` | three replacements for `ui_radio_table` and hand-made tables of radios with inputs : `ui_choice` (boxed, every option's inputs visible), `ui_select_switch` (a select showing only the chosen option's block) and `ui_radio_list` (compact radios); the backup destination selector twice and Virtualmin's new IP address selectors |
| Buttons | `demo_buttons_tab` | `ui_submit`, `ui_reset` and `ui_link_button` in one row, with a disabled and a confirmed one; a form ended by `ui_form_end`, one by `ui_form_grouped_buttons`, one by `ui_form_end_side_by_side` with a separate form at the right; a `ui_confirmation_form` page |
| Accordions | `demo_accordions_tab` | a settings form of `ui_table_start` followed by `ui_hidden_table_start` sections |
| Tables | `demo_tables_tab` | the empty state shown instead of a table with no rows, `ui_columns_table` with a `ui_details` disclosure in its first cell (classes `inline inlined`, as grub2's boot entries), and `ui_form_columns_table`, both with the sortable flag; the tab description itself hides more text behind a `ui_details` tick (class `inline`), as Virtualmin's SSL page does |
| Lists | `demo_lists_tab` | `ui_list` rows with badges, tags, meta and actions; a backup history with state icons, a filesystem list with inline progress bars, and a user list with a confirmed delete link |
| Icon links | `demo_iconlinks_tab` | `icons_table` with SVG icons from `images/`, then a rule and the bottom-of-page `ui_buttons_row` block from `demo_page_actions` |
| Icon links | `demo_iconlinks_tab` | `icons_table` with SVG icons from `images/`, then under a rule the page's own settings form with Save and Delete, as the Nginx location page lays out icons above the form, then another rule and the bottom-of-page `ui_buttons_row` block from `demo_page_actions` |
| Config editor | `demo_editor_tab` | links to `edit_manual.cgi`, a manual config file editor page as in nftables : file selector form, then a large `ui_textarea` with Save, submitting to a `save_manual.cgi` that writes nothing |
| Alerts | `demo_alerts_tab` | every `ui_alert` type, one with a custom icon and title on one line, and an opened `ui_details` box with the `error` class under the error alert, as MariaDB shows its connection error |
@@ -73,7 +73,10 @@ not core API :
show/hide eye and the generate key next to password inputs on module
pages it knows, or on any page where a password input carries a
`data-password` attribute. Mark the repeat field `data-password-again`
and it only gets the eye. Pass the attribute in the tags argument of
and it only gets the eye. A field for a password that is typed in
rather than created, such as the FTP and SSH logins on the Choices
tab, is marked `data-password-meter-skip` and gets neither the meter nor the
generate button. Pass the attribute in the tags argument of
`ui_password`.
- **Code editor.** Authentic replaces the text area of a manual config
editor page with a code editor, and adds its own "Save and close" and

View File

@@ -16,7 +16,7 @@ index_buttons_desc=Single buttons come from ui_submit, ui_reset and ui_link_butt
index_accordions_desc=A settings page in the style of the grub2 module : a table of common settings first, then collapsible sections built with ui_hidden_table_start for the rest, all in one form.
index_tables_desc=Tables are the existing ui_columns_table and ui_form_columns_table, unchanged. The sortable parameter asks the theme for client-side sorting and searching.
index_lists_desc=Lists show entries with a title, a description and trailing details, and an empty state replaces an empty table.
index_iconlinks_desc=A table of icon links to sub-pages, built with the existing icons_table function and small SVG icons from the module, followed by a rule and the action buttons that end an index page. Modules such as SSH Server, grub2 and Webmin Configuration are laid out this way.
index_iconlinks_desc=A table of icon links to sub-pages, built with the existing icons_table function and small SVG icons from the module, then under a rule the form of the page itself with Save and Delete, as the Nginx location page is laid out, and finally the action buttons that end an index page, as in SSH Server, grub2 and Webmin Configuration.
index_service=Service
index_boot=Start at boot
index_boot_on=Enabled
@@ -314,3 +314,22 @@ index_b_delete=Delete server
index_f_search_ph=Search services
index_f_alerts=Email alerts
index_f_autoupdate=Automatic updates
index_f_rewrites=URLs to rewrite
index_f_rw_from=Original URL path
index_f_rw_to=New path or URL
index_f_rw_flag=Action after rewrite
index_f_rw_last=Restart processing
index_f_rw_break=Stop processing
index_f_rw_redirect=Return 302 redirect
index_f_rw_permanent=Return 301 redirect
index_i_header=URL path location options
index_i_path=URL path
index_i_match=Match type
index_i_match_default=Sub-directory
index_i_match_exact=Exact directory
index_i_match_case=Case sensitive regular expression
index_i_match_nocase=Case insensitive regular expression
index_i_match_noregexp=Disable regular expressions
index_i_root=Default root directory
index_i_delete=Delete location
index_i_delete_confirm=Delete this location and all of its settings?

View File

@@ -535,6 +535,33 @@ $rv .= ui_table_row($text{'index_f_dates'},
demo_date_input('to'))."</span>" ] ]));
$rv .= ui_table_row($text{'index_f_notes'},
ui_textarea('notes', "# ".$text{'index_f_notes_value'}, 4, 60));
# A table of inputs inside a form row, as the Nginx module edits URL
# rewrites : ui_columns_start with the headings, nowrap cells and the
# class argument set to no-hover, so the theme does not highlight rows
# that are inputs, one ui_columns_row per existing entry plus two empty
# rows for new ones, then the whole table as the value of a row spanning
# the form (third argument 3). Inputs are numbered by row, and the save script walks
# the numbers until the first missing from-field, skipping empty rows.
my @rewrites = ( [ '^/old/(.*)$', '/new/$1', 'permanent' ],
[ '^/api/v1/(.*)$', '/api/v2/$1', 'last' ] );
my $rtable = ui_columns_start([ $text{'index_f_rw_from'},
$text{'index_f_rw_to'},
$text{'index_f_rw_flag'} ], 100, 0,
[ 'nowrap', 'nowrap' ], undef, 0, 'no-hover');
my $rn = 0;
foreach my $r (@rewrites, [ ], [ ]) {
$rtable .= ui_columns_row([
ui_textbox("rw_from_$rn", $r->[0], 30),
ui_textbox("rw_to_$rn", $r->[1], 40),
ui_select("rw_flag_$rn", $r->[2],
[ map { [ $_, $text{'index_f_rw_'.$_} ] }
('last', 'break', 'redirect', 'permanent') ]),
]);
$rn++;
}
$rtable .= ui_columns_end();
$rv .= ui_table_row($text{'index_f_rewrites'}, $rtable, 3);
$rv .= ui_table_end();
$rv .= ui_form_end([ [ 'save', $text{'save'} ],
[ 'cancel', $text{'index_f_cancel'} ],
@@ -1140,7 +1167,8 @@ return $rv;
# demo_iconlinks_tab()
# Returns the icon links panel : a grid of linked icons with titles under
# them, as the grub2 and Webmin Configuration modules show their
# sub-pages. This is the existing icons_table(&links, &titles, &icons,
# sub-pages, then the form of the page itself under a rule, as the Nginx
# location page, then the buttons that end an index page. This is the existing icons_table(&links, &titles, &icons,
# columns) function. The icons are small SVG files in the module's images
# directory, 48x48 like those of grub2. icons_table prints rather than
# returns, so its output is captured here.
@@ -1153,9 +1181,33 @@ my $rv = capture_function_output(\&icons_table,
[ map { "images/$_.svg" } @pages ],
scalar(@pages));
# Then the bottom-of-page action buttons after a rule, as the SSH Server
# and grub2 modules end their index page : icons first, a rule, then the
# buttons
# Under the icons, the settings of the page itself, as the Nginx module's
# location page puts the form of the location below the icons of its
# sub-pages : a rule, a two-column ui_table_start form, and Save next to
# a Delete button. A row whose input is wide spans the form with a third
# argument of 3. The file chooser needs the index of this form on the
# page, 13 here : the Tables tab counts the forms before its own, and
# this one follows it.
$rv .= ui_hr();
$rv .= ui_form_start('index.cgi', 'post');
$rv .= ui_hidden('demo', 9);
$rv .= ui_table_start($text{'index_i_header'}, 'width=100%', 2);
$rv .= ui_table_row($text{'index_i_path'},
ui_textbox('lpath', '/.well-known/', 60));
$rv .= ui_table_row($text{'index_i_match'},
ui_select('lmatch', 'noregexp',
[ map { [ $_, $text{'index_i_match_'.$_} ] }
('default', 'exact', 'case', 'nocase', 'noregexp') ]));
$rv .= ui_table_row($text{'index_i_root'},
ui_textbox('lroot', '', 60)." ".file_chooser_button('lroot', 1, 13), 3);
$rv .= ui_table_end();
$rv .= ui_form_end([ [ undef, $text{'save'} ],
[ 'delete', $text{'index_i_delete'}, undef, 0,
"data-ui-confirm='".
quote_escape($text{'index_i_delete_confirm'})."'" ] ]);
# Then the bottom-of-page action buttons after another rule, as the SSH
# Server and grub2 modules end their index page
$rv .= demo_page_actions();
return $rv;
}