開發stark組件2

上個博客咱們,咱們寫到了要告訴前端頁面應該展現什麼字段 ,今天咱們就來詳細說一下 如何後端取到咱們須要的字段 並在前端頁面展現出來css

首先咱們先把前端頁面寫死,先看一下效果html

後端查看頁面代碼:前端

    def list_view(self,request):


        #用戶訪問的模型表:  self.model
        print("self.model:",self.model)


        print("self.list_display",self.list_display,'-'*30)


        queryset=self.model.objects.all()
        list_name=[
            '書名',
            '價格'
        ]

        data_list=[
            ['金梅',122],
            ['火影忍者',23],
            ['鄉間小道',8],
        ]

        return render(request,"stark/list_view.html",{'data_list':data_list,'list_name':list_name})

前端頁面:jquery

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <link rel="stylesheet" href="/static/bootstrap-3.3.7-dist/css/bootstrap.min.css">
</head>
<body>

<div class="container">
    <div class="row">
        <div class="col-md-8 col-md-offset-2">
            <table class="table table-bordered ">
                <thead>
                <tr>
                    {% for foo in list_name %}
                        <th>{{ foo }}</th>
                    {% endfor %}
                </tr>
                </thead>
                <tbody>
                {% for foo in data_list %}
                    <tr>
                        {% for bar in foo %}
                            <td>{{ bar }}</td>
                        {% endfor %}
                    </tr>
                {% endfor %}
                </tbody>
            </table>

        </div>
    </div>
</div>

<script src="/static/jquery-3.3.1.min.js"></script>

</body>
</html>

顯示的效果數據庫

這就咱們今天要完成的 根據自定義配置的不一樣 顯示不一樣的字段bootstrap

既然咱們要根據自定義的字段 顯示相應的字段 咱們就須要在後端 取到相應的字段 後端

下面咱們就改爲從數據庫裏取值安全

    def list_view(self,request):



        queryset=self.model.objects.all()

        data_list=[]
        for obj in queryset:
            temp=[]

            for ziduan in self.list_display:
                val=getattr(obj,ziduan)
                temp.append(val)
            data_list.append(temp)
            print(temp)
        print(data_list,'........')

        return render(request,"stark/list_view.html",{'data_list':data_list})

上面只是拿到了表格的內容 表格的列名尚未取到app

 def list_view(self,request):


        queryset=self.model.objects.all()
        header_list=[]
        for name in self.list_display:
            obj = self.model._meta.get_field(name)#根據字段找到相應的對象
            val = obj.verbose_name#拿到字段的中文名
            header_list.append(val)
        data_list=[]
        for obj in queryset:
            temp=[]

            for ziduan in self.list_display:
                val=getattr(obj,ziduan)
                temp.append(val)
            data_list.append(temp)
            print(temp)
        print(data_list,'........')

        return render(request,"stark/list_view.html",{'data_list':data_list,'header_list':header_list})

這樣咱們就完成了 從數據庫裏取值 可是還有一個問題 咱們取到的list_display是配置類默認的 而非咱們自定義的 就會報錯 因此咱們須要加個判斷函數

      header_list=[]
        for name in self.list_display:
            if name=='__str__':
                val = self.model._meta.model_name.upper()
                print(val,'1')
            else:
                obj = self.model._meta.get_field(name)#根據字段找到相應的對象
                val = obj.verbose_name#拿到字段的中文名
            header_list.append(val)

上面已經完成了最初的目標 可是咱們也能夠在此基礎上添加自定義列 以下圖

app01下的stark 自定義一個刪除列

    def delete_col(self, obj=None, is_header=False):
        if is_header:
            return "刪除"
        return mark_safe("<a href='%s/delete/'>刪除</a>" % obj.pk) #mark_safe至關於標籤是安全的 不要轉譯

    list_display = ["title","price",delete_col]

site.register(models.Book,BookConfig)

這樣咱們list_display就會有一個非字符串的值 

那在咱們的配置類就須要判斷一個是否,不然程序就會崩掉了

class ModelStark():
    def __init__(self,model):
        self.model = model

    list_display = ["__str__"]

    def list_view(self,request):



        #用戶訪問的模型表:  self.model
        print("self.model:",self.model)


        # print("self.list_display",self.list_display,'-'*30)

        queryset=self.model.objects.all()
        header_list=[]
        for name in self.list_display:
            if isinstance(name,str):

                if name=='__str__':
                    val = self.model._meta.model_name.upper()
                    print(val,'1')
                else:
                    obj = self.model._meta.get_field(name)#根據字段找到相應的對象
                    val = obj.verbose_name#拿到字段的中文名
            else:
                val=name(self,is_header=True)
            header_list.append(val)
        data_list=[]
        for obj in queryset:
            temp=[]

            for ziduan in self.list_display:
                if isinstance(ziduan,str):#判斷是否是字符串
                    val=getattr(obj,ziduan)
                else:
                    val=ziduan(self,obj)
                temp.append(val)
            data_list.append(temp)
            print(temp)
        print(data_list,'........')

        return render(request,"stark/list_view.html",{'data_list':data_list,'header_list':header_list})

可是這樣還不夠好 咱們應該把刪除這種操做設計成默認的 咱們知道設置成默認的就是在配置類裏添加,可是有一個問題 若是將這些加入list_display裏,那若是有自定義的 那麼配置類就會被覆蓋 因此咱們要想一個辦法解決這個問題

先將刪除 編輯 選擇 定義到配置類

  def delete_col(self,obj=None,is_header=False):

        if is_header:
            return "刪除"

        return mark_safe("<a href='%s/delete/'>刪除</a>"%obj.pk)

    def edit_col(self,obj=None,is_header=False):
        if is_header:
            return "編輯"

        return mark_safe("<a href=''>編輯</a>")

    def check_col(self,obj=None,is_header=False):
        if is_header:
            return "選擇"

        return mark_safe("<input type='checkbox'>")

既然咱們把上面的函數放進list_display裏 也會被自定義的類覆蓋 那咱們能夠在建立新列表 把上面的和list_display所有放進去返回 不就能夠了

   def get_new_list_display(self):
        new_list_display=[]

        new_list_display.extend(self.list_display)
        new_list_display.append(ModelStark.edit_col)
        new_list_display.append(ModelStark.delete_col)
        new_list_display.insert(0,ModelStark.check_col)

        return new_list_display

相關文章
相關標籤/搜索