zoukankan      html  css  js  c++  java
  • Flask入门之模板导入与块宏(六)

    1 模板包含include

    主体结构(导入整个模板,直接渲染不可修改)

    {% include('模板名称') %}

    {% include('目录/模板名称') %}

    功能: 其功能就是将另一个模板加载到当前模板中,并直接渲染在当前位置上,而且是一次渲染整个模块内容

    #导入头部header.html
    {% include 'header.html' %}
    	主体内容
    #导入底部footer.html
    {% include 'footer.html' %}
    
    #忽略模板文件不存在时的错误
    {% include 'footer.html' ignore missing %}
    
    #也可以组成模板列表,会按照顺序依次加载
    {% include ['footer.html','bottom.html','end.html'] ignore missing %}
    

    注意:当include模板文件不存在时,程序会抛出异常,加上ignore missing关键字可以忽略不存在时的异常.

    2 宏(macro)

    **概念 **: Jinja2中宏的功能类似python中函数定义,分为声明与调用两个部分

    (1) 宏的定义

    主体结构

    {% macro 宏的名称([参数...s]) %}

    ​ 宏的主体

    {% endmacro %}

    宏的调用

    {{ 宏的名称[参数列表] }}

    (2) 宏的实例1

    templates/common/formmacro.html

    {% macro input(type='text',name='',value='') %}
        <input type="{{ type }}" name="{{ name }}" value="{{ value }}">
    {% endmacro %}
    

    先导入后调用

    {% import 'common/formmacro.html' as formmacro %}
    <form action=''>
    	<p>用户名:{{ formmacro.input(name='uername') }}</p>
        <p>密码:{{ formmacro.input('password','userpass') }}</p>
          <p>性别:
            {{ formmacro.input('radio','sex',1) }} 男
            {{ formmacro.input('radio','sex',0) }} 女
          </p>
          <p>{{ formmacro.input('submit',value='submit') }}</p>
    </form>
    

    (3) 宏的实例2

    #定义一个users宏,输出user.name  caller(user.gender)传递参数
    {% macro list_users(users) -%}
      <table>
        {%- for user in users %}
          <tr><td>{{ user.name |e }}</td>{{ caller(user.gender) }}</tr>
        {%- endfor %}
      </table>
    {%- endmacro %}
    
    #调用宏,{{ caller(user.gender) }}”部分被调用者”{% call(gender) %}”语句块内部的内容替代
    {% call(gender) list_users(users) %}
        <td>
        {% if gender == 'M' %}
        <img src="{{ url_for('static', filename='img/male.png') }}" width="20px">
        {% else %}
        <img src="{{ url_for('static', filename='img/female.png') }}" width="20px">
        {% endif %}
        </td>
        <td><input name="delete" type="button" value="Delete"></td>
    {% endcall %}
    

    (4)import 导入:(针对导入宏或者自定义的宏)

    import ....as....

    {% import 'common/formmacro.html' as formmacro %}
    如果index.html和formmacro同级 可以直接导入
    {% import 'formmacro.html' as formmacro %}
    

    from ... import as

    {% from 'common/formmacro.html' import input %}   #从包导入宏
    {% from 'common/formmacro.html' import input as form %}  #从包导入宏并重命名
    

    注意:

    1. 不能在宏定义的上方去调用
    2. 宏如果存在形参 如果不传实参 则行参的值为空 也不会报错
    3. 在给形参默认值的时候 必须遵循默认值的规则 幽默认值的放在后面 和 python的函数一样

    (5) 宏的内部变量

    varargs : 这是一个列表。如果调用宏时传入的参数多于宏声明时的参数,多出来的没指定参数名的参数就会保存在这个列表中。

    kwargs : 这是一个字典。如果调用宏时传入的参数多于宏声明时的参数,多出来的指定了参数名的参数就会保存在这个字典中。

    {% macro input(name, type='text', value='') %}
        <input type="{{ type }}" name="{{ name }}" value="{{ value|e }}">
        <br /> {{ varargs }}
        <br /> {{ kwargs }}
    {% endmacro %}
    <p>{{ input('submit', 'submit', 'Submit', 'more arg1', 'more arg2', ext='more arg3') }}</p>
    
    

    3 块(block)

    主体结构:一般结合继承使用,用于填充block块

    {% extend ‘parent.html’ %}
    
    {% block block_name %}
    {% endblock 块名%}
    

    注意:

    1. 模板不支持多继承,也就是子模板中定义的块,不可能同时被两个父模板替换。
    2. 模板中不能定义多个同名的块,子模板和父模板都不行,这样无法知道要替换哪一个部分的内容。

    (1) 保留父模板中的内容采用 super( )方法

    • #父模板中设置好块
      <head>
          {% block head %}
          <link rel="stylesheet" href="{{ url_for('static', filename='style.css') }}">
          <title>{% block title %}{% endblock %}</title>
          {% endblock head%}
      </head>
      <body>
          <div class="page">
          {% block content %}
          {% endblock %}
          </div>
      </body>
      
    • {% block title %}首页{% endblock %}
      {% block head %}
          {{ super() }}  #继承父类保持父类不变
          <style type="text/css">
              h1 { color: #336699; }
          </style>
      {% endblock %}
      
    • 注: 父模板与子模板中都有head块,运行时,父模板中的块先被加载,而后是子模板的块head

    (2) 块内语句的作用域

    默认情况下,块内语句是无法访问块作用域外的变量

    #父模板中
    {% for item in range(5) %}
            <li>{% block list %}{% endblock %}</li>
    {% endfor %}
    
    #子模板继承
    {% block list %}
        <p>{{ item }}</p>
    {% endblock %}
    
    #此时子模板是无法获取到父模板中 list块中的内容,即打印为空
    

    如果你想在块内访问这个块外的变量,你就需要在块声明时添加scoped关键字

    #父模板中添加 scoped 关键字
    {% for item in range(5) %}
            <li>{% block list scoped %}{% endblock %}</li>
    {% endfor %}
    
    #子模板继承
    {% block list %}
        <p>{{ item }}</p>
    {% endblock %}
    
    #此时item能获取到 0,1,2,3,4
    

    4 模板的继承

    主体架构

    {% extends '继承的模板名称' %}

    {% block 替换的名称 %}

    {% endblock %}

    自定义一个基类模板base.html

    <!DOCTYPE html>
    <html lang="en">
    {% block head %}
    <head>
        <meta charset="UTF-8">
        <title>{% block title %}{% endblock %}</title>  #title块
        {% block meta %}{% endblock %}
        <style>
            {% block style %}   #css样式块
            	*{color:red;}
            {% endblock %}
        </style>
        {% block link %}{% endblock %}  #外联样式块
    </head>
    {% endblock %}
    <body>
    {% include 'common/header.html' %}  #页面导入
    {% block content %}
    
    {% endblock %}
    {% include 'common/footer.html' %}  #页面导入
    </body>
    </html>
    

    使用index.html继承父类

    {% extends 'common/base.html' %}   #继承父类模板
    {% block title %}首页{% endblock %}
    {% block style %}
        {# 调用基础模板内的样式  如果不调用则全部被覆盖 #}
        {{ super() }}
        p{font-size:20px;}
    {% endblock %}
    {% block content %}
        我是中间的内容部分
    {% endblock %}
    

    注意:

    1. 在替换的外部的填写的内容 不会被显示出来
    2. 如果在替换某一个block的时候 替换以后所有的样式消失 则去查看是否有调用super()
  • 相关阅读:
    babel-loader的原理
    js弱类型转换的知识点
    个人说明
    嗯三月的小计划
    bzoj2326 [HNOI2011]数学作业
    bzoj2654 tree
    bzoj1018[SHOI2008]堵塞的交通traffic
    bzoj1937[Shoi2004]Mst 最小生成树
    一般图最大匹配-带花树-带注释模板
    FFT快速傅里叶变换-递归版-带注释模板
  • 原文地址:https://www.cnblogs.com/why957/p/9123248.html
Copyright © 2011-2022 走看看