python3GUI--抖音无水印视频下载工具(附源码)

文章目录

  • 一.准备工作
  • 二.预览
    • 1.启动
    • 2.运行
    • 3.结果
  • 三.设计流程
    • 1.总体设计
    • 2.详细设计
  • 四.源代码
  • 五.说明&总结

hello,大家好啊,失踪人口回归了 [捂脸]!本次使用tkinter撰写一篇 抖音无水印视频下载,目的很纯粹,就是为了设置 微信状态视频。本篇博文中,我会写下我的代码撰写思路以及想写设计流程,代码放在了第四节,工具打包好放在了 蓝奏云,慢慢看,后面有链接。

一.准备工作

本次要用到以下依赖库:re json os random tkinter threading requests pillow 其中后两个需要安装后使用

二.预览

1.启动

python3GUI--抖音无水印视频下载工具(附源码)_第1张图片

2.运行

python3GUI--抖音无水印视频下载工具(附源码)_第2张图片

3.结果

python3GUI--抖音无水印视频下载工具(附源码)_第3张图片

(小姐姐挺漂亮,视频确实无水印

三.设计流程

设计流程分为总体设计和详细设计,这里我会使用viso画出几个流程图,用以展示我的思路,详细设计部分列举了两个函数实现的具体流程。

1.总体设计

python3GUI--抖音无水印视频下载工具(附源码)_第4张图片

2.详细设计

2.1 parse()函数

python3GUI--抖音无水印视频下载工具(附源码)_第5张图片

2.2 download()函数
python3GUI--抖音无水印视频下载工具(附源码)_第6张图片

四.源代码

#--*coding:utf-8*--
from tkinter import *
from tkinter import ttk
from tkinter import messagebox
import os
import json
import threading
import requests
from PIL import Image,ImageTk

'''
抖音无水印视频下载工具
难点:1.视频接口
      2.进度条
'''
def clean_progressbar():
    # 清空进度条
    fill_line = canvas.create_rectangle(1.5, 1.5, 0, 23, width=0, fill="white")
    x = 500  # 未知变量,可更改
    n = 600 / x  # 465是矩形填充满的次数
    for t in range(x):
        n = n + 600 / x
        # 以矩形的长度作为变量值更新
        canvas.coords(fill_line, (0, 0, n, 60))
        window.update()

def download():
    #先清空进度条,再下载
    clean_progressbar()
    real_link=t1.get('0.0',END).split('**')[-1]
    headers2 = {
     
        'sec-fetch-dest': 'document',
        'user-agent': 'Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/88.0.4324.104 Mobile Safari/537.36'
    }
    r2 = requests.get(real_link, headers=headers2, stream=True)
    try:
        os.mkdir(video_path)
    except:
        pass
    file =video_path+ video_title + '.mp4'
    #下载与进度条
    chunk_size = 1024  # 每一块的大小,每次下载块的大小
    file_size = int(r2.headers['Content-Length'])  # 提取出来的文件大小为string格式,使用int()强制转化
    fill_line = canvas.create_rectangle(1.5, 1.5, 0, 23, width=0, fill="green")
    raise_data = 600 / (file_size / chunk_size)  # 增量大小,600为进度条的长度
    _size = 0  # 已经下载文件的大小
    with open(file, "wb") as f:
        n=0
        for data in r2.iter_content(chunk_size):  # inter_content:用于边下载边存硬盘,每次下载chunk_size大小的块
            f.write(data)
            n = n + raise_data
            canvas.coords(fill_line, (0, 0, n, 60))
            window.update()
    #下载完以后清空
    t1.delete('0.0',END)
    t1.insert(END,'{title}.mp4\n下载完成!'.format(title=video_title))

#解析出无水印视频下载地址以及视频标题
def parse(share_link):
    # 先处理短链接获取item_ids
    headers = {
     
        'accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9',
        'sec-fetch-dest': 'document',
        'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/88.0.4324.104 Safari/537.36'
    }
    # 使用allow_redirects=False禁止重定向,拿到重定向的url
    r1 = requests.get(share_link, allow_redirects=False, headers=headers)
    item_ids = re.findall(r'video/(\d+)/', r1.text)
    interface_url='https://www.iesdouyin.com/web/api/v2/aweme/iteminfo/?item_ids={}'.format(''.join(item_ids))
    r=requests.get(interface_url,headers=headers)
    _json=json.loads(r.text)
    try:
        item_list=_json.get('item_list')[0]
        video_title=item_list.get('desc')#视频名称
        watermark_video_link=item_list.get('video').get('play_addr').get('url_list')[0]#视频带水印地址
        real_video_link=watermark_video_link.replace('playwm','play')#视频无水印地址
        return video_title,real_video_link
    except TypeError:
        messagebox.showerror('提示','请检查输入地址!')
        t1.delete('0.0',END)
        return '输入地址有误','请检查!'

#调用jiexi()将视频标题和下载链接显示在Text Widget中
def pre_parse():
    share_link=e1.get()
    if len(share_link)!=0:
        global video_title, real_video_link
        try:
            video_title, real_video_link=parse(share_link)
        except TypeError:
            t1.insert(END,'输入地址有误,请检查!')
        t1.delete('0.0',END)
        #去除标题中的表情以及符号,只保留汉字
        try:
            t1.insert(END, video_title + '\n' +'*'*30+ real_video_link)
            b2.config(state='normal')
        except TclError:
            filted_title=re.findall(r'[\u4E00-\u9FA5\s]+',video_title)
            t1.insert(END,''.join(filted_title)+'\n'+'*'*30+real_video_link)
            b2.config(state='normal')
    else:
        messagebox.showerror('错误','请输入地址!')
        t1.delete('0.0',END)
        t1.insert(END,'请在上面输入地址!')

#打开文件夹函数
def open_dir():
    try:
        os.mkdir(video_path)
    except:
        pass
    abs_path=os.path.abspath(video_path)
    os.startfile(abs_path)

#退出窗口函数
def quit_window():
    window.destroy()

#函数打包进线程
def thread_it(func,*args):
    t=threading.Thread(target=func,args=args)
    t.setDaemon(True)#先守护主线程
    t.start()#再启动

if __name__ == '__main__':
    video_path='./video/'
    window=Tk()
    window.title('Downloader-v1.0')
    width=295
    height=380
    screenWidth = window.winfo_screenwidth()  # 获取显示区域的宽度
    screenHeight = window.winfo_screenheight()  # 获取显示区域的高度
    left = (screenWidth - width) / 2
    top = (screenHeight - height) / 2
    window.geometry("%dx%d+%d+%d" % (width, height, left, top))
    window.resizable(0,0)

    window.iconbitmap('./rely/my_favicon.ico')
    photo=Image.open('./rely/dy_logo.png')
    photo=photo.resize((200,50))
    image=ImageTk.PhotoImage(photo)
    l0=ttk.Label(window,imag=image,justify='center')
    l0.pack()
    f1=ttk.Labelframe(window,text='视频链接地址:')
    f1.place(x=40,y=55)
    e1=ttk.Entry(f1,width=30)
    e1.pack()
    f2=ttk.Labelframe(window,text='信息:')
    f2.place(x=40,y=102)
    t1=Text(f2,height=6,width=30)
    t1.pack()
    t1.insert(END,'{_xing}\n将抖音分享链接地址粘贴在上面输入框中,本程序会自动解析出视频的下载地址并且显示在这里\n{_xing}'.format(_xing='*'*29))
    b1=ttk.Button(window,text='解析',command=lambda :thread_it(pre_parse))
    b1.place(x=40,y=265)
    b2=ttk.Button(window,text='下载',state='disable',command=lambda :thread_it(download))
    b2.place(x=170,y=265)
    b3=ttk.Button(window,text='打开文件夹',command=open_dir)
    b3.place(x=40,y=298)
    b4=ttk.Button(window,text='退出',command=quit_window)
    b4.place(x=170,y=298)

    f3=ttk.Labelframe(window)
    f3.place(x=40,y=329)
    l1=ttk.Label(f3,text='  敬告:本软件仅供学习交流使用!',width=30,justify='center',foreground='red')
    l1.pack(fill=X)

    f4=ttk.LabelFrame(window,text='下载进度:')
    f4.place(x=40,y=210)
    canvas = Canvas(f4, width=210, height=20,bg="white")
    canvas.pack(side='left')

    l2_var=StringVar()
    l2=ttk.Label(f4,textvariable=l2_var,text='未下载')
    l2.pack(side='left',anchor=S)

    window.mainloop()
    '''
    test_url:   https://v.douyin.com/JcxTMj2/
    '''


五.说明&总结

5.1说明:

所示截图均为举例,本软件仅供学习交流使用!

5.2总结:
本次使用python的tkinter撰写了一个抖音无水印视频爬取GUI工具,因为中间写过几个GUI界面了对tkinter的widget有些熟悉了,线程用起来更加熟练。他山之石,可以攻玉,本次思路、代码的撰写参考了:

tkinter实现下载进度条(python)

以上帮助我解决了进度条问题。

最新版抖音(20200624)去水印原理及源码,简单的原理与面临的挑战

以上帮助我解决了视频接口获取问题。

在此感谢帮助我的人!,工具已经打包上传到了蓝奏云https://wws.lanzous.com/isCLul0dlfa
, 思路、代码方面有什么不足欢迎各位大佬指正、批评!觉得工具还行的话点个呗!
python3GUI--抖音无水印视频下载工具(附源码)_第7张图片

你可能感兴趣的:(GUI,python爬虫,python小工具,python,gui,tkinter)