Merge pull request #6596 from dennisreimann/fix-6592

Forms: Properly support checkbox type
This commit is contained in:
Nicolas Dorier 2025-02-11 14:24:16 +09:00 committed by GitHub
commit 63750d69c4
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
4 changed files with 47 additions and 27 deletions

View file

@ -11,13 +11,9 @@ public class HtmlInputFormProvider : FormComponentProviderBase
{
foreach (var t in new[] {
"text",
"radio",
"checkbox",
"password",
"file",
"hidden",
"button",
"submit",
"color",
"date",
"datetime-local",
@ -25,13 +21,9 @@ public class HtmlInputFormProvider : FormComponentProviderBase
"week",
"time",
"email",
"image",
"number",
"range",
"search",
"url",
"tel",
"reset"})
"tel"})
typeToComponentProvider.Add(t, this);
}
public override string View => "Forms/InputElement";

View file

@ -1,6 +1,7 @@
@model BTCPayServer.Abstractions.Form.Field
@{
var isInvalid = ViewContext.ModelState[Model.Name]?.ValidationState is Microsoft.AspNetCore.Mvc.ModelBinding.ModelValidationState.Invalid;
var isCheckbox = Model.Type == "checkbox";
var errors = isInvalid ? ViewContext.ModelState[Model.Name].Errors : null;
}
@if (Model.Type == "hidden")
@ -8,21 +9,43 @@
<input id="@Model.Name" type="@Model.Type" name="@Model.Name" value="@Model.Value" />
return;
}
<div class="form-group">
<label class="form-label" for="@Model.Name"@(Model.Required ? " data-required" : "")>
@Safe.Raw(Model.Label)
</label>
<input id="@Model.Name" type="@Model.Type" class="form-control @(errors is null ? "" : "is-invalid")"
name="@Model.Name" value="@Model.Value" data-val="true" readonly="@Model.Constant"
@if (!string.IsNullOrEmpty(Model.HelpText))
{
@Safe.Raw($" aria-describedby=\"HelpText-{Model.Name}\"")
}
@if (Model.Required)
{
@Safe.Raw($" data-val-required=\"{Model.Label} is required.\" required")
}
/>
<div class="form-@(isCheckbox ? "check" : "group")">
@if (isCheckbox)
{
<input id="@Model.Name" type="@Model.Type" class="form-check-input @(errors is null ? "" : "is-invalid")"
name="@Model.Name" value="true" data-val="true" readonly="@Model.Constant"
@if (Model.Value == "true")
{
@Safe.Raw(" checked")
}
@if (!string.IsNullOrEmpty(Model.HelpText))
{
@Safe.Raw($" aria-describedby=\"HelpText-{Model.Name}\"")
}
@if (Model.Required)
{
@Safe.Raw($" data-val-required=\"{Model.Label} is required.\" required")
} />
<label class="form-check-label" for="@Model.Name"@(Model.Required ? " data-required" : "")>
@Safe.Raw(Model.Label)
</label>
}
else
{
<label class="form-label" for="@Model.Name"@(Model.Required ? " data-required" : "")>
@Safe.Raw(Model.Label)
</label>
<input id="@Model.Name" type="@Model.Type" class="form-control @(errors is null ? "" : "is-invalid")"
name="@Model.Name" value="@Model.Value" data-val="true" readonly="@Model.Constant"
@if (!string.IsNullOrEmpty(Model.HelpText))
{
@Safe.Raw($" aria-describedby=\"HelpText-{Model.Name}\"")
}
@if (Model.Required)
{
@Safe.Raw($" data-val-required=\"{Model.Label} is required.\" required")
} />
}
<span class="text-danger" data-valmsg-for="@Model.Name" data-valmsg-replace="true">@(isInvalid && errors.Any() ? errors.First().ErrorMessage : string.Empty)</span>
@if (!string.IsNullOrEmpty(Model.HelpText))
{

View file

@ -149,7 +149,12 @@
</div>
</template>
<template id="field-type-input">
<div class="form-group mb-0">
<div class="form-check mb-0" v-if="type === 'checkbox'">
<input class="form-check-input" :id="name" :name="name" :type="type" v-model="value" />
<label class="form-check-label" :for="name" :data-required="required" v-sanitize="label"></label>
<div v-if="helpText" :id="`HelpText-{name}`" class="form-text" v-sanitize="helpText"></div>
</div>
<div class="form-groupcheck mb-0" v-else>
<label class="form-label" :for="name" :data-required="required" v-sanitize="label"></label>
<input class="form-control" :id="name" :name="name" :type="type" v-model="value" />
<div v-if="helpText" :id="`HelpText-{name}`" class="form-text" v-sanitize="helpText"></div>
@ -208,7 +213,7 @@
</h2>
</nav>
<div>
<button id="page-primary" type="submit" class="btn btn-primary order-sm-1">Save</button>
<button id="page-primary" type="submit" class="btn btn-primary order-sm-1">Save</button>
@if (!isNew)
{
<a class="btn btn-secondary" asp-action="ViewPublicForm" asp-route-formId="@formId" id="ViewForm" text-translate="true">View</a>

View file

@ -10,7 +10,7 @@ document.addEventListener('DOMContentLoaded', () => {
let config = parseConfig($config.value) || {}
const specialFieldTypeOptions = ['fieldset', 'textarea', 'select', 'mirror']
const inputFieldTypeOptions = ['text', 'number', 'password', 'email', 'url', 'tel', 'date', 'hidden']
const inputFieldTypeOptions = ['text', 'number', 'password', 'email', 'url', 'tel', 'date', 'datetime-local', 'color', 'checkbox', 'hidden']
const fieldTypeOptions = inputFieldTypeOptions.concat(specialFieldTypeOptions)
const getFieldComponent = type => `field-type-${specialFieldTypeOptions.includes(type) ? type : 'input'}`