• Django Admin管理后台详解16(转)表单联动


    转:https://www.cnblogs.com/thunderLL/p/9210472.html

    通过自定义Admin的模板文件实现省市区的三级联动.要求创建记录时,根据省>市>区的顺序选择依次显示对应数据.
    修改记录时默认显示已存在的数据.

    Model

    class Member(models.Model):
        name = models.CharField(max_length=100, verbose_name='姓名')
        province = models.CharField(max_length=100, null=True, blank=True, verbose_name='省份')
        city = models.CharField(max_length=100, null=True, blank=True, verbose_name='城市')
        district = models.CharField(max_length=100, null=True, blank=True, verbose_name='区/县')
    
        class Meta:
            verbose_name_plural = verbose_name = '人员'
    
        def __str__(self):
            return self.name

    View和url

    # views
    LOCATION = {'吉林省': {'长春市': ['南关区', '朝阳区', '二道区', '绿园区']}}
    
    
    def choose_province(request):
        province = list(LOCATION.keys())
        return JsonResponse(province, safe=False)
    
    
    def choose_city(request):
        province = request.GET.get('p')
        cities = list(LOCATION[province].keys())
        return JsonResponse(cities, safe=False)
    
    
    def choose_district(request):
        province = request.GET.get('p')
        city = request.GET.get('c')
        districts = LOCATION[province][city]
        return JsonResponse(districts, safe=False)
       
    # urls
    from person.views import choose_province, choose_city, choose_district
    
    urlpatterns = [
        path('province/', choose_province),
        path('city/', choose_city),
        path('district/', choose_district),
        path('admin/', admin.site.urls),
    ]

    Admin

    class MemberForm(forms.ModelForm):
        class Meta:
            widgets = {
                'province': forms.Select(),
                'city': forms.Select(),
                'district': forms.Select()
            }
    
    @admin.register(Member)
    class MemberAdmin(admin.ModelAdmin):
        form = MemberForm
        fields = ('name', ('province', 'city', 'district'))
        list_display = ('name', 'province', 'city', 'district')
        change_form_template = 'area.html'

    这里需要写一个form将省市区这三个字段显示为单选框.

    模板文件

    找到django源码中的change_form.html(django/contrib/admin/templates/admin/)文件,复制到app下templates目录中.
    在admin中指定自定义的模板文件change_form_template = 'area.html'

    {% block admin_change_form_document_ready %}
        <script type="text/javascript"
                id="django-admin-form-add-constants"
                src="{% static 'admin/js/change_form.js' %}"
                {% if adminform and add %}
                    data-model-name="{{ opts.model_name }}"
                {% endif %}>
        </script>
    
        <script type="text/javascript">
            (function($) {
                $('#id_city').change(function() {
                    let p_id = $('#id_province').val();
                    let c_id = $('#id_city').val();
                    $.get('/district/', {"p": p_id, "c": c_id }, function(a_info) {
                        var area_info = $('#id_district').empty().append('<option value>' + '---------' + '</option>');
                        $.each(a_info, function(i, area) {
                            area_info.append('<option value="' + area + '">' + area + '</option>')
                        });
                        {% if change %}
                            $("#id_district").find("option:contains({{ original.district }})").attr('selected', true);
                        {% endif %}
                    });
                });
    
                $('#id_province').change(function() {
                    let p_id = $('#id_province').val();
                    $.get('/city/', { 'p': p_id }, function(c_info) {
                        var city_info = $('#id_city').empty().append('<option value>' + '---------' + '</option>');
                        $.each(c_info, function(i, city) {
                            city_info.append('<option value="' + city + '">' + city + '</option>')
                        });
                        {% if change %}
                            $("#id_city").find("option:contains({{ original.city }})").attr('selected', true);
                            $("#id_city").trigger("change");
                        {% endif %}
                    });
                });
    
                $.get('/province/', function(p_info) {
                    var province_info = $('#id_province').empty().append('<option value>' + '---------' + '</option>');
                    $.each(p_info, function(i, province) {
                        province_info.append('<option value="' + province + '">' + province + '</option>')
                    });
                    {% if change %}
                        $("#id_province").find("option:contains({{ original.province }})").attr('selected', true);
                        $("#id_province").trigger("change");
                    {% endif %}
                });
            })(django.jQuery);
        </script>
  • 相关阅读:
    grunt in webstorm
    10+ Best Responsive HTML5 AngularJS Templates
    响应式布局
    responsive grid
    responsive layout
    js event bubble and capturing
    Understanding Service Types
    To add private variable to this Javascript literal object
    Centering HTML elements larger than their parents
    java5 新特性
  • 原文地址:https://www.cnblogs.com/wangbin2188/p/15591600.html
Copyright © 2020-2023  润新知