Spaces:
Runtime error
Runtime error
File size: 6,415 Bytes
cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 9106952 cc4f6e6 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 |
from fastapi import FastAPI
import gradio as gr
from PIL import Image
import numpy as np
import torch
from transformers import pipeline
import cv2 # cv2๋ ์ด๋ฏธ์ง ๋ก๋/์ ์ฅ/์ ์ฒ๋ฆฌ ๋ฑ์ ์ฌ์ฉ๋ ์ ์์ง๋ง, ํ์ฌ ์ฝ๋์์๋ PIL๋ง์ผ๋ก๋ ์ถฉ๋ถํฉ๋๋ค.
app = FastAPI()
# ๋ฅ๋ฌ๋ ๋ชจ๋ธ ๋ก๋ (Depth Anything)
# ๋ชจ๋ธ ๋ก๋ฉ์ ์ฑ ์์ ์ ํ ๋ฒ๋ง ํ๋๋ก ๊ธ๋ก๋ฒ ๋ณ์๋ก ์ค์
print("Loading Depth Anything model...")
try:
# ๐๐๐ ๋ชจ๋ธ ์ด๋ฆ ์์ : ์ ํํ Depth Anything v2 Large ๋ชจ๋ธ ID ๐๐๐
# ๋ ์์ ๋ชจ๋ธ์ ์ํ์๋ฉด "LiangNX/depth-anything-v2-base-nyu" ๋ก ๋ณ๊ฒฝํ์ธ์.
depth_estimator = pipeline(task="depth-estimation", model="LiangNX/depth-anything-v2-large-nyu", device="cpu") # GPU ์ฌ์ฉ ์ device="cuda"
print("Depth Anything model loaded successfully.")
except Exception as e:
print(f"Error loading Depth Anything model: {e}")
depth_estimator = None # ๋ชจ๋ธ ๋ก๋ ์คํจ ์ None์ผ๋ก ์ค์
def process_image_for_depth(image_path_or_pil_image):
"""
๋จ์ผ ์ด๋ฏธ์ง์์ ๋์ค ๋งต์ ์ถ์ถํ๋ ํจ์.
"""
if depth_estimator is None:
return None, "Error: Depth Anything model not loaded. Check server logs."
# Gradio๋ PIL Image ๊ฐ์ฒด๋ก ์ด๋ฏธ์ง๋ฅผ ์ ๋ฌํฉ๋๋ค.
if isinstance(image_path_or_pil_image, str):
# ํ์ผ ๊ฒฝ๋ก๋ก ์ด๋ฏธ์ง๊ฐ ์ ๋ฌ๋ ๊ฒฝ์ฐ (์: Gradio์ `filepath` ํ์
)
image = Image.open(image_path_or_pil_image).convert("RGB")
else:
# PIL Image ๊ฐ์ฒด๊ฐ ์ง์ ์ ๋ฌ๋ ๊ฒฝ์ฐ
image = image_path_or_pil_image.convert("RGB")
try:
# Depth Anything ๋ชจ๋ธ ์ถ๋ก
# result๋ ๋์
๋๋ฆฌ๋ก, 'depth' (PIL Image)์ 'depth_npy' (numpy array)๋ฅผ ํฌํจํฉ๋๋ค.
result = depth_estimator(image)
# ๋์ค ๋งต (PIL Image) - ์ด PIL ์ด๋ฏธ์ง๋ ์ด๋ฏธ ์๊ฐํํ๊ธฐ ์ข์ ํํ๋ก ๋์ด ์์ต๋๋ค.
depth_image_pil = result["depth"]
# ๋์ค ๋งต (Numpy Array) - ํ์ํ๋ค๋ฉด ์ถ๊ฐ ์ฒ๋ฆฌ (์: ์ ๊ทํ, ๋ค๋ฅธ ํ์์ผ๋ก ๋ณํ)
# ํ์ฌ๋ ํ๋ฐฑ ์ด๋ฏธ์ง๋ก ๋ฐ๋ก ์ฌ์ฉํด๋ ์ถฉ๋ถํ๋ฏ๋ก, ์๋ ์ฝ๋๋ ์ ํ ์ฌํญ์
๋๋ค.
# depth_np = result["depth_npy"]
# normalized_depth_np = (depth_np - depth_np.min()) / (depth_np.max() - depth_np.min()) * 255
# normalized_depth_np = normalized_depth_np.astype(np.uint8)
# depth_grayscale_pil = Image.fromarray(normalized_depth_np)
return depth_image_pil, None # ๋์ค ๋งต PIL Image ๋ฐํ
except Exception as e:
import traceback
traceback.print_exc() # ์๋ฌ ๋ฐ์ ์ ์์ธ ํธ๋ ์ด์ค๋ฐฑ ์ถ๋ ฅ
return None, f"Error processing image for depth: {e}"
# Gradio ์ธํฐํ์ด์ค ์ ์
with gr.Blocks() as demo:
gr.Markdown("# ๐งโ๐ป ์ผ๊ตด ๋์ค ๋งต ์ถ์ถ๊ธฐ")
gr.Markdown("์ฌ๋ฌ ์ฅ์ ์ผ๊ตด ์ฌ์ง์ ์
๋ก๋ํ๋ฉด ๊ฐ ์ฌ์ง์์ ๋ฅ๋ฌ๋์ ํตํด ๋์ค ๋งต(๊น์ด ์ ๋ณด)์ ์ถ์ถํฉ๋๋ค.")
gr.Markdown("โ ๏ธ **์ฐธ๊ณ :** ๋ฌด๋ฃ CPU ํ๊ฒฝ์์๋ ๋ชจ๋ธ ๋ก๋ฉ ๋ฐ ์ด๋ฏธ์ง ์ฒ๋ฆฌ ์๊ฐ์ด ๋งค์ฐ ์ค๋ ๊ฑธ๋ฆด ์ ์์ต๋๋ค.")
with gr.Row():
# file_count="multiple"๋ก ์ฌ๋ฌ ํ์ผ ์
๋ก๋ ๊ฐ๋ฅํ๊ฒ ์ค์
# type="filepath"๋ก ์ค์ ํ์ฌ Gradio๊ฐ ํ์ผ์ ์์ ๊ฒฝ๋ก์ ์ ์ฅํ๋๋ก ํจ
input_images = gr.File(label="์ผ๊ตด ์ฌ์ง ์
๋ก๋ (์ต๋ 10์ฅ ๊ถ์ฅ)", file_count="multiple", type="filepath")
output_gallery = gr.Gallery(label="์๋ณธ ์ด๋ฏธ์ง ๋ฐ ๋์ค ๋งต", columns=[2], rows=[1], object_fit="contain", height="auto")
process_button = gr.Button("๋์ค ๋งต ์ถ์ถ ์์")
def process_all_images(image_paths):
"""
์
๋ก๋๋ ๋ชจ๋ ์ด๋ฏธ์ง์ ๋ํด ๋์ค ๋งต ์ถ์ถ์ ์ํํ๊ณ ๊ฒฐ๊ณผ๋ฅผ ๋ฐํํ๋ ํจ์.
"""
if not image_paths:
return [(None, "์ด๋ฏธ์ง๋ฅผ ์
๋ก๋ํด์ฃผ์ธ์.")]
results_for_gallery = [] # Gradio Gallery์ ํ์ํ (PIL Image, Label) ํํ ๋ฆฌ์คํธ
for i, path in enumerate(image_paths):
try:
original_image = Image.open(path).convert("RGB")
depth_map_pil, error = process_image_for_depth(original_image)
# ์๋ณธ ์ด๋ฏธ์ง๋ฅผ ๋จผ์ ์ถ๊ฐ
results_for_gallery.append((original_image, f"์๋ณธ ์ด๋ฏธ์ง {i+1}"))
if error:
print(f"Error processing image {i+1}: {error}")
# ์ค๋ฅ๊ฐ ๋ฐ์ํ ๊ฒฝ์ฐ ๋์ค ๋งต ๋์ ์ค๋ฅ ๋ฉ์์ง ํ์
# ์ด ๋ถ๋ถ์ Gradio Gallery๊ฐ (Image, Label)์ ๊ธฐ๋ํ๋ฏ๋ก,
# ์ค๋ฅ ๋ฉ์์ง๋ฅผ ํ
์คํธ ์ด๋ฏธ์ง๋ก ๋ง๋ค๊ฑฐ๋, ์ค๋ฅ ์ด๋ฏธ์ง๋ฅผ ์ฌ์ฉํ ์ ์์ต๋๋ค.
# ์ฌ๊ธฐ์๋ ๊ฐ๋จํ ๋น ์ด๋ฏธ์ง์ ํจ๊ป ์ค๋ฅ ๋ฉ์์ง๋ฅผ ํ์ํ๋๋ก ํฉ๋๋ค.
dummy_error_image = Image.new('RGB', original_image.size, color = 'red')
results_for_gallery.append((dummy_error_image, f"์ค๋ฅ ๋ฐ์: {error}"))
else:
results_for_gallery.append((depth_map_pil, f"๋์ค ๋งต {i+1}"))
except Exception as e:
# ํ์ผ ์์ฒด๋ฅผ ์ฌ๋ ๋ฐ ๋ฌธ์ ๊ฐ ๋ฐ์ํ ๊ฒฝ์ฐ
print(f"Failed to open or process file {path}: {e}")
dummy_error_image = Image.new('RGB', (200, 200), color = 'red') # ์์ ์๋ฌ ์ด๋ฏธ์ง
results_for_gallery.append((dummy_error_image, f"ํ์ผ ์ฒ๋ฆฌ ์ค๋ฅ: {e}"))
return results_for_gallery
# ๋ฒํผ ํด๋ฆญ ์ ํจ์ ์ฐ๊ฒฐ
process_button.click(
fn=process_all_images,
inputs=input_images,
outputs=output_gallery
)
# Gradio ์ฑ์ FastAPI์ ๋ง์ดํธ
# ๊ธฐ๋ณธ ๊ฒฝ๋ก (path="/")์ Gradio ์ฑ์ ๋ง์ดํธํ์ฌ ์น ํ์ด์ง ์ ์ ์ ๋ฐ๋ก UI๊ฐ ๋ณด์ด๋๋ก ํฉ๋๋ค.
app = gr.mount_gradio_app(app, demo, path="/")
# FastAPI ๊ธฐ๋ณธ ์๋ํฌ์ธํธ (์ ํ ์ฌํญ, Gradio ์ฑ์ด ๊ธฐ๋ณธ ๊ฒฝ๋ก๋ฅผ ์ ์ ํจ)
# ์ด ์๋ํฌ์ธํธ๋ /api ๊ฒฝ๋ก๋ก ์ ์ํ์ ๋๋ง ์๋ํฉ๋๋ค.
@app.get("/api")
def read_root():
return {"message": "Welcome to the Face Depth Map Extractor! Visit / for the UI."} |