#标题block
{% block title %}课程机构列表 - 慕学在线网{% endblock %}
#css block
{% block customcss %}{% endblock %}
#js bolck
{% block customjs %}{% endblock %}
{% block custom_bread %}
- 首页>
- 课程机构
{% endblock %}
#整个section部分是需要修改的
{% block content %}
{%endblock%}
在新建的html文件中,需要复用html模板的,直接继承,并对需要修改的block进行修改,利用{% extends ‘模板文件’ %},直接对html文件进行继承
{% extends 'organization_base.html' %}
{% load staticfiles %}
{% block title %}替换html的title{% endblock %}
{% block custom_bread %}
- 首页>
- 我爱张馨
{% endblock %}
{% block content %}
写好url,并绑定好view即可
#url
url(r'organiztion_list/$',OrganiztionListView.as_view(),name='organiztion_list'),
#view逻辑
class OrganiztionListView(View):
def get(self,request):
return render(request, 'org_list.html',{})
每个页面的user信息传入,Django已经为我们做好的user信息的封装,登陆信息保存在requests中,并以session与服务器进行握手确认,添加登陆信息只需要将user信息在模板中读取出来即可
1.{% if request.user.is_authenticated %}用于确认用户的登陆情况
2.{% else %}逻辑用于若未登陆则返回默认的头部
3.注意{% endif %}
{% if request.user.is_authenticated %}
{% else %}
{% endif %}
设置好用户上传的路径
在settings中设置MEDIA_URL和MEDIA_ROOT将自动绑定为upload_to的资源上传相对路径
MEDIA_URL = '/media/'
MEDIA_ROOT = os.path.join(BASE_DIR, "media")
若不这样做的话,也可以在upload_to中写清楚相对服务器的根路径
CoursePicture = models.ImageField(upload_to='static/Pic/courses/%Y/%m',max_length=500,verbose_name=u'课程封面')
静态资源static和media
利用model传值进html中并进行动态展示
设置好视图函数View
class OrganiztionListView(View):
def get(self,request):
all_city = CityDict.objects.all()
all_org = CourseOrganization.objects.all()
org_num = all_org.count()
return render(request, 'org_list.html',{
'all_city':all_city,
'all_org':all_org,
'org_num':org_num,
})
在Template模板中用for循环进行循环插入数据
#City修改
全部
{% for city in all_city %}
{{ city.CityName }}
{% endfor %}
#课程机构修改,暂时只插入课程名称,课程地址,课程图片
{% for org in all_org %}
{% endfor %}
图片的插入,设置动态资源media的映射路径
1.视图中传入参数
class OrganiztionListView(View):
def get(self,request):
all_city = CityDict.objects.all()
all_org = CourseOrganization.objects.all()
org_num = all_org.count()
return render(request, 'org_list.html',{
'all_city':all_city,
'all_org':all_org,
'org_num':org_num,
})
2.在settings的TEMPLATES中写入media,为了将{{ MEDIA_URL }}注册到html中
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [os.path.join(BASE_DIR, 'templates')]
,
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
'django.core.context_processors.media',
],
},
},
]
3.在html模板中写入文件的相对路径
{{ MEDIA_URL }}{{ org.OrganizationImage }}
4.在url中配置好上传图片资源的访问处理函数,即映射路径
from django.views.static import serve
from GMOOC.settings import MEDIA_ROOT
url(r'^media/(?P.*)/$', serve, {"document_root":MEDIA_ROOT},name='img_path'),
设置完MEDIA_URL和url.py影射路径后,可以从浏览器输入127.0.0.1:8000/media/图片路径.jpg访问到相关的图片。
映射路径
分页功能
python第三方库-pure pagination用于Django分页
安装方法:
cd进入相应的环境(虚拟环境),执行pip django-pure-pagination ,完成安装
在setting的install app中,添加应用pure_pagination
INSTALLED_APPS = (
...
'pure_pagination',
)
在setting中增加pure-pagination的setting
PAGINATION_SETTINGS = {
'PAGE_RANGE_DISPLAYED': 10,
'MARGIN_PAGES_DISPLAYED': 2,
'SHOW_FIRST_PAGE_WHEN_INVALID': True,
}
在view中改写分页函数的设置
class OrganiztionListView(View):
def get(self,request):
all_city = CityDict.objects.all()
all_org = CourseOrganization.objects.all()
org_num = all_org.count()
try:
page = request.GET.get('page', 1)
except PageNotAnInteger:
page = 1
# Provide Paginator with the request object for complete querystring generation
p = Paginator(all_org,1,request=request)
orgs = p.page(page)
return render(request, 'org_list.html',{
'all_city':all_city,
'all_org':orgs,
'org_num':org_num,
})
因为使用pure-pagination对分页功能进行封装,所以原本属于all_orgs的元素内容全部封装在object_list内
{% for org in all_org.object_list %}
{% endfor %}
重新修改Template中页码的设置
{# 判断是否有前一页逻辑 #}
{% if all_org.has_previous %}
上一页
{% endif %}
{# 中间页码 #}
{% for page in all_org.pages %}
{% ifequal page all_org.number %} {# 判断是否是当前页 #}
{{ page }}
{% else %} {# 如果不是当前页的话 #}
{{ page }}
{% endifequal %}
{% endfor %}
{# 判断是否有后一页逻辑 #}
{% if all_org.has_next %}
下一页
{% endif %}
使用外键的时候,在mysql中储存为某外键_id的形式
若还未经过设置,则页面通过href进行跳转,前端依靠url后面的“?参数”对页面的参数进行上传,后端通过request.GET.get获取参数,并通过在view中和Template中设置对信息进行处理和显示
注意数据格式
筛选功能
修改视图函数-view
class OrganiztionListView(View):
def get(self,request):
all_city = CityDict.objects.all()
all_org = CourseOrganization.objects.all()
###############################城市筛选功能###################################
city_id = request.GET.get('city','')
if city_id:
all_org = all_org.filter(City_id = int(city_id))
##########################################################################
###############################机构筛选功能###################################
category = request.GET.get('ct', '')
if category:
all_org = all_org.filter(Caterory=category)
##########################################################################
#筛选完毕后对展示数据进行统计
org_num = all_org.count()
###############################分页功能###################################
try:
page = request.GET.get('page', 1)
except PageNotAnInteger:
page = 1
# Provide Paginator with the request object for complete querystring generation
p = Paginator(all_org,10,request=request)
orgs = p.page(page)
##########################################################################
return render(request, 'org_list.html',{
'all_city':all_city,
'all_org':orgs,
'org_num':org_num,
'city_id':city_id,
'category':category,
})
城市筛选函数
city_id = request.GET.get('city','')
if city_id:
all_org = all_org.filter(City_id = int(city_id))
利用request.GET.get获取url中的city参数,并传给city_id,如果存在city_id则调用过滤函数,对展示数据all_org进行过滤
机构筛选函数
category = request.GET.get('ct', '')
if category:
all_org = all_org.filter(Caterory=category)
利用request.GET.get获取url中的ct参数,并传给category,如果存在category则调用过滤函数,对展示数据all_org进行过滤
城市筛选和机构筛选是串联的,实现双层过滤
修改Template进行展示
机构部分,选择“全部”时,href跳转至 ?city={{ city.id }} 保留city的选择,当选择不同机构时候,“href跳转至 ?ct=机构代码&city={{ city_id }}” 保留city的选择,同时将ct和city的参数传递至url,发送至后端在视图函数中进行判断,反馈正确的数据给前端。
全部
{# 不会变化,所以写死 #}
培训机构
高校
个人
/div>
城市部分,选择“全部”时,href跳转至 ?ct={{ category }} 保留ct的选择。利用for循环遍历所有城市,当选择不同城市的时候,href跳转至 “?ct={{ category }}&city={{ city.id }}” 保留ct的选择,同时将ct和city的参数传递至url,发送至后端在视图函数中进行判断,反馈正确的数据给前端。
city_id 是从前端单击筛选后给到后端的数据,同时也是后端经过判断后返回给前端的状态数据,city.id是遍历CityDict后展示在前端的city筛选数据,通过对city.id和city_id的相同判断后,确定哪个是正被选择的项(简单的说就是后端给出过滤后的数据后,同时把过滤条件city的值传回给Template,在Template中判断筛选项和正在使用的过滤条件是否温吻合,相同的话即为正在被选中的项。)
注意数据格式的不同,city.id和city_id的数据格式不同,所以用 |stringformat:’i’ 将city.id转化为字符串
全部
{% for city in all_city %}
{{ city.CityName }}
{% endfor %}
热门排名
在视图函数中配置逻辑,利用order_by函数对all_org进行排序,自定排序逻辑
hot_orgs = all_org.order_by("-FavoriteNumber")[0:3] #倒叙排名
在view中传值至模板,在Template中进行展示,forloop.counter是for的内置参数,用于每次for循环的计数
授课机构排名
{% for course in hot_orgs %}
- {{ forloop.counter }}
-
{{ course.Organization }}
{{ course.City }}
{% endfor %}
课程排序
增加字段SutdentNumber和CourseNumber
StudentNumber = models.IntegerField(verbose_name=u'学习人数',default=0)
CourseNumber = models.IntegerField(verbose_name=u'课程数',default=0)
照例完成数据库迁移
在视图函数中完成排序逻辑函数
#需要筛选完成后才能进行排序
sort = request.GET.get('sort', '') # 过去参数
if sort:
if sort == 'student': #按学生人数进行排名
all_org = all_org.order_by('-StudentNumber') #倒叙排列
if sort == 'course': #按学生人数进行排名
all_org = all_org.order_by('-CourseNumber') #倒叙排列
在Template中完成展示函数,利用if判断选中状态,利用href将选中状态通过url传递给后端进行逻辑判断并兼容前面的机构筛选和地区筛选功能