Spaces:
Paused
Paused
| import os | |
| from moviepy.editor import (VideoFileClip, ImageClip, CompositeVideoClip, AudioFileClip, concatenate_videoclips) | |
| import ImportantVariables | |
| from ImportantVariables import PATHS, check_paths_exist | |
| from moviepy.editor import ColorClip | |
| # Add background image behind the video | |
| def add_bg_image_on_video(video_clip, image_clip, target_width=1920, target_height=1080): | |
| print("add_bg_image_on_video") | |
| final_clip = CompositeVideoClip([image_clip, video_clip.set_position(("center", "center"))]) | |
| return final_clip | |
| def find_width_of_x(width,height): | |
| x=int((width-height*(9/16))/2) | |
| return x | |
| # Add an image (logo/banner/subscribe button) on top of a video | |
| def add_image_to_video(shorts_video_clip, image_clip, width_of_image, height_of_image=0, position=(0, 0)): | |
| print("add_image_to_video") | |
| if height_of_image == 0: | |
| image_clip = image_clip.resize(width=width_of_image) | |
| else: | |
| image_clip = image_clip.resize(width=width_of_image, height=height_of_image) | |
| final_clip = CompositeVideoClip([shorts_video_clip, image_clip.set_position(position)]) | |
| return final_clip | |
| # Add logo to the video | |
| def add_logo_to_video(final_shorts_video_clip, logo_image_clip, bg_image_clip_width, shorts_video_clip_width): | |
| print("add_logo_to_video") | |
| width_of_image = (bg_image_clip_width - shorts_video_clip_width) / 2 | |
| height_of_image = 0 | |
| x = 0 | |
| y = "center" | |
| position = (x, y) | |
| if width_of_image >= (final_shorts_video_clip.h // 4): | |
| final_clip = add_image_to_video(final_shorts_video_clip, logo_image_clip, width_of_image, height_of_image, | |
| position) | |
| return final_clip | |
| else: | |
| return final_shorts_video_clip | |
| # Add banner to the video | |
| def add_banner_to_video(final_shorts_video_clip, banner_image_clip): | |
| print("add_banner_to_video") | |
| w,h =final_shorts_video_clip.size | |
| print(w,h) | |
| width_of_image=find_width_of_x(w,h) | |
| print("width_of_image",width_of_image) | |
| height_of_image = 0 | |
| x = "right" | |
| y = "top" | |
| position = (x, y) | |
| final_clip = add_image_to_video(final_shorts_video_clip, banner_image_clip, width_of_image, height_of_image, | |
| position) | |
| return final_clip | |
| # Add subscribe button to the video | |
| def add_subscribe_png(final_shorts_video_clip, subscribe_image_clip, bg_image_clip_width, shorts_video_clip_width): | |
| print("add_subscribe_png") | |
| width_of_image = (bg_image_clip_width - shorts_video_clip_width) / 2 | |
| height_of_image = 0 | |
| x = "right" | |
| y = "center" | |
| position = (x, y) | |
| if width_of_image >= (final_shorts_video_clip.h // 4): | |
| final_clip = add_image_to_video(final_shorts_video_clip, subscribe_image_clip, width_of_image, height_of_image, | |
| position) | |
| return final_clip | |
| else: | |
| return final_shorts_video_clip | |
| def add_like_share_subscribe_animation(final_shorts_video_clip, animation_clip_path): | |
| try: | |
| print("add_like_share_subscribe_animation") | |
| # Load the animation clip | |
| animation_clip = VideoFileClip(animation_clip_path) | |
| # Repeat the animation clip every 10 seconds | |
| main_video_duration = final_shorts_video_clip.duration | |
| repeated_clips = [] | |
| start_time = 0 | |
| while start_time < main_video_duration: | |
| clip = animation_clip.set_start(start_time).set_duration( | |
| min(animation_clip.duration, main_video_duration - start_time)) | |
| repeated_clips.append(clip) | |
| start_time += 10 # Add animation every 10 seconds | |
| # Combine all repeated animations | |
| animation_sequence = concatenate_videoclips(repeated_clips) | |
| w,h=final_shorts_video_clip.size | |
| # Resize the animation clip if necessary | |
| animation_sequence = animation_sequence.resize(height=h/5.1) # Example: Resize to a height of 100px | |
| position = ("center", "bottom") # Position: Centered horizontally, bottom vertically | |
| # Overlay the animation onto the main video | |
| final_clip = CompositeVideoClip([final_shorts_video_clip, animation_sequence.set_position(position)]) | |
| return final_clip | |
| except Exception as e: | |
| print(f"Error adding animation: {e}") | |
| return final_shorts_video_clip | |
| # Main function to process a single video | |
| def add_main_features(shorts_video_path): | |
| global shorts_video_clip | |
| dimensions = get_video_dimensions(shorts_video_path) | |
| if dimensions: | |
| width, height = dimensions | |
| if is_16_9(width, height): | |
| print(f"β Video is 16:9. Cropping to 9:16...") | |
| shorts_video_clip = crop_to_9_16(shorts_video_path) | |
| else: | |
| print(f"β Video is not 16:9, no cropping needed.") | |
| shorts_video_clip = VideoFileClip(shorts_video_path) | |
| print(f"β Video Clip Loaded: {shorts_video_clip}") | |
| max_duration = 0.5 | |
| # clip_duration = min(max_duration, shorts_video_clip.duration) | |
| # shorts_video_clip = shorts_video_clip.subclip(0, clip_duration) | |
| bg_image_clip = ImageClip(PATHS["background"]).set_duration(shorts_video_clip.duration) | |
| banner_image_clip = ImageClip(PATHS["banner"]).set_duration(shorts_video_clip.duration) | |
| logo_image_clip = ImageClip(PATHS["logo"]).set_duration(shorts_video_clip.duration) | |
| subscribe_png_clip = ImageClip(PATHS["subscribe"]).set_duration(shorts_video_clip.duration) | |
| print("subscribe_png_clip",subscribe_png_clip) | |
| print("π bg_image_clip before resize:", bg_image_clip) | |
| print(f"π Background image size: {bg_image_clip.size}") | |
| bg_image_clip = ColorClip(size=(1280, 720), color=(255, 0, 0)) # Red background | |
| bg_image_clip = bg_image_clip.set_duration(shorts_video_clip.duration) | |
| print("β Test background created") | |
| print("β bg_image_clip resized successfully!") # If this doesn't print, script is freezing here | |
| print("π bg_image_clip after resize:", bg_image_clip) | |
| bg_image_clip_width = bg_image_clip.w | |
| shorts_video_clip_width = shorts_video_clip.w | |
| print("shorts_video_clip_width",shorts_video_clip_width) | |
| # Add background image | |
| final_shorts_video_clip = add_bg_image_on_video(shorts_video_clip, bg_image_clip) | |
| # Add logo | |
| final_shorts_video_clip = add_logo_to_video(final_shorts_video_clip, logo_image_clip, bg_image_clip_width,shorts_video_clip_width) | |
| # Add banner | |
| final_shorts_video_clip = add_banner_to_video(final_shorts_video_clip, banner_image_clip) | |
| # Add subscribe png | |
| final_shorts_video_clip = add_subscribe_png(final_shorts_video_clip, subscribe_png_clip, bg_image_clip_width,shorts_video_clip_width) | |
| return final_shorts_video_clip | |
| # Concatenate multiple videos | |
| def concatenate_videos(video_directory): | |
| video_clips = [] | |
| target_width = 1920 | |
| target_height = 1080 | |
| for filename in os.listdir(video_directory): | |
| if filename.endswith(('.mp4', '.avi', '.mov')): | |
| video_path = os.path.join(video_directory, filename) | |
| print(f"Processing: {video_path}") | |
| try: | |
| video_clip = add_main_features(video_path) | |
| if video_clip and video_clip.duration > 0: | |
| video_clip = video_clip.without_audio() | |
| video_clip = video_clip.resize(width=target_width, height=target_height) | |
| video_clip = video_clip.set_fps(30) | |
| video_clips.append(video_clip) | |
| else: | |
| print(f"Skipping invalid clip: {video_path}") | |
| except Exception as e: | |
| print(f"Error processing {video_path}: {e}") | |
| if video_clips: | |
| print(f"Concatenating {len(video_clips)} video clips...") | |
| final_clip = concatenate_videoclips(video_clips, method="compose") | |
| return final_clip | |
| else: | |
| print("No valid video files found in the directory.") | |
| return None | |
| # Add audio to concatenated video | |
| def concatenate_videos_with_audio(video_directory, audio_file): | |
| audio_clip = AudioFileClip(audio_file) | |
| video_clip = concatenate_videos(video_directory) | |
| animation_clip_path = PATHS["animation"] | |
| video_clip = add_like_share_subscribe_animation(video_clip, animation_clip_path) | |
| if video_clip is None: | |
| raise ValueError("No valid video clips to concatenate.") | |
| if audio_clip.duration < video_clip.duration: | |
| audio_clip = audio_clip.set_duration(video_clip.duration) | |
| elif video_clip.duration < audio_clip.duration: | |
| audio_clip = audio_clip.set_duration(video_clip.duration) | |
| # video_clip = video_clip.set_audio(audio_clip) | |
| return video_clip | |
| # Main function | |
| def main(): | |
| video_directory = PATHS["input_videos"] | |
| audio_file = PATHS["audio"] | |
| final_clip = concatenate_videos_with_audio(video_directory, audio_file) | |
| final_clip.write_videofile(PATHS["output_video"], codec="libx264", audio_codec="aac") | |
| print("Video created successfully!") | |
| def main_for_one_vedio(input_video_path,output_vedio_path): | |
| missing_paths = check_paths_exist(PATHS) | |
| print(missing_paths) | |
| animation_clip_path = PATHS["animation"] | |
| print(animation_clip_path) | |
| final_clip = add_main_features(input_video_path) | |
| print("hello") | |
| # final_clip = add_like_share_subscribe_animation(final_clip, animation_clip_path) | |
| final_clip.write_videofile(output_vedio_path, codec="libx264", audio_codec="aac") | |
| print("Video created successfully!") | |
| def get_video_dimensions(video_path): | |
| clip = VideoFileClip(video_path) | |
| width, height = clip.size # Get (width, height) | |
| clip.close() | |
| print(width, height) | |
| return width, height | |
| def is_16_9(width, height): | |
| aspect_ratio = width / height | |
| print(aspect_ratio) | |
| return abs(aspect_ratio - (16 / 9)) < 0.01 | |
| def crop_to_9_16(video_path): | |
| clip = VideoFileClip(video_path) | |
| width, height = clip.size | |
| new_width = int(height * 9 / 16) # Calculate new width for 9:16 | |
| crop_x = (width - new_width) // 2 # Crop equally from left & right | |
| cropped_clip = clip.crop(x1=crop_x, x2=crop_x + new_width) | |
| return cropped_clip | |
| def main_for_many_vedios(input_folder_path,output_folder_path): | |
| print("hello") | |
| for filename in os.listdir(input_folder_path): | |
| if filename.endswith(".mp4"): | |
| input_video_path = os.path.join(input_folder_path, filename) | |
| name, _ = os.path.splitext(filename) | |
| output_video_path = os.path.join(output_folder_path, f"{filename}_process.mp4") | |
| main_for_one_vedio(input_video_path, output_video_path) | |
| print(f"Processed {filename}") | |
| def main_for_me(): | |
| input_video_folder_path = PATHS["input_folder_path"] | |
| output_video_folder_path=ImportantVariables.create_output_videos_folder() | |
| main_for_many_vedios(input_video_folder_path,output_video_folder_path) | |
| if __name__ == "__main__": | |
| main_for_me() | |