#pip install scenedetect opencv-python -i https://pypi.tuna.tsinghua.edu.cn/simple

from scenedetect.video_manager import VideoManager
from scenedetect.scene_manager import SceneManager
from scenedetect.stats_manager import StatsManager
from scenedetect.detectors.content_detector import ContentDetector
from moviepy.editor import *


# 获取所有文件
def getAllFiles(fire_dir):
    filepath_list = []
    for root,folder_names,file_names in os.walk(fire_dir):
        for file_name in file_names:
            file_path = root+os.sep+file_name
            filepath_list.append(file_path)
            print(file_path)
    print(filepath_list)
    return filepath_list


#获取智能画面分割的时间或者秒数
def find_scenes(video_path):
    video_manager = VideoManager([video_path])
    stats_manager = StatsManager()
    scene_manager = SceneManager(stats_manager)

    # 使用contect-detector
    scene_manager.add_detector(ContentDetector())

    shijian_list = []

    try:
        video_manager.set_downscale_factor()

        video_manager.start()

        scene_manager.detect_scenes(frame_source=video_manager)

        scene_list = scene_manager.get_scene_list()
        print("scene_list:")
        print(scene_list)



        print('List of scenes obtained:')
        for i, scene in enumerate(scene_list):
            shijian_list.append([scene[0].get_timecode(),scene[1].get_timecode()])
            print(
                'Scene %2d: Start %s / Frame %d, End %s / Frame %d' % (
                    i + 1,
                    scene[0].get_timecode(), scene[0].get_frames(),
                    scene[1].get_timecode(), scene[1].get_frames(),))


    finally:
        video_manager.release()

    return shijian_list

#将时间字符转为毫秒数
#字符形式:00:00:06.867
def zifuToHaoMiaoStart(zifu):
    line = zifu.split(".")
    print("line_list")
    print(line)
    haomiao = int(line[1])
    line = line[0].split(":")
    seconds = int(line[0]) * 3600 + int(line[1]) * 60 + int(line[2])
    zuizong_miao = (seconds*1000+haomiao)/1000
    print(zuizong_miao)
    return zuizong_miao

#将时间字符转为毫秒数
#字符形式:00:00:06.867
def zifuToHaoMiaoEnd(zifu):
    line = zifu.split(".")
    print("line_list")
    print(line)
    haomiao = int(line[1])
    line = line[0].split(":")
    seconds = int(line[0]) * 3600 + int(line[1]) * 60 + int(line[2])
    zuizong_miao = (seconds*1000+haomiao-1)/1000
    print(zuizong_miao)
    return zuizong_miao

#切分一个画面
def getOneHuaMian(start_time_str,end_time_str,yuan_video_path,num):
    # 剪辑'00:00:00.000' - '00:00:06.867'
    start_time_str = start_time_str
    start_sec = zifuToHaoMiaoStart(zifu=start_time_str)
    end_time_str = end_time_str
    end_sec = zifuToHaoMiaoEnd(zifu=end_time_str)
    video_path = yuan_video_path
    video = CompositeVideoClip([VideoFileClip(video_path).subclip(start_sec, end_sec)])
    #获取文件后缀
    wenjianming = os.path.splitext(video_path)[0]
    createDir(wenjianming)  #创建一个和视频同名的文件夹
    houzuo = os.path.splitext(video_path)[-1]
    print("文件名:")
    print(wenjianming)
    print("文件后缀")
    print(houzuo)
    danchumingzi = wenjianming.split("\\")[-1]
    print("单纯文件名字:")
    print(danchumingzi)


    video.write_videofile("%s//%s_%s.mp4" % (wenjianming,danchumingzi,str(num)))

#如果不存在就创建
def createDir(file_dir):
    # 如果不存在文件夹,就创建
    if not os.path.isdir(file_dir):
        os.mkdir(file_dir)

#切分一个视频
def clipOneVideo(video_path):
    shijian_list = find_scenes(video_path) #多组时间列表
    print(shijian_list)
    shijian_list_len = len(shijian_list)
    # duozu_shijian_list = []   #多组时间列表
    # if shijian_list_len>1:
    #     for i in range(0,shijian_list_len-1):
    #         yizu_shijian_list = []   #一组时间列表
    #         yizu_shijian_list.append(shijian_list[i])
    #         yizu_shijian_list.append(shijian_list[i+1])
    #         duozu_shijian_list.append(yizu_shijian_list)
    # print("duozu_shijian_list:")
    # print(duozu_shijian_list)
    #
    # duozu_shijian_list_len = len(duozu_shijian_list)
    print("总共有%s个场景" % str(shijian_list_len))
    for i in range(0,shijian_list_len):
        start_time_str = shijian_list[i][0]
        end_time_str = shijian_list[i][1]
        getOneHuaMian(start_time_str, end_time_str, yuan_video_path=video_path, num=i+1)
        print("第%s个镜头剪切完成" % str(i+1))
        print("总共有%s个场景,第%s个镜头剪切完成" % (str(shijian_list_len),str(i+1)))


#循环处理一个文件夹下所有的视频文件
def getAllVideo(gen_dir):
    all_file_list = getAllFiles(gen_dir)
    for file_name in all_file_list:
        if ".mp4".lower() in file_name.lower():
            clipOneVideo(file_name)


if __name__ == '__main__':
    gen_dir = r"F:\存储盘\古风美女素材下载\筛选出的可用的视频"
    getAllVideo(gen_dir)
    # video_path = r'D:\PycharmProjects\cigenpic\视频切割\2023091911502.mp4'
    # clipOneVideo(video_path)

直接可运行,提示没有相应的模块的,可以pip install 安装一下即可

 

第二版更完善,可以直接用

#pip install scenedetect opencv-python -i https://pypi.tuna.tsinghua.edu.cn/simple

from scenedetect.video_manager import VideoManager
from scenedetect.scene_manager import SceneManager
from scenedetect.stats_manager import StatsManager
from scenedetect.detectors.content_detector import ContentDetector
from moviepy.editor import *
import shutil


# 获取所有文件
def getAllFiles(fire_dir):
    filepath_list = []
    for root,folder_names,file_names in os.walk(fire_dir):
        for file_name in file_names:
            file_path = root+os.sep+file_name
            filepath_list.append(file_path)
            print(file_path)
    print(filepath_list)
    return filepath_list


#获取智能画面分割的时间或者秒数
def find_scenes(video_path):
    video_manager = VideoManager([video_path])
    stats_manager = StatsManager()
    scene_manager = SceneManager(stats_manager)

    # 使用contect-detector
    scene_manager.add_detector(ContentDetector())

    shijian_list = []

    try:
        video_manager.set_downscale_factor()

        video_manager.start()

        scene_manager.detect_scenes(frame_source=video_manager)

        scene_list = scene_manager.get_scene_list()
        print("scene_list:")
        print(scene_list)



        print('List of scenes obtained:')
        for i, scene in enumerate(scene_list):
            shijian_list.append([scene[0].get_timecode(),scene[1].get_timecode()])
            print(
                'Scene %2d: Start %s / Frame %d, End %s / Frame %d' % (
                    i + 1,
                    scene[0].get_timecode(), scene[0].get_frames(),
                    scene[1].get_timecode(), scene[1].get_frames(),))


    finally:
        video_manager.release()

    return shijian_list

#将时间字符转为毫秒数
#字符形式:00:00:06.867
def zifuToHaoMiaoStart(zifu):
    line = zifu.split(".")
    print("line_list")
    print(line)
    haomiao = int(line[1])
    line = line[0].split(":")
    seconds = int(line[0]) * 3600 + int(line[1]) * 60 + int(line[2])
    zuizong_miao = (seconds*1000+haomiao)/1000
    print(zuizong_miao)
    return zuizong_miao

#将时间字符转为毫秒数
#字符形式:00:00:06.867
def zifuToHaoMiaoEnd(zifu):
    line = zifu.split(".")
    print("line_list")
    print(line)
    haomiao = int(line[1])
    line = line[0].split(":")
    seconds = int(line[0]) * 3600 + int(line[1]) * 60 + int(line[2])
    zuizong_miao = (seconds*1000+haomiao-1)/1000
    print(zuizong_miao)
    return zuizong_miao

#切分一个画面
def getOneHuaMian(start_time_str,end_time_str,yuan_video_path,num):
    # 剪辑'00:00:00.000' - '00:00:06.867'
    start_time_str = start_time_str
    start_sec = zifuToHaoMiaoStart(zifu=start_time_str)
    end_time_str = end_time_str
    end_sec = zifuToHaoMiaoEnd(zifu=end_time_str)
    video_path = yuan_video_path
    video = CompositeVideoClip([VideoFileClip(video_path).subclip(start_sec, end_sec)])
    #获取文件后缀
    wenjianming = os.path.splitext(video_path)[0]
    createDir(wenjianming)  #创建一个和视频同名的文件夹
    houzuo = os.path.splitext(video_path)[-1]
    print("文件名:")
    print(wenjianming)
    print("文件后缀")
    print(houzuo)
    danchumingzi = wenjianming.split("\\")[-1]
    print("单纯文件名字:")
    print(danchumingzi)


    video.write_videofile("%s//%s_%s.mp4" % (wenjianming,danchumingzi,str(num)))

#如果不存在就创建
def createDir(file_dir):
    # 如果不存在文件夹,就创建
    if not os.path.isdir(file_dir):
        os.mkdir(file_dir)

#切分一个视频
def clipOneVideo(video_path):
    shijian_list = find_scenes(video_path) #多组时间列表
    print(shijian_list)
    shijian_list_len = len(shijian_list)

    print("总共有%s个场景" % str(shijian_list_len))
    for i in range(0,shijian_list_len):
        start_time_str = shijian_list[i][0]
        end_time_str = shijian_list[i][1]
        getOneHuaMian(start_time_str, end_time_str, yuan_video_path=video_path, num=i+1)
        print("第%s个镜头剪切完成" % str(i+1))
        print("总共有%s个场景,第%s个镜头剪切完成" % (str(shijian_list_len),str(i+1)))

#移动文件到指定文件夹下的yiqiege目录
def moveFile(gen_dir,file_path):
    # 将已经切割的移动到已经切割文件夹gen_dir
    zhumulu = str(gen_dir).strip(gen_dir.split("\\")[-1])
    # 创建文件夹
    qiegewenjianjia = r"%s\yiqiege" % zhumulu
    print("切割文件夹名字:")
    print(qiegewenjianjia)
    createDir(qiegewenjianjia)
    try:
        # 移动文件到文件夹目录中
        shutil.move(file_path, qiegewenjianjia)
        print("移动文件%s到已切割文件夹" % file_path)
    except Exception as e:
        print("移动出错:%s" % str(e))

#循环处理一个文件夹下所有的视频文件
def getAllVideo(gen_dir):
    all_file_list = getAllFiles(gen_dir)
    for file_name in all_file_list:
        if ".mp4".lower() in file_name.lower():
            try:
                clipOneVideo(file_name)
                #处理完成后,将该视频移动已剪切文件夹下
                moveFile(gen_dir, file_name)
            except Exception as e:
                print("报错:%s" % str(e))


if __name__ == '__main__':
    gen_dir = r"F:\存储盘\古风美女素材下载\筛选出的可用的视频\原视频"
    getAllVideo(gen_dir)
    # video_path = r'D:\PycharmProjects\cigenpic\视频切割\2023091911502.mp4'
    # clipOneVideo(video_path)

 

posted on 2023-09-27 20:10  大话人生  阅读(365)  评论(0编辑  收藏  举报