Day17 gin基础02 模板语法
day17 20220502
01
前后端不分离
前后端分离
demo\index.html
charset="UTF-8">
这是一个首页页面
用户名:root
demo\main.go
package main
import (
"html/template"
"net/http"
)
func tmpl(w http.ResponseWriter,r *http.Request){
t1,err:=template.ParseFiles("index.html")
if err!=nil {
panic(err)
}
t1.Execute(w,"hello user01")
}
func main() {
server:=http.Server{
Addr: "127.0.0.1:8080",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
gin框架中接收一个参数 gin.Context
标准http框架,接收两个参数 请求和响应
函数什么时候被调用的
函数变量(c *gin.Context) c是形参
函数由框架本身完成调用,传入实参。
源码
func ParseFiles(filenames ...string) (*Template, error) {
return parseFiles(nil, readFileOS, filenames...)
}
测试
模板变量替换 . 点操作
demo\index.html
charset="UTF-8">
这是一个首页页面
用户名:{{ . }}
demo\main.go
package main
import (
"html/template"
"net/http"
)
func tmpl(w http.ResponseWriter,r *http.Request){
t1,err:=template.ParseFiles("index.html")
if err!=nil {
panic(err)
}
user:="root"
t1.Execute(w,user)
}
func main() {
//http框架,和gin框架一样都是web框架,只不过gin更强大
server:=http.Server{
Addr: "127.0.0.1:8080",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
占位符,与data 相对应
//变量替换
t1.Execute(w,nil)
测试
注意设置working directory
func tmpl(w http.ResponseWriter,r *http.Request){
t1,err:=template.ParseFiles("index.html")
if err!=nil {
panic(err)
}
user:="root"
//变量替换
t1.Execute(w,user)
}
浏览器在后端 已经完成了替换,才给浏览器返回
此时的index.html不是纯html静态文件
叫:模板页面
charset="UTF-8">
这是一个首页页面!!!
用户名:{{ . }}
用户名:{{ . }}
用户名:{{ . }}
02 模板语法之
模板语法之--切片对象
demo\main.go
package main
import (
"html/template"
"net/http"
)
func tmpl(w http.ResponseWriter,r *http.Request){
t1,err:=template.ParseFiles("index.html")
if err!=nil {
panic(err)
}
//user:="root"
names:=[]string{"user01","user02","user03"}
//变量替换
t1.Execute(w,names)
}
func main() {
//http框架,和gin框架一样都是web框架,只不过gin更强大
server:=http.Server{
Addr: "127.0.0.1:8080",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
demo\index.html
charset="UTF-8">
这是一个首页页面
用户名:{{ . }}
取第二个姓名 index . 1
charset="UTF-8">
这是一个首页页面
用户名:{{ . }}
用户名:{{ index . 1 }}
模板语法之--结构体对象
package main
import (
"html/template"
"net/http"
)
type Student struct{
Name string
Age int
Gender string
}
func tmpl(w http.ResponseWriter,r *http.Request){
t1,err:=template.ParseFiles("index.html")
if err!=nil{
panic(err)
}
//结构体对象
s1:=Student{Name: "user01",Age: 22,Gender: "male"}
t1.Execute(w,s1)
}
func main() {
//http框架和gin框架一样都是web框架,只不过gin更强大
server:=http.Server{
Addr: "127.0.0.1:8080",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
注意:这里注释的干扰问题
不要使用html的注释语法,否则遍历不到,导致页面不能正常显示
使用{{/* */}}注释方式,或者直接删除不需要代码
demo\index.html
charset="UTF-8">
这是一个首页页面
{{ . }}
姓名:{{ .Name }}
年龄:{{ .Age }}
变量替换
案例
注意:此处模板中是 .s1.Name
s9\day17\lesson04\index.html
charset="UTF-8">
这是一个首页页面
{{.}}
姓名:{{.s1.Name}}
年龄:{{.s1.Age}}
s9\day17\lesson04\main.go
package main
import (
"html/template"
"net/http"
)
type Student struct {
Name string
Age int
Gender string
}
func tmpl(w http.ResponseWriter, r *http.Request) {
t1, err := template.ParseFiles("index.html")
if err != nil {
panic(err)
}
//结构体对象
s1 := Student{Name: "user01", Age: 22, Gender: "male"}
t1.Execute(w, map[string]interface{}{
"s1": s1,
})
}
func main() {
//http框架和gin框架一样都是web框架,只不过gin更强大
server := http.Server{
Addr: "127.0.0.1:8080",
}
http.HandleFunc("/index", tmpl)
server.ListenAndServe()
}
放入多个对象
此时 . 代表 map对象
.s1.
练习
练习1
传入切片
package main
import (
"net/http"
"text/template"
)
type Student struct {
Name string
Age int
Gender string
}
func tmpl(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("index.html")
if err!=nil{
panic(err)
}
//user:="root"
names:=[]string{"user01","user02","user03"}
//s1:=Student{Name: "user11",Age: 18,Gender: "male"}
t1.Execute(w,names)
}
func main() {
server:=http.Server{
Addr:"127.0.0.1:8090",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
Index.html
charset="UTF-8">
这是一个首页页面!!!
用户列表:{{ . }}
用户列表第二个名字:{{ index . 1}}
测试
练习2
main.go
package main
import (
"net/http"
"text/template"
)
type Student struct {
Name string
Age int
Gender string
}
func tmpl(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("index.html")
if err!=nil{
panic(err)
}
//user:="root"
//names:=[]string{"user01","user02","user03"}
s1:=Student{Name: "user11",Age: 18,Gender: "male"}
t1.Execute(w,s1)
}
func main() {
server:=http.Server{
Addr:"127.0.0.1:8090",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
index.html
charset="UTF-8">
这是一个首页页面!!!
用户名:{{ . }}
用户名:{{.Name}}
年龄:{{ .Age }}
测试访问
练习3
map 空接口
package main
import (
"net/http"
"text/template"
)
type Student struct {
Name string
Age int
Gender string
}
func tmpl(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("index.html")
if err!=nil{
panic(err)
}
user:="root"
names:=[]string{"user01","user02","user03"}
s1:=Student{Name: "user11",Age: 18,Gender: "male"}
t1.Execute(w,map[string]interface{}{
"user":user,
"names":names,
"s1":s1,
})
}
func main() {
server:=http.Server{
Addr:"127.0.0.1:8090",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
index.html
charset="UTF-8">
这是一个首页页面
{{.}}
姓名:{{.s1.Name}}
年龄:{{.s1.Age}}
user:{{.user}}
names:{{.names}}
names:{{ index .names 0}}
03 模板语法之--if判断和循环
main.go
package main
import (
"html/template"
"net/http"
)
type Student struct {
Name string
Age int
Gender string
}
func tmpl(w http.ResponseWriter, r *http.Request) {
t1, err := template.ParseFiles("index.html")
if err != nil {
panic(err)
}
user:="user001"
names:=[]string{"user21","user22","user23"}
//结构体对象
s1 := Student{Name: "user01", Age: 22, Gender: "male"}
//t1.Execute(w, map[string]interface{}{
// "s1": s1,
//})
t1.Execute(w,map[string]interface{}{
"user":user,
"names":names,
"s1":s1,
"books":[]string{"西游记","三国演义","红楼梦","水浒传"},
})
}
func main() {
//http框架和gin框架一样都是web框架,只不过gin更强大
server := http.Server{
Addr: "127.0.0.1:8080",
}
http.HandleFunc("/index", tmpl)
server.ListenAndServe()
}
index.html
charset="UTF-8">
这是一个首页页面
s1对象姓名:{{.s1.Name}}
s1对象年龄:{{.s1.Age}}
四大名著:{{ .books }}
测试
index 索引
charset="UTF-8">
这是一个首页页面
s1对象姓名:{{.s1.Name}}
s1对象年龄:{{.s1.Age}}
四大名著:{{ .books }}
{{index .books 0}}
{{index .books 1}}
{{index .books 2}}
{{index .books 3}}
range循环
{{range $value:=.books}}
{{range $key,$value:=.books}}
可以有$index 不使用
- {{$value}}
{{range $index,$value:=.books}}
{{end}}
示例
charset="UTF-8">
这是一个首页页面
s1对象姓名:{{.s1.Name}}
s1对象年龄:{{.s1.Age}}
四大名著:{{ .books }}
- {{$index}} {{$value}}
{{range $index,$value:=.books}}
{{end}}
if判断
charset="UTF-8">
这是一个首页页面
{{.}}
登录人:{{.user1}}
s1对象姓名:{{.s1.Name}}
s1对象年龄:{{.s1.Age}}
四大名著:{{ .books }}
- {{$value}}
{{range $key,$value:=.books}}
{{end}}
变量user1不存在,打印空白
添加if判断
s9\day17\lesson04\index.html
charset="UTF-8">
这是一个首页页面
{{.}}
{{ if .user1 }}
登录人:{{.user1}}
{{else}}
匿名用户
{{end}}
s1对象姓名:{{.s1.Name}}
s1对象年龄:{{.s1.Age}}
四大名著:{{ .books }}
- {{$value}}
{{range $key,$value:=.books}}
{{end}}
s9\day17\lesson04\main.go
user1不能存在,所以打印匿名用户
package main
import (
"html/template"
"net/http"
)
type Student struct {
Name string
Age int
Gender string
}
func tmpl(w http.ResponseWriter, r *http.Request) {
t1, err := template.ParseFiles("index.html")
if err != nil {
panic(err)
}
user:="user001"
names:=[]string{"user21","user22","user23"}
//结构体对象
s1 := Student{Name: "user01", Age: 22, Gender: "male"}
//t1.Execute(w, map[string]interface{}{
// "s1": s1,
//})
t1.Execute(w,map[string]interface{}{
"user":user,
"names":names,
"s1":s1,
"books":[]string{"西游记","三国演义","红楼梦","水浒传"},
})
}
func main() {
//http框架和gin框架一样都是web框架,只不过gin更强大
server := http.Server{
Addr: "127.0.0.1:8080",
}
http.HandleFunc("/index", tmpl)
server.ListenAndServe()
}
注释
注释方法: {{/*a comment */}}。注释后的内容不会被引擎进行替换。但需要注意,注释行在替换的时候也会占用行,所以应该去除前缀和后缀空白,否则会多一空行。
实验中没显示出差别。
{{- /* index .names 1 */}}
作业:
main.go
package main
import (
"html/template"
"net/http"
)
type Student struct {
Name string
Age int
Gender string
}
type Book struct {
Title string
Price int
}
func tmpl(w http.ResponseWriter, r *http.Request) {
t1, err := template.ParseFiles("index.html")
if err != nil {
panic(err)
}
user:="user001"
names:=[]string{"user21","user22","user23"}
//结构体对象
s1 := Student{Name: "user01", Age: 22, Gender: "male"}
//t1.Execute(w, map[string]interface{}{
// "s1": s1,
//})
book01:=Book{Title: "西游记",Price: 99}
book02:=Book{Title: "三国演义",Price: 199}
book03:=Book{Title: "红楼梦",Price: 399}
book04:=Book{Title: "水浒传",Price: 299}
book_list:=[]Book{book01,book02,book03,book04}
t1.Execute(w,map[string]interface{}{
"user":user,
"names":names,
"s1":s1,
"books":[]string{"西游记","三国演义","红楼梦","水浒传"},
"book_list":book_list,
})
}
func main() {
//http框架和gin框架一样都是web框架,只不过gin更强大
server := http.Server{
Addr: "127.0.0.1:8080",
}
http.HandleFunc("/index", tmpl)
server.ListenAndServe()
}
表格
charset="UTF-8">
这是一个首页页面
| 序号 | 书籍名称 | 书籍价格 |
| {{$index}} | {{$value.Title}} | {{$value.Price}} |
打印结果
下午01 扩展
package main
import (
"net/http"
"text/template"
)
type Student struct {
Name string
Age int
Gender string
}
type Book struct {
Title string
Price int
}
func tmpl(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("index.html")
if err!=nil{
panic(err)
}
book01 :=Book{Title: "西游记",Price: 99}
book02 :=Book{Title: "三国演义",Price: 199}
book03 :=Book{Title: "红楼梦",Price: 399}
book04 :=Book{Title: "水浒传",Price: 299}
book_list:=[]Book{book01,book02,book03,book04}
//user:="root"
//names:=[]string{"user01","user02","user03"}
//s1:=Student{Name: "user11",Age: 18,Gender: "male"}
t1.Execute(w,map[string]interface{}{
//"user":user,
//"names":names,
//"s1":s1,
"book_list":book_list,
})
}
func main() {
server:=http.Server{
Addr:"127.0.0.1:8090",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
charset="UTF-8">
.c1 {
}
这是一个首页页面!!!
| 序号 | 书籍名称 | 书籍价格 |
| {{$index}} | {{$value.Title}} | {{$value.Price}} |
| {{$index}} | {{$value.Title}} | {{$value.Price}} |
下午 02 自定义 模板函数
package main
import (
"net/http"
"text/template"
)
type Student struct {
Name string
Age int
Gender string
}
type Book struct {
Title string
Price int
}
func tmpl(w http.ResponseWriter,r *http.Request){
//解析模板
t1:=template.New("index.html")
t1.Funcs(funcMap).ParseFiles("index.html")
book01 :=Book{Title: "西游记",Price: 99}
book02 :=Book{Title: "三国演义",Price: 199}
book03 :=Book{Title: "红楼梦",Price: 399}
book04 :=Book{Title: "水浒传",Price: 299}
book_list:=[]Book{book01,book02,book03,book04}
t1.Execute(w,map[string]interface{}{
"book_list":book_list,
})
}
func add2(x,y int)int {
return x+y
}
var funcMap = template.FuncMap{
"add":add2,
}
func main() {
server:=http.Server{
Addr:"127.0.0.1:8090",
}
http.HandleFunc("/index",tmpl)
server.ListenAndServe()
}
charset="UTF-8">
.c1 {
}
这是一个首页页面!!!
| 序号 | 书籍名称 | 书籍价格 |
| {{add $index 1}} | {{$value.Title}} | {{$value.Price}} |
| {{add $index 1}} | {{$value.Title}} | {{$value.Price}} |
测试
下午03 嵌套 define
提示:在项目中使用子模板,可以让项目模板具有模块化的能力,提高模块复用能力和可维护性。
s9\day17\lesson06\test01.html
charset="UTF-8">
{{template "header.html"}}
i am test01!!!
s9\day17\lesson06\header.html
s9\day17\lesson06\main.go
找不到header.html,
1 定义时加载
package main
import (
"html/template"
"net/http"
)
func test01(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("test01.html","header.html")
if err!=nil{
panic(err)
}
t1.Execute(w,nil)
}
func main() {
server:=http.Server{
Addr:"127.0.0.1:8090",
}
http.HandleFunc("/index",test01)
server.ListenAndServe()
}
练习
main.go
package main
import (
"net/http"
"text/template"
)
func test01(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("test01.html","header.html")
if err!=nil{
panic(err)
}
t1.Execute(w,nil)
}
func test02(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("test02.html","header.html")
if err!=nil{
panic(err)
}
t1.Execute(w,nil)
}
func main() {
server:=http.Server{
Addr:"127.0.0.1:8090",
}
http.HandleFunc("/test01",test01)
http.HandleFunc("/test02",test02)
server.ListenAndServe()
}
test01.html
charset="UTF-8">
{{template "header.html"}}
i am test01!!!
参考 注意:匹配到第一个,就不再匹配了。只匹配到header.html没有匹配到test01.html
t1,err:=template.ParseGlob("test01/*")
下午04 继承
母版
base.html
charset="UTF-8">
{{template "content"}}
test01.html
{{define "content"}}
I am test01 content!
{{end}}
test02.html
{{define "content"}}
I am test02 content!
{{end}}
main.go
package main
import (
"net/http"
"text/template"
)
func test01(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("base.html","test01.html")
if err!=nil{
panic(err)
}
t1.Execute(w,nil)
}
func test02(w http.ResponseWriter,r *http.Request){
//解析模板
t1,err:=template.ParseFiles("base.html","test02.html")
if err!=nil{
panic(err)
}
t1.Execute(w,nil)
}
func main() {
server:=http.Server{
Addr:"127.0.0.1:8090",
}
http.HandleFunc("/test01",test01)
http.HandleFunc("/test02",test02)
server.ListenAndServe()
}
测试
下午05 gin模板语法
案例1
s9\day17\lesson07\main.go
package main
import "github.com/gin-gonic/gin"
func index(c *gin.Context){
c.HTML(200,"index.html",nil)
}
func main() {
r:=gin.Default()
//返回一个html页面
r.LoadHTMLGlob("templates/*")
r.GET("/index",index)
r.Run() //监听并在 0.0.0:8080 上启动服务
}
s9\day17\lesson07\templates\index.html
charset="UTF-8">
gin框架的模板语法
案例2 引入{{.user}}
s9\day17\lesson07\main.go
package main
import "github.com/gin-gonic/gin"
func index(c *gin.Context){
user:="root"
c.HTML(200,"index.html",gin.H{
"user":user,
})
}
func main() {
r:=gin.Default()
//返回一个html页面
r.LoadHTMLGlob("templates/*")
r.GET("/index",index)
r.Run() //监听并在 0.0.0:8080 上启动服务
}
s9\day17\lesson07\templates\index.html
charset="UTF-8">
gin框架的模板语法
用户名:{{.user}}
案例3 引入 切片
主程序main.go
s9\day17\lesson07\main.go
package main
import "github.com/gin-gonic/gin"
type Book struct {
Title string
Price int
}
func index(c *gin.Context){
user:="root"
book01:=Book{Title: "西游记",Price: 99}
book02:=Book{Title: "三国演义",Price: 199}
book03:=Book{Title: "红楼梦",Price: 399}
book04:=Book{Title: "水浒传",Price: 299}
book_list:=[]Book{book01,book02,book03,book04}
c.HTML(200,"index.html",gin.H{
"user":user,
"book_list":book_list,
})
}
func main() {
r:=gin.Default()
//返回一个html页面
r.LoadHTMLGlob("templates/*")
r.GET("/index",index)
r.Run() //监听并在 0.0.0:8080 上启动服务
}
页面index.html
s9\day17\lesson07\templates\index.html
charset="UTF-8">
gin框架的模板语法
用户名:{{.user}}
| 序号 | 书籍名称 | 书籍价格 |
|---|---|---|
| {{$index}} | {{$book.Title}} | {{$book.Price}} |
访问
案例4 引入自定义函数
主程序main.go
s9\day17\lesson07\main.go
引入r.SetFuncMap(template.FuncMap{
package main
import (
"github.com/gin-gonic/gin"
"html/template"
)
type Book struct {
Title string
Price int
}
func index(c *gin.Context){
user:="root"
book01:=Book{Title: "西游记",Price: 99}
book02:=Book{Title: "三国演义",Price: 199}
book03:=Book{Title: "红楼梦",Price: 399}
book04:=Book{Title: "水浒传",Price: 299}
book_list:=[]Book{book01,book02,book03,book04}
c.HTML(200,"index.html",gin.H{
"user":user,
"book_list":book_list,
})
}
func main() {
r:=gin.Default()
r.SetFuncMap(template.FuncMap{
"add":func(x,y int) int{
return x+y
},
})
//返回一个html页面
r.LoadHTMLGlob("templates/*")
r.GET("/index",index)
r.Run() //监听并在 0.0.0:8080 上启动服务
}
页面index.html
s9\day17\lesson07\templates\index.html
引入
charset="UTF-8">
gin框架的模板语法
用户名:{{.user}}
| 序号 | 书籍名称 | 书籍价格 |
|---|---|---|
| {{add $index 1}} | {{$book.Title}} | {{$book.Price}} |
访问
序号默认从0开始,现在从1开始
嵌套与继承
代码
s9\day17\lesson08\main.go
package main
import (
"github.com/gin-gonic/gin"
"html/template"
)
type Book struct {
Title string
Price int
}
type Ncov struct {
City string
GanRanNum int
DeadNum int
RecentNum int
}
func index(c *gin.Context){
user:="root"
book01:=Book{Title: "西游记",Price: 99}
book02:=Book{Title: "三国演义",Price: 199}
book03:=Book{Title: "红楼梦",Price: 399}
book04:=Book{Title: "水浒传",Price: 299}
book_list:=[]Book{book01,book02,book03,book04}
c.HTML(200,"index.html",gin.H{
"user":user,
"book_list":book_list,
})
}
func getNcov(c *gin.Context){
city01:=Ncov{City: "city01",GanRanNum: 100,DeadNum: 3,RecentNum: 10}
city02:=Ncov{City: "city02",GanRanNum: 30,DeadNum: 0,RecentNum: 6}
city03:=Ncov{City: "city03",GanRanNum: 78,DeadNum: 2,RecentNum: 3}
city04:=Ncov{City: "city04",GanRanNum: 50,DeadNum: 3,RecentNum: 5}
ncovList:=[]Ncov{city01,city02,city03,city04}
c.HTML(200,"ncov.html",gin.H{
"ncovList":ncovList,
})
}
func main() {
r:=gin.Default()
r.SetFuncMap(template.FuncMap{
"add":func(x,y int) int{
return x+y
},
})
//返回一个html页面
r.LoadHTMLGlob("templates/*")
r.GET("/2019ncov",getNcov)
r.GET("/index",index)
r.Run() //监听并在 0.0.0:8080 上启动服务
}
示例页面1 图书管理系统页面
页面index.html 引入bootstrap
boostrap官网下载模板,删除中间部分,添加表格
s9\day17\lesson08\templates\index.html
完整页面代码:
http-equiv="X-UA-Compatible" content="IE=edge">
name="viewport" content="width=device-width, initial-scale=1">
name="author" content="">
rel="icon" href="https://fastly.jsdelivr.net/npm/@bootcss/v3.bootcss.com@1.0.35/favicon.ico">
rel="canonical" href="https://getbootstrap.com/docs/3.4/examples/theme/">
图书管理系统
This is a template showcasing the optional theme stylesheet included in Bootstrap. Use it as a starting point to create something more unique by building on or modifying it.
| 序号 | 书籍名称 | 书籍价格 |
|---|---|---|
| {{add $index 1}} | {{$book.Title}} | {{$book.Price}} |
引入样式
table样式
table-boarderd样式
table-striped样式
table-hover样式
| 序号 | 书籍名称 | 书籍价格 |
|---|---|---|
| {{add $index 1}} | {{$book.Title}} | {{$book.Price}} |
查看
示例页面2 疫情查看系统页面
页面ncov.html
http-equiv="X-UA-Compatible" content="IE=edge">
name="viewport" content="width=device-width, initial-scale=1">
name="author" content="">
rel="icon" href="https://fastly.jsdelivr.net/npm/@bootcss/v3.bootcss.com@1.0.35/favicon.ico">
rel="canonical" href="https://getbootstrap.com/docs/3.4/examples/theme/">
疫情查询系统
This is a template showcasing the optional theme stylesheet included in Bootstrap. Use it as a starting point to create something more unique by building on or modifying it.
| 序号 | 城市 | 累计感染人数 | 累计死亡人数 | 累计新增人数 |
|---|---|---|---|---|
| {{add $index 1}} | {{$city.City}} | {{$city.GanRanNum}} | {{$city.DeadNum}} | {{$city.RecentNum}} |
查看
下午06 单模板继承
Gin框架默认都是使用单模板,如果需要使用block template功能,可以通过"https://github.com/gin-contrib/multitemplate"库实现,
1.1 base.html
构建base页面: 下载bootstrap模板删除
http-equiv="X-UA-Compatible" content="IE=edge">
name="viewport" content="width=device-width, initial-scale=1">
name="author" content="">
rel="icon" href="https://fastly.jsdelivr.net/npm/@bootcss/v3.bootcss.com@1.0.35/favicon.ico">
rel="canonical" href="https://getbootstrap.com/docs/3.4/examples/theme/">
1.2 添加内容
{{block "content" .}}
{{end}}
2 index.html
{{template "base.html" }}
{{block "content" .}}
图书管理系统
This is a template showcasing the optional theme stylesheet included in Bootstrap. Use it as a starting point to create something more unique by building on or modifying it.
| 序号 | 书籍名称 | 书籍价格 |
|---|---|---|
| {{$index}} | {{$book.Title}} | {{$book.Price}} |
{{end}}
3 ncov.html
继承模板
{{template "base.html"}}
{{block "content" .}}
疫情查询系统
This is a template showcasing the optional theme stylesheet included in Bootstrap. Use it as a starting point to create something more unique by building on or modifying it.
| 序号 | 城市 | 累计感染人数 | 累计死亡人数 | 累计新增人数 |
|---|---|---|---|---|
| {{$index}} | {{$city.City}} | {{$city.GanRanNum}} | {{$city.DeadNum}} | {{$city.RecentNum}} |
{{end}}
main.go
s9\day17\lesson08\main.go
package main
import (
"github.com/gin-contrib/multitemplate"
"github.com/gin-gonic/gin"
"html/template"
)
type Book struct {
Title string
Price int
}
type Ncov struct {
City string
GanRanNum int
DeadNum int
RecentNum int
}
func index(c *gin.Context){
user:="root"
book01:=Book{Title: "西游记",Price: 99}
book02:=Book{Title: "三国演义",Price: 199}
book03:=Book{Title: "红楼梦",Price: 399}
book04:=Book{Title: "水浒传",Price: 299}
book_list:=[]Book{book01,book02,book03,book04}
c.HTML(200,"index",gin.H{
"user":user,
"book_list":book_list,
})
}
func getNcov(c *gin.Context){
city01:=Ncov{City: "city01",GanRanNum: 100,DeadNum: 3,RecentNum: 10}
city02:=Ncov{City: "city02",GanRanNum: 30,DeadNum: 0,RecentNum: 6}
city03:=Ncov{City: "city03",GanRanNum: 78,DeadNum: 2,RecentNum: 3}
city04:=Ncov{City: "city04",GanRanNum: 50,DeadNum: 3,RecentNum: 5}
ncovList:=[]Ncov{city01,city02,city03,city04}
c.HTML(200,"ncov",gin.H{
"ncovList":ncovList,
})
}
func createMyRender() multitemplate.Renderer {
r:=multitemplate.NewRenderer()
r.AddFromFiles("index","templates/base.html","templates/index.html")
r.AddFromFiles("ncov","templates/base.html","templates/ncov.html")
return r
}
func add(x,y int) int{
return x+y
}
func main() {
r:=gin.Default()
r.SetFuncMap(template.FuncMap{
"add":add,
})
//返回一个html页面
//r.LoadHTMLGlob("templates/*")
r.HTMLRender=createMyRender()
r.GET("/2019ncov",getNcov)
r.GET("/index",index)
r.Run() //监听并在 0.0.0:8080 上启动服务
}
改为多继承
r.HTMLRender=createMyRender()
注意对齐
添加左侧栏
修改base.html
修改部分的代码
Panel content
Panel content
{{block "content" .}}
{{end}}
完整代码
http-equiv="Content-Type" content="text/html; charset=UTF-8">
http-equiv="X-UA-Compatible" content="IE=edge">
name="viewport" content="width=device-width, initial-scale=1">
name="author" content="">
rel="icon" href="https://fastly.jsdelivr.net/npm/@bootcss/v3.bootcss.com@1.0.35/favicon.ico">
rel="canonical" href="https://getbootstrap.com/docs/3.4/examples/theme/">
rel="stylesheet">
rel="stylesheet">
rel="stylesheet">
rel="stylesheet">
Panel content
Panel content
{{block "content" .}}
{{end}}
查看页面
title标签
修改base.html
{{block "title" .}}
{{end}}
添加index.html
{{block "title" .}}
{{end}}
添加ncov.html
{{block "title" .}}
{{end}}
最终
base.html
{{block "title" .}}
{{end}}
rel="stylesheet">
rel="stylesheet">
rel="stylesheet">
rel="stylesheet">
Panel content
Panel content
{{block "content" .}}
{{end}}
index.html
{{template "base.html" }}
{{block "title" .}}
{{end}}
{{block "content" .}}
图书管理系统
This is a template showcasing the optional theme stylesheet included in Bootstrap. Use it as a starting point to create something more unique by building on or modifying it.
| 序号 | 书籍名称 | 书籍价格 |
|---|---|---|
| {{$index}} | {{$book.Title}} | {{$book.Price}} |
{{end}}
ncov.html
{{template "base.html"}}
{{block "title" .}}
{{end}}
{{block "content" .}}
疫情查询系统
This is a template showcasing the optional theme stylesheet included in Bootstrap. Use it as a starting point to create something more unique by building on or modifying it.
| 序号 | 城市 | 累计感染人数 | 累计死亡人数 | 累计新增人数 |
|---|---|---|---|---|
| {{$index}} | {{$city.City}} | {{$city.GanRanNum}} | {{$city.DeadNum}} | {{$city.RecentNum}} |
{{end}}
main.go
package main
import (
"github.com/gin-contrib/multitemplate"
"github.com/gin-gonic/gin"
"html/template"
)
type Book struct {
Title string
Price int
}
type Ncov struct {
City string
GanRanNum int
DeadNum int
RecentNum int
}
func index(c *gin.Context){
user:="root"
book01:=Book{Title: "西游记",Price: 99}
book02:=Book{Title: "三国演义",Price: 199}
book03:=Book{Title: "红楼梦",Price: 399}
book04:=Book{Title: "水浒传",Price: 299}
book_list:=[]Book{book01,book02,book03,book04}
c.HTML(200,"index",gin.H{
"user":user,
"book_list":book_list,
})
}
func getNcov(c *gin.Context){
city01:=Ncov{City: "city01",GanRanNum: 100,DeadNum: 3,RecentNum: 10}
city02:=Ncov{City: "city02",GanRanNum: 30,DeadNum: 0,RecentNum: 6}
city03:=Ncov{City: "city03",GanRanNum: 78,DeadNum: 2,RecentNum: 3}
city04:=Ncov{City: "city04",GanRanNum: 50,DeadNum: 3,RecentNum: 5}
ncovList:=[]Ncov{city01,city02,city03,city04}
c.HTML(200,"ncov",gin.H{
"ncovList":ncovList,
})
}
func createMyRender() multitemplate.Renderer {
r:=multitemplate.NewRenderer()
r.AddFromFiles("index","templates/base.html","templates/index.html")
r.AddFromFiles("ncov","templates/base.html","templates/ncov.html")
return r
}
func add(x,y int) int{
return x+y
}
func main() {
r:=gin.Default()
r.SetFuncMap(template.FuncMap{
"add":add,
})
//返回一个html页面
//r.LoadHTMLGlob("templates/*")
r.HTMLRender=createMyRender()
r.GET("/2019ncov",getNcov)
r.GET("/index",index)
r.Run() //监听并在 0.0.0:8080 上启动服务
}