Django实现音乐网站 ⒄

使用Python Django框架制作一个音乐网站,本篇主要是单曲详情页及对

之前开发歌曲详情无数据及分页不存在情况处理。

目录

单曲详情

设置路由

视图处理

引入库文件

读取歌词方法

单曲详情视图

模板渲染

无数据处理

歌手详情-基本信息

视图查询修改

模板判断无数据

歌手头部公共信息

歌手基本信息模板

歌手详情-单曲列表

视图查询修改

模板判断无数据

歌手详情-专辑列表

视图查询修改

模板判断无数据

总结


单曲详情

单曲详情算是一个公共的页面,歌单、排行榜、专辑等都可跳转详情页,

显示相应单曲信息和歌词列表。

设置路由

这次不在设置参数,采用一种新的方式传参。

path('album/song', views.album_song, name='album_song'),

视图处理

引入库文件

接下来需要读取文件和django设置的媒体目录配置,所以要引用下面的类库。

import os
from django.conf import settings

读取歌词方法

通过文件函数读取os连接起来的django设置媒体目录和歌词文件的全路径。

因为查询返回的歌词文件路径是文件格式需要转化为字符串格式。

通过循环文件句柄,将读取的每一行放入列表中。

def read_lyric(path):
    """ 读取歌词文件 """

    f = open(os.path.join(settings.MEDIA_ROOT, str(path)), 'r', encoding='utf-8')
    lines = []
    for line in f:
        lines.append(line)
    f.close()
    return lines

单曲详情视图

这里的参数改为使用request GET 方式读取相应名称参数。

下面通过filter过滤条件,之后first取一条符合条件数据。

歌词字段通过读取歌词方法返回内容判断并赋值;

最后通过locals函数把设置好的变量全都传递给模板。

def album_song(request):
    """ 专辑中单曲详情 """

    id = request.GET.get('id')
    sid = request.GET.get('sid')
    info = Album.objects.filter(id=id).first()
    song_info = Singe.objects.filter(id=sid).first()
    # 歌词处理
    lyrics = []
    if song_info:
        lyrics = read_lyric(song_info.lyric)

    return render(request, 'album/song.html', locals())

模板渲染

模板中主要渲染两部分内容:单曲信息+歌词列表及所属专辑信息。

{% extends 'common/base.html' %}
{% load static %}

{% block title %}我的音乐-单曲{% endblock title %}

{% block content %}
<link rel="stylesheet" href="{% static 'css/album.css' %}">

<!--导航条开始-->
<div class="header">
    <img src="{% static 'images/logo.png' %}" class="logo" alt="">
    <ul>
        <li><a href="{% url 'player:index' %}">推荐</a></li>
        <li><a href="javascript:void(0)">排行榜</a></li>
        <li><a href="javascript:void(0)" class="selected">歌手</a></li>
        <li><a href="javascript:void(0)">歌单</a></li>
    </ul>
</div>
<!--导航条结束-->

<!--专辑内容开始-->
<div class="main_con">
    <div class="content">
        <div class="info_l">
            <div class="cover_out">
                <img src="/media/{{info.cover}}" alt="" class="cover" data-src="info.cover" lazy="loaded">
                <img src="{% static 'images/album_cover_record.png' %}" alt="" class="record">
            </div>
            <p class="intr">专辑简介 </p>
            <p class="intr_txt">
                {{info.desc}}...
            </p>
            <div><a href="javascript:;" class="download bg_primary">
                <i class="glyphicon glyphicon-download-alt"></i>&nbsp;下载这首歌</a>
            </div>
        </div>
        <!--单曲歌词列表开始-->
        <div class="info_r">
            <p class="song_name flex_c">{{info.name}}</p>
            <p class="artist_name flex_c">{{song_info.singler.name}}</p>
            <p class="song_info">
                <span>专辑:</span><span class="tip">{{info.name}}</span>
                <span>发行时间:{{song_info.addtime|date:'Y-m-d'}}</span>
            </p>
            <div class="btns">
                <button class="play bg_primary">
                    <i class="glyphicon glyphicon-play"></i>&nbsp;<span>立即播放</span>
                </button>
                <button><i class="glyphicon glyphicon-plus"></i>&nbsp;<span>添加</span>
                </button>
                <button>
                    <i class="glyphicon glyphicon-heart"></i>&nbsp;<span>收藏</span>
                </button>
            </div>
            <div class="lyric lyricAll">
                {% for line in lyrics %}
                    {% if forloop.counter == 1 %}
                        <p class="active">{{line}}</p>
                    {% else %}
                        <p>{{line}}</p>
                    {% endif %}
                {% empty %}
                    <p>暂无歌词</p>
                {% endfor %}
            </div>
        </div>
        <!--单曲歌词列表结束-->
    </div>
</div>
<!--专辑内容结束-->
{% endblock content %}

 

无数据处理

歌手详情-基本信息

视图查询修改

原本使用get方式查询,这种方式可以获得一条符合条件的数据,缺点在于如果没有符合条件的数据,则会抛出异常;改为filter查询方式,这种方式会返回符合记录的集合。就算没有符合条件的也不会抛出异常,只会返回空集。还需要判断结果进行赋值。

内容如下:

def singer_detail(request, id):
    """ 歌手详情-基本信息 """

    infos = Singler.objects.filter(id=id)
    if infos:
        info = infos[0]
    else:
        info = False
    return render(request, 'singer/detail.html', {'info': info})

 

模板判断无数据

这里需要把视图传递的变量进行渲染,只需要增加判断是否有数据,没数据显示无数据页面即可。

歌手头部公共信息

这里也有歌手信息需要判断,只需要处理路由跳转链接,其他不会报错就不处理了。

内容如下:

<span class="all">
    {% if info %}
    <a href="{% url 'player:singer_detail' info.id %}">全部</a>
    {% else %}
    <a href="javascript:void(0)">全部</a>
    {% endif %}
    > </span>

 

歌手基本信息模板

这里新增两部分内容:

处理跳转链接,即歌手相关信息的跳转链接;

二是增加判断显示无数据内容。

内容如下:

<div class="main_con">
    <div class="con_l">
        <ul class="tabs flex_c">
            <li>
                {% if info %}
                <span class=""><a href="{% url 'player:singer_song' info.id 1 %}">单曲</a></span>
                <span class=""><a href="{% url 'player:singer_album' info.id 1 %}">专辑</a></span>
                {% else %}
                <span class=""><a href="javascript:void(0)">单曲</a></span>
                <span class=""><a href="javascript:void(0)">专辑</a></span>
                {% endif %}
                <span class="active">简介</span>
            </li>
        </ul>
        <div class="child_view">
            {% if not info %}
            <!--设置无数据内容-->
            <div class="nodata flex_c">
                <div class="inner">
                    <img src="{% static 'images/nodata.png' %}"
                         alt="" class="nodata_img">
                    <div class="tip"><p>暂无相关数据</p></div>
                </div>
            </div>
            {% else %}
            <p class="tit">基本信息</p>
            <div class="list_info">
                <div class="info_list flex_c">
                    <div class="item_l">
                        <span>姓名:<span class="text">{{info.name}}</span></span>
                    </div>
                    &nbsp;
                    <div class="item_r">
                        <span>英文名:<span class="text">{{info.english_name}}</span></span>
                    </div>
                </div>
                <div class="info_list flex_c">
                    <div class="item_l">
                        <span>性别:<span class="text">
                            {% if info.gender %}
                                男
                            {% else %}
                                女
                            {% endif %}
                        </span></span>
                    </div>
                    &nbsp;
                    <div class="item_r">
                        <span>国籍:<span class="text">{{info.country_name}}</span></span>
                    </div>
                </div>
                <div class="info_list flex_c">
                    <div class="item_l">
                        <span>生日:<span class="text">{{info.birthday}}</span></span>
                    </div>
                    &nbsp;
                    <div class="item_r">
                        <span>星座:<span class="text">{{info.constellation}}</span></span>
                    </div>
                </div>
                <div class="info_list flex_c">
                    <div class="item_l">
                        <span>身高:<span class="text">{{info.height}}cm</span></span>
                    </div>
                    &nbsp;
                    <div class="item_r">
                        <span>体重:<span class="text">{{info.weight}}kg</span></span>
                    </div>
                </div>
            </div>
            <p class="tit">个人简介</p>
            <p class="info">{{info.desc|safe}}</p>
            {% endif %}
        </div>
    </div>
</div>

 

歌手详情-单曲列表

视图查询修改

歌手基本信息查询把get查询改为filter过滤器查询。

分页数据也要处理无分页和分页超过最大分页情况。

内容如下:

def singer_song(request, id, page):
    """ 歌手详情-单曲列表 """

    # 歌手基本信息
    info = Singler.objects.filter(pk=id).first()

    song_list = Singe.objects.filter(singler_id=id).all()

    # 实例化Paginator
    paginator = Paginator(song_list, 20)

    try:
        res = paginator.page(page)
    except PageNotAnInteger:
        res = paginator.page(1)
    except EmptyPage:
        res = paginator.page(paginator.num_pages)

    return render(request, 'singer/song_list.html', {
        'info': info,
        'songList': res,
        'list_num': len(song_list)
    })

 

模板判断无数据

主要判断跳转链接进行无数据处理。

内容如下:

<ul class="tabs flex_c">
    <li>
        <span class="active">单曲</span>
        {% if info %}
        <span><a href="{% url 'player:singer_album' info.id 1 %}">专辑</a></span>
        <span><a href="{% url 'player:singer_detail' info.id %}">简介</a></span>
        {% else %}
        <span><a href="javascript:void(0)">专辑</a></span>
        <span><a href="javascript:void(0)">简介</a></span>
        {% endif %}
    </li>
</ul>

 

歌手详情-专辑列表

视图查询修改

还是歌手基本信息查询方式修改;分页处理修改;这里使用locals优化传给模板的变量。

内容如下:

def singer_album(request, id, page):
    """ 歌手详情-专辑列表 """

    # 歌手基本信息
    info = Singler.objects.filter(pk=id).first()

    # 专辑列表
    albumList = Album.objects.filter(singler_id=id).order_by('-id').all()

    # 实例化Paginator
    paginator = Paginator(albumList, 20)

    try:
        res = paginator.page(page)
    except PageNotAnInteger:
        res = paginator.page(1)
    except EmptyPage:
        res = paginator.page(paginator.num_pages)

    list_num = len(res)
    return render(request, 'singer/album_list.html', locals())

模板判断无数据

原有的无数据页面不用修改,只需要判断单曲和简介的链接处理。

内容如下:

<ul class="tabs flex_c">
    <li>
        {% if info %}
        <span><a href="{% url 'player:singer_song' info.id 1 %}">单曲</a></span>
        <span class="active">专辑</span>
        <span><a href="{% url 'player:singer_detail' info.id %}">简介</a></span>
        {% else %}
        <span><a href="javascript:void(0)">单曲</a></span>
        <span class="active">专辑</span>
        <span><a href="javascript:void(0)">简介</a></span>
        {% endif %}
    </li>
</ul>

总结

数据查询时,查询单条数据最好使用filter过滤器+first,

如果直接使用get查询,没有符合条件就会抛出异常,

或者也可以使用try对异常进行处理。

模板中要增加无数据提醒内容,这样用户体验会好一点。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

JSON_L

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值