bbs 第二天 注册功能 需要上传图片

2.注册功能:

  Django的forms表单中添加字段

from django import forms
from django.core.exceptions import ValidationError
# Django内置的正则
from django.core.validators import RegexValidator
from blog import models

class LoginForm(forms.Form):
    username = forms.CharField(
        label="用户名",
        min_length=3,
        max_length=12,
        error_messages={
            "required": "用户名不能为空",
            "min_length": "用户名最少3位",
            "max_length": "用户名最长12位"
        },
        widget=forms.widgets.TextInput(
            attrs={"class": "form-control c1"}
        )
    )
    password = forms.CharField(
        label="密码",
        min_length=4,
        max_length=12,
        error_messages={
            "required": "密码不能为空",
            "min_length": "密码最短4位",
            "max_length": "密码最长12位"
        },
        widget=forms.widgets.PasswordInput(
            attrs={"class": "form-control"}
        )
    )

# 注册功能的字段的校验
class RegForm(forms.Form):
    username = forms.CharField(
        label="用户名",
        min_length=3,
        max_length=12,
        error_messages={
            "required": "用户名不能为空",
            "min_length": "用户名最短3位",
            "max_length": "用户名最长12位"
        },
        widget=forms.widgets.TextInput(
            attrs={"class": "form-control"}
        )
    )

    password = forms.CharField(
        label="密码",
        min_length=3,
        max_length=12,
        error_messages={
            "required": "密码不能为空",
            "min_length": "密码最短3位",
            "max_length": "密码最长12位"
        },
        widget=forms.widgets.PasswordInput(
            attrs={"class": "form-control"}
        )
    )

    re_password = forms.CharField(
        label="确认密码",
        min_length=3,
        max_length=12,
        error_messages={
            "required": "密码不能为空",
            "min_length": "密码最短3位",
            "max_length": "密码最长12位"
        },
        widget=forms.widgets.PasswordInput(
            attrs={"class": "form-control"}
        )
    )

    phone = forms.CharField(
        label="手机号",
        min_length=11,
        max_length=11,
        validators=[
            RegexValidator(r'^\d{11}$', "手机号必须是数字"),

            RegexValidator(r'^1[356789][0-9]{9}$', "手机号码格式不正确")

        ],
        error_messages={
                         "required": "手机不能为空!",
                         "min_length": "手机号码11位",
                         "max_length": "手机号码11位"
        },
        widget=forms.widgets.TextInput(
            attrs={"class": "form-control"}
        )

    )

    # 钩子函数  clean_data 取到字段里面的所有内容
    # 局部钩子  用于校验一些正常的结果  clean_字段名
    def clean_username(self):
        # 取里面username字段名的数据
        value = self.cleaned_data.get("username", "")
        if "金瓶" in value:
            raise ValidationError("名字非法")
        elif models.UserInfo.objects.filter(username=value):
            raise ValidationError("用户名已存在")
        else:
            return value

    # 全局钩子  用于校验密码是否一致
    def clean(self):
        pwd = self.cleaned_data.get('password', '')
        re_pwd = self.cleaned_data.get('re_password', '')
        # 如果密码不为空或者一致
        if re_pwd and pwd == re_pwd:
            return self.cleaned_data
        else:
            err_msg = "两次密码不一致或者为空"
            self.add_error("re_password", err_msg)
            # raise ValidationError(err_msg)
View Code

    reg.html页面

<div class="container">
    <div class="row">
        <div class="panel panel-primary col-md-8 col-md-offset-2 " id="login-form">
            <div class="panel-heading">
                <h3 class="panel-title text-center ">注册界面</h3>
            </div>

            <div class="col-md-4 col-md-offset-4" id="login-form">
                <form autocomplete="off" novalidate>

                    <div class="form-group">
                        <label for="{{ form_obj.username.id_for_label }}">{{ form_obj.username.label }}</label>
                        {{ form_obj.username }}
                        <span class="help-block"></span>

                    </div>

                    <div class="form-group">
                        <label for="{{ form_obj.password.id_for_label }}">{{ form_obj.password.label }}</label>
                        {{ form_obj.password }}
                        <span class="help-block"></span>

                    </div>

                    <div class="form-group">
                        <label for="{{ form_obj.re_password.id_for_label }}">{{ form_obj.re_password.label }}</label>
                        {{ form_obj.re_password }}
                        <span class="help-block"></span>

                    </div>

                    <div class="form-group">
                        <label for="{{ form_obj.phone.id_for_label }}">{{ form_obj.phone.label }}</label>
                        {{ form_obj.phone }}
                        <span class="help-block"></span>

                    </div>

                    <div class="form-group">
                        <label>头像</label>
                        <div class="col-ms-10">
                            <input accept="image/*" type="file" id="id_avatar" name="avatar" style="display: none">
                            <label for="id_avatar"><img src="/static/img/default.png" id="show-avatar"></label>

                        </div>
                    </div>

                    <div class="form-group">
                        <button id="reg-button" type="button" class="btn btn-default">注册</button>
                    </div>
                </form>
            </div>
        </div>
    </div>
</div>
View Code

    views.py

def reg(request):
    if request.method == 'POST':
        ret = {'code': 0}
        # 如果是POST请求就拿到所有form表单里面的所有数据
        form_obj = forms.RegForm(request.POST)
        # 校验form里面的正则数据是否通过
        if form_obj.is_valid():
            # 把头像对象拿出来
            # 取到前端写好的FormData对象里面的所有数据
            # 取到图片对象 头像
            avatar_obj = request.FILES.get('avatar')
            # 创建用户前需要把重复一次的密码提出来
            form_obj.cleaned_data.get('re_password', '')
            # 创建用户
            models.UserInfo.objects.create_user(
                # 头像
                avatar=avatar_obj,
                # 所有用户信息
                **form_obj.cleaned_data
            )
            ret['data'] = "/login/"
        else:
            # 没有通过数据校验
            ret['code'] = 1
            # 通过data 发送form_obj里面正则校验报错的信息到前端
            ret['data'] = form_obj.errors

        return JsonResponse(ret)
    # 如果不是POST请求就发送一个空的form表单对象过去前端
    form_obj = forms.RegForm()
    return render(request, "reg.html", {'form_obj': form_obj})
View Code

    Ajax发送数据:用户名、密码、手机、头像,然后还有头像预览

<script>
    // 找到注册按钮绑定点击事件
    $("#reg-button").click(function () {
        var dataObj = new FormData();
        dataObj.append("username", $("#id_username").val());
        dataObj.append("password", $("#id_password").val());
        dataObj.append("re_password", $("#id_re_password").val());
        dataObj.append("phone", $("#id_phone").val());
        dataObj.append("avatar", $("#id_avatar")[0].files[0]);
        $.ajax({
            url: "/reg/",
            type: "POST",
            processData: false,
            contentType: false,
            data: dataObj,
            success: function (data) {
                console.log(data);
                if (data.code) {
                    // 如果有报错信息,应该在页面的对应位置展示出来
                    var errMsgObj = data.data;
                    $.each(errMsgObj, function (k, v) {
                        // k: 字段名  v:报错信息的数组
                        // 根据字段名找对应的input标签,把错误信息添加到对应位置
                        $("#id_" + k).next(".help-block").text(v[0]).parent().parent().addClass("has-error");
                    })
                } else {
                    console.log(data.data);
                    location.href = data.data || "/login/"
                }

            }
        })
    });

    // 给每一个input标签绑定focus事件,移除当前的错误提示信息
    $("input.form-control").focus(function () {
        $(this).next(".help-block").text("").parent().parent().removeClass("has-error");
    });

    // 头像预览
    $("#id_avatar").change(function () {
        // 找到你选中的那个头像文件
        var fileObj = this.files[0];
        console.log(fileObj);
        // 读取文件路径
        var fileReader = new FileReader();
        fileReader.readAsDataURL(fileObj);
        // 等图片被读取完毕之后,再做后续操作
        fileReader.onload = function () {
            // 设置预览图片
            $("#show-avatar").attr("src", fileReader.result);
        };
    })

</script>
View Code

 

猜你喜欢

转载自www.cnblogs.com/kermitjam/p/9275306.html