Progress Telerik 教程(七):表单与验证完全指南

作者:微信公众号:【架构师老卢】
9-25 18:30
26

Progress Telerik Ultimate Collection 2025 Q2下载地址 https://soft51.cc/software/175792580241152290

1. 表单控件概述

表单是Web应用程序中用户交互的核心界面,Telerik UI提供了丰富的表单控件和强大的验证功能。

1.1 主要表单控件

输入控件:

  • TextBox(文本输入)
  • NumericTextBox(数字输入)
  • MaskedTextBox(格式化输入)
  • DatePicker(日期选择)

选择控件:

  • DropDownList(下拉列表)
  • ComboBox(可编辑下拉框)
  • MultiSelect(多选列表)
  • Switch(开关)

特殊控件:

  • Upload(文件上传)
  • Editor(富文本编辑器)
  • Slider(滑块)

2. 表单控件布局

2.1 基础表单布局

<div class="container">
    <div class="card">
        <div class="card-header">
            <h4>用户注册表单</h4>
        </div>
        <div class="card-body">
            @using (Html.BeginForm("Register", "User", FormMethod.Post))
            {
                <!-- 基本信息组 -->
                <fieldset class="border p-3 mb-4">
                    <legend>基本信息</legend>
                    
                    <div class="row">
                        <div class="col-md-6">
                            <div class="form-group mb-3">
                                <label class="form-label required">用户名</label>
                                @(Html.Kendo().TextBox()
                                    .Name("Username")
                                    .Placeholder("请输入用户名")
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                        </div>
                        
                        <div class="col-md-6">
                            <div class="form-group mb-3">
                                <label class="form-label required">邮箱地址</label>
                                @(Html.Kendo().TextBox()
                                    .Name("Email")
                                    .Placeholder("请输入邮箱")
                                    .HtmlAttributes(new { 
                                        @class = "form-control",
                                        type = "email"
                                    })
                                )
                            </div>
                        </div>
                    </div>
                    
                    <div class="row">
                        <div class="col-md-6">
                            <div class="form-group mb-3">
                                <label class="form-label required">密码</label>
                                @(Html.Kendo().TextBox()
                                    .Name("Password")
                                    .HtmlAttributes(new { 
                                        @class = "form-control",
                                        type = "password"
                                    })
                                )
                                <div class="form-text">密码长度至少6位</div>
                            </div>
                        </div>
                        
                        <div class="col-md-6">
                            <div class="form-group mb-3">
                                <label class="form-label">手机号码</label>
                                @(Html.Kendo().MaskedTextBox()
                                    .Name("Phone")
                                    .Mask("000-0000-0000")
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                        </div>
                    </div>
                </fieldset>
                
                <!-- 个人信息组 -->
                <fieldset class="border p-3 mb-4">
                    <legend>个人信息</legend>
                    
                    <div class="row">
                        <div class="col-md-4">
                            <div class="form-group mb-3">
                                <label class="form-label">性别</label>
                                @(Html.Kendo().DropDownList()
                                    .Name("Gender")
                                    .BindTo(new[]
                                    {
                                        new { Value = "", Text = "请选择" },
                                        new { Value = "Male", Text = "男" },
                                        new { Value = "Female", Text = "女" }
                                    })
                                    .DataTextField("Text")
                                    .DataValueField("Value")
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                        </div>
                        
                        <div class="col-md-4">
                            <div class="form-group mb-3">
                                <label class="form-label">出生日期</label>
                                @(Html.Kendo().DatePicker()
                                    .Name("BirthDate")
                                    .Format("yyyy-MM-dd")
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                        </div>
                        
                        <div class="col-md-4">
                            <div class="form-group mb-3">
                                <label class="form-label">年龄</label>
                                @(Html.Kendo().NumericTextBox()
                                    .Name("Age")
                                    .Min(18)
                                    .Max(100)
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                        </div>
                    </div>
                    
                    <div class="form-group mb-3">
                        <label class="form-label">技能标签</label>
                        @(Html.Kendo().MultiSelect()
                            .Name("Skills")
                            .BindTo(new[] { "JavaScript", "C#", "Python", "Java", "React" })
                            .Placeholder("选择您的技能")
                            .HtmlAttributes(new { @class = "form-control" })
                        )
                    </div>
                    
                    <div class="form-group mb-3">
                        <label class="form-label">个人简介</label>
                        @(Html.Kendo().TextArea()
                            .Name("Biography")
                            .Rows(4)
                            .HtmlAttributes(new { @class = "form-control" })
                        )
                    </div>
                </fieldset>
                
                <!-- 协议确认 -->
                <div class="form-group mb-4">
                    <div class="form-check">
                        @(Html.Kendo().Switch()
                            .Name("AcceptTerms")
                            .Messages(messages => messages
                                .Checked("已同意")
                                .Unchecked("未同意")
                            )
                        )
                        <label class="form-check-label ms-3">
                            我已阅读并同意用户协议和隐私政策
                        </label>
                    </div>
                </div>
                
                <!-- 提交按钮 -->
                <div class="form-actions">
                    <button type="button" class="btn btn-secondary me-3" onclick="resetForm()">
                        重置
                    </button>
                    <button type="submit" class="btn btn-primary">
                        注册账户
                    </button>
                </div>
            }
        </div>
    </div>
</div>

<style>
.required::after {
    content: " *";
    color: #dc3545;
}

fieldset {
    border-color: #dee2e6 !important;
    border-radius: 0.375rem;
}

fieldset legend {
    font-size: 1rem;
    font-weight: 600;
    color: #495057;
}

.form-actions {
    padding-top: 1rem;
    border-top: 1px solid #dee2e6;
}
</style>

2.2 响应式步骤表单

<div class="container">
    <div class="card">
        <div class="card-header">
            <h4>分步注册表单</h4>
            <div class="progress mt-2" style="height: 4px;">
                <div class="progress-bar" id="formProgress" style="width: 25%"></div>
            </div>
        </div>
        <div class="card-body">
            <!-- 步骤导航 -->
            <ul class="nav nav-pills nav-justified mb-4">
                <li class="nav-item">
                    <span class="nav-link active" id="step1-tab">基本信息</span>
                </li>
                <li class="nav-item">
                    <span class="nav-link" id="step2-tab">账户设置</span>
                </li>
                <li class="nav-item">
                    <span class="nav-link" id="step3-tab">完成注册</span>
                </li>
            </ul>
            
            <!-- 步骤内容 -->
            <div class="step-content">
                <!-- 步骤1 -->
                <div class="step" id="step1">
                    <h5 class="mb-3">基本信息</h5>
                    <div class="row">
                        <div class="col-md-6">
                            <div class="form-group mb-3">
                                <label class="form-label required">姓名</label>
                                @(Html.Kendo().TextBox()
                                    .Name("FullName")
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                        </div>
                        <div class="col-md-6">
                            <div class="form-group mb-3">
                                <label class="form-label required">邮箱</label>
                                @(Html.Kendo().TextBox()
                                    .Name("Email")
                                    .HtmlAttributes(new { 
                                        @class = "form-control",
                                        type = "email"
                                    })
                                )
                            </div>
                        </div>
                    </div>
                    
                    <div class="form-group mb-3">
                        <label class="form-label">公司名称</label>
                        @(Html.Kendo().TextBox()
                            .Name("Company")
                            .HtmlAttributes(new { @class = "form-control" })
                        )
                    </div>
                </div>
                
                <!-- 步骤2 -->
                <div class="step" id="step2" style="display: none;">
                    <h5 class="mb-3">账户设置</h5>
                    <div class="row">
                        <div class="col-md-6">
                            <div class="form-group mb-3">
                                <label class="form-label required">用户名</label>
                                @(Html.Kendo().TextBox()
                                    .Name("Username")
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                        </div>
                        <div class="col-md-6">
                            <div class="form-group mb-3">
                                <label class="form-label required">密码</label>
                                @(Html.Kendo().TextBox()
                                    .Name("Password")
                                    .HtmlAttributes(new { 
                                        @class = "form-control",
                                        type = "password"
                                    })
                                )
                            </div>
                        </div>
                    </div>
                    
                    <div class="form-group mb-3">
                        <label class="form-label">偏好设置</label>
                        @(Html.Kendo().MultiSelect()
                            .Name("Preferences")
                            .BindTo(new[] { "邮件通知", "短信提醒", "系统推送" })
                            .HtmlAttributes(new { @class = "form-control" })
                        )
                    </div>
                </div>
                
                <!-- 步骤3 -->
                <div class="step" id="step3" style="display: none;">
                    <h5 class="mb-3">确认信息</h5>
                    <div id="confirmationContent">
                        <!-- 动态生成确认内容 -->
                    </div>
                    
                    <div class="alert alert-info">
                        请确认以上信息无误后提交注册。
                    </div>
                </div>
            </div>
            
            <!-- 导航按钮 -->
            <div class="step-navigation mt-4">
                <button type="button" class="btn btn-outline-secondary" id="prevBtn" onclick="previousStep()">
                    上一步
                </button>
                <button type="button" class="btn btn-primary float-end" id="nextBtn" onclick="nextStep()">
                    下一步
                </button>
                <button type="button" class="btn btn-success float-end" id="submitBtn" onclick="submitForm()" style="display: none;">
                    提交注册
                </button>
            </div>
        </div>
    </div>
</div>

<script>
let currentStep = 1;
const totalSteps = 3;

function nextStep() {
    if (currentStep < totalSteps) {
        currentStep++;
        updateStepDisplay();
        
        if (currentStep === totalSteps) {
            generateConfirmation();
        }
    }
}

function previousStep() {
    if (currentStep > 1) {
        currentStep--;
        updateStepDisplay();
    }
}

function updateStepDisplay() {
    // 隐藏所有步骤
    $('.step').hide();
    $('#step' + currentStep).show();
    
    // 更新导航
    $('.nav-link').removeClass('active');
    $('#step' + currentStep + '-tab').addClass('active');
    
    // 更新进度条
    const progress = (currentStep / totalSteps) * 100;
    $('#formProgress').css('width', progress + '%');
    
    // 更新按钮
    $('#prevBtn').toggle(currentStep > 1);
    $('#nextBtn').toggle(currentStep < totalSteps);
    $('#submitBtn').toggle(currentStep === totalSteps);
}

function generateConfirmation() {
    const confirmHtml = 
        '<table class="table">' +
        '<tr><td><strong>姓名:</strong></td><td>' + $('[name="FullName"]').val() + '</td></tr>' +
        '<tr><td><strong>邮箱:</strong></td><td>' + $('[name="Email"]').val() + '</td></tr>' +
        '<tr><td><strong>公司:</strong></td><td>' + $('[name="Company"]').val() + '</td></tr>' +
        '<tr><td><strong>用户名:</strong></td><td>' + $('[name="Username"]').val() + '</td></tr>' +
        '</table>';
    
    $('#confirmationContent').html(confirmHtml);
}

function submitForm() {
    showNotification("注册成功!", "success");
}

$(document).ready(function() {
    updateStepDisplay();
});
</script>

3. 数据验证与错误提示

3.1 客户端验证

<!-- 验证器配置 -->
@(Html.Kendo().Validator()
    .For("#validationForm")
    .Rules(rules => {
        rules.Add("usernameFormat", @<text>
            function(input) {
                if (input.is("[name='Username']")) {
                    return /^[a-zA-Z0-9_]{3,20}$/.test(input.val());
                }
                return true;
            }
        </text>);
        
        rules.Add("passwordStrength", @<text>
            function(input) {
                if (input.is("[name='Password']")) {
                    var value = input.val();
                    return value.length >= 6 && 
                           /[A-Z]/.test(value) && 
                           /[a-z]/.test(value) && 
                           /[0-9]/.test(value);
                }
                return true;
            }
        </text>);
    })
    .Messages(messages => {
        messages.Add("usernameFormat", "用户名格式不正确");
        messages.Add("passwordStrength", "密码强度不够");
    })
)

<form id="validationForm">
    <div class="form-group mb-3">
        <label class="form-label required">用户名</label>
        @(Html.Kendo().TextBox()
            .Name("Username")
            .HtmlAttributes(new { 
                @class = "form-control",
                required = "required"
            })
        )
        <span class="k-invalid-msg" data-for="Username"></span>
        <div class="form-text">3-20位字母、数字或下划线</div>
    </div>
    
    <div class="form-group mb-3">
        <label class="form-label required">邮箱地址</label>
        @(Html.Kendo().TextBox()
            .Name("Email")
            .HtmlAttributes(new { 
                @class = "form-control",
                type = "email",
                required = "required"
            })
        )
        <span class="k-invalid-msg" data-for="Email"></span>
    </div>
    
    <div class="form-group mb-3">
        <label class="form-label required">密码</label>
        @(Html.Kendo().TextBox()
            .Name("Password")
            .HtmlAttributes(new { 
                @class = "form-control",
                type = "password",
                required = "required"
            })
        )
        <div class="password-strength mt-2">
            <div class="progress" style="height: 4px;">
                <div class="progress-bar" id="strengthBar"></div>
            </div>
            <small id="strengthText">请输入密码</small>
        </div>
        <span class="k-invalid-msg" data-for="Password"></span>
    </div>
    
    <div class="form-group mb-3">
        <label class="form-label required">年龄</label>
        @(Html.Kendo().NumericTextBox()
            .Name("Age")
            .Min(18)
            .Max(100)
            .HtmlAttributes(new { 
                @class = "form-control",
                required = "required"
            })
        )
        <span class="k-invalid-msg" data-for="Age"></span>
    </div>
    
    <button type="submit" class="btn btn-primary">提交</button>
</form>

<script>
$(document).ready(function() {
    var validator = $("#validationForm").kendoValidator().data("kendoValidator");
    
    // 表单提交处理
    $("#validationForm").on("submit", function(e) {
        e.preventDefault();
        
        if (validator.validate()) {
            showNotification("表单验证通过", "success");
        } else {
            showNotification("请修正表单错误", "error");
        }
    });
    
    // 密码强度检测
    $("[name='Password']").on("input", function() {
        checkPasswordStrength($(this).val());
    });
});

function checkPasswordStrength(password) {
    var strength = 0;
    var strengthText = "";
    var strengthClass = "";
    
    if (password.length >= 6) strength++;
    if (/[a-z]/.test(password)) strength++;
    if (/[A-Z]/.test(password)) strength++;
    if (/[0-9]/.test(password)) strength++;
    
    switch (strength) {
        case 0:
        case 1:
            strengthText = "密码强度:弱";
            strengthClass = "bg-danger";
            break;
        case 2:
        case 3:
            strengthText = "密码强度:中";
            strengthClass = "bg-warning";
            break;
        case 4:
            strengthText = "密码强度:强";
            strengthClass = "bg-success";
            break;
    }
    
    var percentage = (strength / 4) * 100;
    $("#strengthBar").css("width", percentage + "%").attr("class", "progress-bar " + strengthClass);
    $("#strengthText").text(strengthText);
}
</script>

3.2 服务器端验证

// 数据模型
public class UserModel
{
    [Required(ErrorMessage = "用户名不能为空")]
    [StringLength(20, MinimumLength = 3, ErrorMessage = "用户名长度3-20位")]
    [RegularExpression(@"^[a-zA-Z0-9_]+$", ErrorMessage = "用户名只能包含字母数字下划线")]
    public string Username { get; set; }

    [Required(ErrorMessage = "邮箱不能为空")]
    [EmailAddress(ErrorMessage = "邮箱格式不正确")]
    public string Email { get; set; }

    [Required(ErrorMessage = "密码不能为空")]
    [MinLength(6, ErrorMessage = "密码至少6位")]
    public string Password { get; set; }

    [Range(18, 100, ErrorMessage = "年龄必须在18-100之间")]
    public int Age { get; set; }
}

// 控制器验证
[HttpPost]
public async Task<IActionResult> Register(UserModel model)
{
    // 额外验证
    if (await IsUsernameTaken(model.Username))
    {
        ModelState.AddModelError("Username", "用户名已被使用");
    }

    if (!ModelState.IsValid)
    {
        return Json(new { 
            success = false, 
            errors = ModelState.ToDictionary(
                kvp => kvp.Key,
                kvp => kvp.Value.Errors.Select(e => e.ErrorMessage).ToArray()
            )
        });
    }

    // 创建用户
    await CreateUser(model);
    return Json(new { success = true, message = "注册成功" });
}

3.3 实时验证示例

<form id="realTimeForm">
    <div class="form-group mb-3">
        <label class="form-label">用户名</label>
        @(Html.Kendo().TextBox()
            .Name("Username")
            .HtmlAttributes(new { @class = "form-control" })
            .Events(events => events.Change("checkUsername"))
        )
        <div class="validation-status" id="usernameStatus"></div>
    </div>
    
    <div class="form-group mb-3">
        <label class="form-label">确认密码</label>
        @(Html.Kendo().TextBox()
            .Name("ConfirmPassword")
            .HtmlAttributes(new { 
                @class = "form-control",
                type = "password"
            })
            .Events(events => events.Change("checkPasswordMatch"))
        )
        <div class="validation-status" id="confirmStatus"></div>
    </div>
</form>

<script>
function checkUsername() {
    var username = $("[name='Username']").val();
    if (username.length < 3) return;
    
    $("#usernameStatus").html('<i class="fa fa-spinner fa-spin"></i> 检查中...');
    
    $.post('/User/CheckUsername', { username: username }, function(result) {
        if (result.available) {
            $("#usernameStatus").html('<i class="fa fa-check text-success"></i> 用户名可用');
        } else {
            $("#usernameStatus").html('<i class="fa fa-times text-danger"></i> 用户名已被使用');
        }
    });
}

function checkPasswordMatch() {
    var password = $("[name='Password']").val();
    var confirmPassword = $("[name='ConfirmPassword']").val();
    
    if (confirmPassword) {
        if (password === confirmPassword) {
            $("#confirmStatus").html('<i class="fa fa-check text-success"></i> 密码匹配');
        } else {
            $("#confirmStatus").html('<i class="fa fa-times text-danger"></i> 密码不匹配');
        }
    }
}
</script>

4. 综合实例:完整注册表单

<div class="container">
    <div class="row justify-content-center">
        <div class="col-lg-8">
            <div class="card">
                <div class="card-header">
                    <h4>用户注册</h4>
                </div>
                <div class="card-body">
                    <form id="registrationForm">
                        <!-- 基本信息 -->
                        <div class="form-section mb-4">
                            <h5>基本信息</h5>
                            
                            <div class="row">
                                <div class="col-md-6">
                                    <div class="form-group mb-3">
                                        <label class="form-label required">用户名</label>
                                        @(Html.Kendo().TextBox()
                                            .Name("Username")
                                            .HtmlAttributes(new { @class = "form-control" })
                                        )
                                        <span class="k-invalid-msg" data-for="Username"></span>
                                    </div>
                                </div>
                                
                                <div class="col-md-6">
                                    <div class="form-group mb-3">
                                        <label class="form-label required">邮箱</label>
                                        @(Html.Kendo().TextBox()
                                            .Name("Email")
                                            .HtmlAttributes(new { 
                                                @class = "form-control",
                                                type = "email"
                                            })
                                        )
                                        <span class="k-invalid-msg" data-for="Email"></span>
                                    </div>
                                </div>
                            </div>
                            
                            <div class="row">
                                <div class="col-md-6">
                                    <div class="form-group mb-3">
                                        <label class="form-label required">密码</label>
                                        @(Html.Kendo().TextBox()
                                            .Name("Password")
                                            .HtmlAttributes(new { 
                                                @class = "form-control",
                                                type = "password"
                                            })
                                        )
                                        <span class="k-invalid-msg" data-for="Password"></span>
                                    </div>
                                </div>
                                
                                <div class="col-md-6">
                                    <div class="form-group mb-3">
                                        <label class="form-label required">确认密码</label>
                                        @(Html.Kendo().TextBox()
                                            .Name("ConfirmPassword")
                                            .HtmlAttributes(new { 
                                                @class = "form-control",
                                                type = "password"
                                            })
                                        )
                                        <span class="k-invalid-msg" data-for="ConfirmPassword"></span>
                                    </div>
                                </div>
                            </div>
                        </div>
                        
                        <!-- 个人信息 -->
                        <div class="form-section mb-4">
                            <h5>个人信息</h5>
                            
                            <div class="row">
                                <div class="col-md-4">
                                    <div class="form-group mb-3">
                                        <label class="form-label">姓名</label>
                                        @(Html.Kendo().TextBox()
                                            .Name("FullName")
                                            .HtmlAttributes(new { @class = "form-control" })
                                        )
                                    </div>
                                </div>
                                
                                <div class="col-md-4">
                                    <div class="form-group mb-3">
                                        <label class="form-label">性别</label>
                                        @(Html.Kendo().DropDownList()
                                            .Name("Gender")
                                            .BindTo(new[]
                                            {
                                                new { Value = "", Text = "请选择" },
                                                new { Value = "Male", Text = "男" },
                                                new { Value = "Female", Text = "女" }
                                            })
                                            .DataTextField("Text")
                                            .DataValueField("Value")
                                            .HtmlAttributes(new { @class = "form-control" })
                                        )
                                    </div>
                                </div>
                                
                                <div class="col-md-4">
                                    <div class="form-group mb-3">
                                        <label class="form-label">出生日期</label>
                                        @(Html.Kendo().DatePicker()
                                            .Name("BirthDate")
                                            .Format("yyyy-MM-dd")
                                            .HtmlAttributes(new { @class = "form-control" })
                                        )
                                    </div>
                                </div>
                            </div>
                            
                            <div class="form-group mb-3">
                                <label class="form-label">手机号码</label>
                                @(Html.Kendo().MaskedTextBox()
                                    .Name("Phone")
                                    .Mask("000-0000-0000")
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                            
                            <div class="form-group mb-3">
                                <label class="form-label">个人简介</label>
                                @(Html.Kendo().TextArea()
                                    .Name("Biography")
                                    .Rows(3)
                                    .HtmlAttributes(new { @class = "form-control" })
                                )
                            </div>
                        </div>
                        
                        <!-- 协议确认 -->
                        <div class="form-group mb-4">
                            <div class="form-check">
                                @(Html.Kendo().Switch()
                                    .Name("AcceptTerms")
                                    .HtmlAttributes(new { required = "required" })
                                )
                                <label class="form-check-label ms-3">
                                    我已阅读并同意用户协议
                                </label>
                            </div>
                        </div>
                        
                        <!-- 提交按钮 -->
                        <div class="text-center">
                            <button type="button" class="btn btn-secondary me-3" onclick="resetForm()">
                                重置表单
                            </button>
                            <button type="submit" class="btn btn-primary">
                                提交注册
                            </button>
                        </div>
                    </form>
                </div>
            </div>
        </div>
    </div>
</div>

<!-- 验证器配置 -->
@(Html.Kendo().Validator()
    .For("#registrationForm")
    .Rules(rules => {
        rules.Add("usernameFormat", @<text>
            function(input) {
                if (input.is("[name='Username']")) {
                    return /^[a-zA-Z0-9_]{3,20}$/.test(input.val());
                }
                return true;
            }
        </text>);
        
        rules.Add("passwordStrength", @<text>
            function(input) {
                if (input.is("[name='Password']")) {
                    var value = input.val();
                    return value.length >= 6;
                }
                return true;
            }
        </text>);
        
        rules.Add("confirmPassword", @<text>
            function(input) {
                if (input.is("[name='ConfirmPassword']")) {
                    return input.val() === $("[name='Password']").val();
                }
                return true;
            }
        </text>);
    })
    .Messages(messages => {
        messages.Add("usernameFormat", "用户名格式不正确(3-20位字母数字下划线)");
        messages.Add("passwordStrength", "密码至少6位字符");
        messages.Add("confirmPassword", "两次输入的密码不一致");
    })
)

<script>
$(document).ready(function() {
    var validator = $("#registrationForm").kendoValidator().data("kendoValidator");
    
    // 表单提交处理
    $("#registrationForm").on("submit", function(e) {
        e.preventDefault();
        
        if (validator.validate()) {
            submitRegistration();
        } else {
            showNotification("请修正表单中的错误", "error");
        }
    });
    
    // 实时密码匹配检查
    $("[name='ConfirmPassword']").on("input", function() {
        var password = $("[name='Password']").val();
        var confirmPassword = $(this).val();
        
        if (confirmPassword && password !== confirmPassword) {
            $(this).addClass("k-invalid");
        } else {
            $(this).removeClass("k-invalid");
        }
    });
});

function submitRegistration() {
    showLoadingNotification("正在提交注册信息...");
    
    var formData = {
        Username: $("[name='Username']").val(),
        Email: $("[name='Email']").val(),
        Password: $("[name='Password']").val(),
        FullName: $("[name='FullName']").val(),
        Gender: $("[name='Gender']").data("kendoDropDownList").value(),
        Phone: $("[name='Phone']").val(),
        Biography: $("[name='Biography']").val(),
        AcceptTerms: $("[name='AcceptTerms']").data("kendoSwitch").check()
    };
    
    $.post('/User/Register', formData, function(result) {
        hideLoadingNotification();
        
        if (result.success) {
            showNotification("注册成功!", "success");
            resetForm();
        } else {
            showNotification("注册失败:" + result.message, "error");
        }
    });
}

function resetForm() {
    $("#registrationForm")[0].reset();
    
    // 重置Telerik控件
    $("[data-role]").each(function() {
        var widget = kendo.widgetInstance($(this));
        if (widget && typeof widget.value === 'function') {
            widget.value("");
        }
    });
    
    $(".k-invalid").removeClass("k-invalid");
    showNotification("表单已重置", "info");
}

// 工具函数
var loadingNotification;

function showLoadingNotification(message) {
    hideLoadingNotification();
    loadingNotification = showNotification(
        '<i class="fa fa-spinner fa-spin me-2"></i>' + message,
        "info"
    );
}

function hideLoadingNotification() {
    if (loadingNotification) {
        loadingNotification = null;
    }
}

function showNotification(message, type) {
    var alertClass = 'alert-info';
    switch(type) {
        case 'success': alertClass = 'alert-success'; break;
        case 'error': alertClass = 'alert-danger'; break;
        case 'warning': alertClass = 'alert-warning'; break;
    }
    
    var alert = $('<div class="alert ' + alertClass + ' alert-dismissible fade show position-fixed" style="top: 20px; right: 20px; z-index: 9999;">' +
                  message +
                  '<button type="button" class="btn-close" data-bs-dismiss="alert"></button>' +
                  '</div>');
    
    $('body').append(alert);
    
    setTimeout(function() {
        alert.alert('close');
    }, 3000);
    
    return alert;
}
</script>

<style>
.form-section {
    border: 1px solid #e9ecef;
    border-radius: 0.375rem;
    padding: 1.5rem;
}

.form-section h5 {
    color: #495057;
    border-bottom: 2px solid #007bff;
    padding-bottom: 0.5rem;
    margin-bottom: 1rem;
}

.required::after {
    content: " *";
    color: #dc3545;
}

.k-invalid {
    border-color: #dc3545 !important;
    box-shadow: 0 0 0 0.2rem rgba(220, 53, 69, 0.25) !important;
}

.k-invalid-msg {
    color: #dc3545;
    font-size: 0.875em;
    margin-top: 0.25rem;
    display: block;
}

.validation-status {
    font-size: 0.875em;
    margin-top: 0.25rem;
    min-height: 1.2em;
}

.password-strength .progress {
    height: 4px;
}

.progress-bar.bg-danger {
    background-color: #dc3545 !important;
}

.progress-bar.bg-warning {
    background-color: #ffc107 !important;
}

.progress-bar.bg-success {
    background-color: #28a745 !important;
}
</style>

总结

本教程介绍了Telerik表单与验证的核心功能:

  1. 表单控件布局

    • 基础表单设计和组织结构
    • 响应式分步表单实现
    • 字段分组和视觉层次
  2. 数据验证与错误提示

    • 客户端实时验证配置
    • 服务器端模型验证
    • 自定义验证规则编写
    • 友好的错误提示展示
  3. 高级功能特性

    • 密码强度检测
    • 实时验证反馈
    • 异步数据检查
    • 表单状态管理
  4. 用户体验优化

    • 清晰的错误提示信息
    • 实时反馈和状态更新
    • 加载状态和进度指示
    • 响应式布局设计

通过掌握这些表单和验证技术,您可以构建功能完善、用户体验良好的数据收集界面,确保数据的准确性和完整性。Telerik的表单控件和验证框架为开发者提供了强大而灵活的工具,满足各种复杂的业务需求。

Progress Telerik Ultimate Collection 2025 Q2下载地址 https://soft51.cc/software/175792580241152290

相关留言评论
昵称:
邮箱:
阅读排行