Trải nghiệm cảm giác thắng lớn với 7win Mô tả 7win - Nơi bạn thể hiện tài năng và may mắn với cơ hội thắng lớn trong các trò chơi cá cược trực tuyến tại 7win. Hãy tham gia ngay
Gần đây, tôi tình cờ xem một đoạn video có hiệu ứng “kéo theo nét đứt”, điều này khiến tôi rất tò mò và muốn thử tạo ra một số hiệu ứng tương tự. Ban đầu, tôi nghĩ sẽ dùng phần mềm dựng video như Premiere để làm việc này, nhưng mỗi lần thực hiện cần ít nhất 60 khung hình được trích xuất từ video, và các khung hình phải cách nhau đều nhau. Việc làm thủ công như vậy không chỉ mất thời gian mà còn dễ gây nhàm chán. Vì vậy, tôi đã quyết định viết một chương trình nhỏ bằng Python để tự động hóa quá trình này.
Một. Chuẩn bị ban đầu
Python sở hữu nhiều thư viện mạnh mẽ, vì vậy việc trích xuất khung hình từ video trở nên đơn giản hơn bao giờ hết. Sau khi tìm kiếm trên mạng, tôi phát hiện rằng chỉ cần sử dụng thư viện cv2 là có thể hoàn thành mục tiêu của mình. Với một chút nghiên cứu cơ bản, tôi đã bắt tay vào viết code ngay lập tức.
Hai. Tạo thư mục lưu trữ
Việc trích xuất khung hình có thể dẫn đến hàng trăm tệp ảnh được lưu rải rác nếu không có kế hoạch rõ ràng. Do đó, trước tiên, tôi tạo một thư mục chuyên dụng để lưu trữ các khung hình. Dưới đây là đoạn mã:
1
2
3
4
# Tạo thư mục tên là "images"
output_folder = 'images'
if not os.path.exists(output_folder):
os.makedirs(output_folder)
Như vậy, chúng ta đã có một nơi lưu trữ tập trung cho các khung hình trích xuất.
Ba. Trích xuất khung hình
1. Xác định đường dẫn video
Ban đầu, tôi chọn video cùng thư mục với script để xử lý. Để lấy danh sách các video trong cùng thư mục, tôi sử dụng đoạn mã sau:
1
2
3
4
5
# Lấy tất cả các file video trong thư mục hiện tại
video_files = glob.glob("*.mp4") + glob.glob("*.avi") # Có thể thêm các định dạng khác nếu cần
print(f'{video_files}')
key = int(input('Chọn video bạn muốn trích xuất (nhập 0 để chọn video đầu tiên):'))
video_file = video_files[key] # Gán video được chọn
Khi tôi thử nghiệm, tôi nhận thấy rằng TikTok sắp xếp các ảnh theo thời gian sửa đổi. Do đó, tôi quyết định thiết lập lại thời gian sửa đổi cho từng khung hình theo thứ tự tăng dần. Đây là một phần của đoạn sanvip.club mã liên quan:
1
2
3
4
5
6
7
8
9
10
# Thiết lập thời gian cho từng khung hình
cap = cv2.VideoCapture(video_file)
fps = cap.get(cv2.CAP_PROP_FPS)
print(f'Tốc độ khung hình: {fps}')
interval = int(fps * float(frame_seconds)) # frame_seconds là khoảng cách trích xuất
i = 0
frame_count = 0
current_time = datetime.now() # Thời gian hiện tại
one_day = timedelta(days=1) # Thêm 1 ngày
new_time = current_time - one_day # Cập nhật thời gian mới
(B) Bắt đầu trích xuất
Tôi sử dụng vòng lặp để đọc từng khung hình và kiểm tra xem nó có đáp ứng điều kiện trích xuất hay không. Nếu đạt yêu cầu, khung hình sẽ được lưu lại. Dưới đây là toàn bộ đoạn mã chi tiết:
while cap.isOpened():
ret, frame = cap.read()
if not ret:
break
frame_count += 1
if frame_count % interval == 0 or is_first_frame is True:
is_first_frame = False
i += 1
video_name = os.path.splitext(video_file)[0] # Tên video không chứa đuôi
output_file = os.path.join(output_folder, f"{i}-{video_name}_frame{frame_count}.jpg")
jpeg_binary = cv2.imencode('.jpg', frame)[1] # Mã hóa khung hình thành JPEG
try:
with open(output_file, 'wb+') as f:
f.write(jpeg_binary)
print(f'Lưu thành công: {output_file}')
one_minute = timedelta(minutes=1) # Thêm 1 phút
new_time += one_minute # Cập nhật thời gian
formatted_time = new_time.strftime('%Y:%m:%d %H:%M:%S') # Định dạng thời gian
FixTime.writeTime(output_file, formatted_time) # Gọi hàm cập nhật thời gian
except Exception as e:
print(f'Lỗi khi lưu: {e}')
a = input('Đã dừng chương trình. Nhấn bất kỳ phím nào để thoát.')
sys.exit()
cap.release()
cv2.destroyAllWindows()
3. Cách thức thay đổi thời gian của ảnh
Trong quá trình thực hiện, tôi gặp khó khăn khi cố gắng thay đổi thời gian tạo và sửa đổi của ảnh. May mắn thay, tôi tìm thấy một bài viết hướng dẫn chi tiết về cách điều chỉnh thời gian của ảnh dựa trên thông tin EXIF. Bài viết này đi kèm với một đoạn mã nguồn giúp giải quyết vấn đề một cách hiệu quả. Tôi đã sử dụng trực tiếp đoạn mã này để tối ưu hóa quy trình. Xin chân thành cảm ơn tác giả của bài viết!
importosimportpiexiffromwin32fileimportCreateFile,SetFileTime,GetFileTime,CloseHandlefromwin32fileimportGENERIC_READ,GENERIC_WRITE,OPEN_EXISTINGfrompywintypesimportTimeimporttimeclassModifTime2ShootTime:def__init__(self,path):self.dir_path=pathself.current_file_path=""self.current_file_time=""self.custom_file_time=""defmodifDirAllFile(self):file_name_list=os.listdir(self.dir_path)forfile_nameinfile_name_list:ifnotfile_name.endswith(".JPG"):continueself.current_file_path=self.dir_path+file_nameprint(self.current_file_path)self.readShootTime()print(self.current_file_time)writeTime(self.current_file_path,self.custom_file_time)time.sleep(0.01)defreadShootTime(self):exif_dict=piexif.load(self.current_file_path)try:time_str=str(exif_dict["Exif"][36868])self.current_file_time=time_str[2:len(time_str)-1]except:self.current_file_time=self.custom_file_timedeftimeOffsetAndStruct(times,format,offset):returntime.localtime(time.mktime(time.strptime(times,format))+offset)defwriteTime(file_path,file_times):format="%Y:%m:%d %H:%M:%S"cTime_t=timeOffsetAndStruct(file_times,format,0)mTime_t=timeOffsetAndStruct(file_times,format,1)aTime_t=timeOffsetAndStruct(file_times,format,2)fh=CreateFile(file_path,GENERIC_READ|GENERIC_WRITE,0,None,OPEN_EXISTING,0,0)createTimes,accessTimes,modifyTimes=GetFileTime(fh)createTimes=Time(time.mktime(cTime_t))accessTimes=Time(time.mktime(aTime_t))modifyTimes=Time(time.mktime(mTime_t))SetFileTime(fh,createTimes,accessTimes,modifyTimes)CloseHandle(fh)if__name__=='__main__':# Ví dụ: thay đổi thời gian cho tất cả ảnh JPG trong một thư mục# modif = ModifTime2ShootTime("D:\\Downloads\\Compressed\\iCloud\\20160615192000\\")# modif.custom_file_time = "2016:06:15 19:20:00"# modif.modifDirAllFile()# Thay đổi thời gian cho một file cụ thểwriteTime("D:\\Downloads\\Compressed\\iCloud\\day\\IMG_4496.mp4","2017:04:26 18:15:00")
Kết luận
Tất cả các đoạn mã đã được trình bày ở trên. Nếu bạn muốn có phiên bản hoàn chỉnh hoặc cần hỗ trợ triển khai, hãy bình luận dưới bài viết này, tôi sẽ sẵn sàng gửi code và hỗ trợ bạn. Chúc bạn thành công trong những dự án sáng tạo của mình!