Spaces:
Sleeping
Sleeping
Update app.py
Browse files
app.py
CHANGED
@@ -5,6 +5,7 @@ import nltk
|
|
5 |
from nltk.tokenize import sent_tokenize
|
6 |
from PIL import Image
|
7 |
from io import BytesIO
|
|
|
8 |
|
9 |
# Ensure NLTK's Punkt tokenizer models are downloaded
|
10 |
nltk.download('punkt')
|
@@ -17,51 +18,70 @@ if not HUGGINGFACE_API_KEY:
|
|
17 |
|
18 |
# Define the Hugging Face Inference API URL for a text-to-image model
|
19 |
# You can choose a different model if preferred
|
20 |
-
|
|
|
21 |
|
22 |
headers = {
|
23 |
"Authorization": f"Bearer {HUGGINGFACE_API_KEY}"
|
24 |
}
|
25 |
|
26 |
-
def query(
|
27 |
"""
|
28 |
-
Sends a POST request to the Hugging Face Inference API with the given
|
|
|
29 |
"""
|
|
|
|
|
|
|
|
|
|
|
30 |
response = requests.post(API_URL, headers=headers, json=payload)
|
|
|
31 |
if response.status_code == 200:
|
32 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
33 |
else:
|
34 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
35 |
|
36 |
def generate_comic(story):
|
37 |
"""
|
38 |
Takes a short story, splits it into sentences, generates an image for each sentence,
|
39 |
-
and returns a list of
|
40 |
"""
|
41 |
# Split the story into sentences
|
42 |
sentences = sent_tokenize(story)
|
43 |
-
|
44 |
images = []
|
45 |
for idx, sentence in enumerate(sentences):
|
46 |
try:
|
47 |
print(f"Generating image for sentence {idx+1}/{len(sentences)}: {sentence}")
|
48 |
-
#
|
49 |
-
|
50 |
-
"inputs": sentence,
|
51 |
-
"options": {
|
52 |
-
"use_cache": False
|
53 |
-
}
|
54 |
-
}
|
55 |
-
# Query the API
|
56 |
-
image_bytes = query(payload)
|
57 |
# Open the image
|
58 |
image = Image.open(BytesIO(image_bytes)).convert("RGB")
|
59 |
images.append(image)
|
60 |
except Exception as e:
|
61 |
print(f"Error generating image for sentence '{sentence}': {e}")
|
62 |
-
#
|
63 |
-
|
64 |
-
|
|
|
|
|
|
|
65 |
return images
|
66 |
|
67 |
def create_comic_panel(images):
|
@@ -71,25 +91,25 @@ def create_comic_panel(images):
|
|
71 |
"""
|
72 |
# Filter out any None images
|
73 |
images = [img for img in images if img is not None]
|
74 |
-
|
75 |
if not images:
|
76 |
return None
|
77 |
-
|
78 |
# Define the size for each panel
|
79 |
panel_width, panel_height = 512, 512 # You can adjust as needed
|
80 |
-
|
81 |
# Resize images to uniform size
|
82 |
resized_images = [img.resize((panel_width, panel_height)) for img in images]
|
83 |
-
|
84 |
# Create a new blank image with enough width to hold all panels
|
85 |
total_width = panel_width * len(resized_images)
|
86 |
max_height = panel_height
|
87 |
comic_image = Image.new('RGB', (total_width, max_height), color=(255, 255, 255))
|
88 |
-
|
89 |
# Paste each panel image side by side
|
90 |
for i, img in enumerate(resized_images):
|
91 |
comic_image.paste(img, (i * panel_width, 0))
|
92 |
-
|
93 |
return comic_image
|
94 |
|
95 |
def process_story(story):
|
|
|
5 |
from nltk.tokenize import sent_tokenize
|
6 |
from PIL import Image
|
7 |
from io import BytesIO
|
8 |
+
import base64
|
9 |
|
10 |
# Ensure NLTK's Punkt tokenizer models are downloaded
|
11 |
nltk.download('punkt')
|
|
|
18 |
|
19 |
# Define the Hugging Face Inference API URL for a text-to-image model
|
20 |
# You can choose a different model if preferred
|
21 |
+
MODEL_NAME = "stabilityai/stable-diffusion-2-1" # Ensure this model is available for your API key
|
22 |
+
API_URL = f"https://api-inference.huggingface.co/models/{MODEL_NAME}"
|
23 |
|
24 |
headers = {
|
25 |
"Authorization": f"Bearer {HUGGINGFACE_API_KEY}"
|
26 |
}
|
27 |
|
28 |
+
def query(prompt):
|
29 |
"""
|
30 |
+
Sends a POST request to the Hugging Face Inference API with the given prompt.
|
31 |
+
Returns the image bytes if successful.
|
32 |
"""
|
33 |
+
payload = {
|
34 |
+
"inputs": prompt,
|
35 |
+
# You can add additional parameters here if needed, such as "parameters": {"num_inference_steps": 50}
|
36 |
+
}
|
37 |
+
|
38 |
response = requests.post(API_URL, headers=headers, json=payload)
|
39 |
+
|
40 |
if response.status_code == 200:
|
41 |
+
# The response is a list of base64-encoded images
|
42 |
+
response_json = response.json()
|
43 |
+
if isinstance(response_json, list) and len(response_json) > 0:
|
44 |
+
image_data = response_json[0] # Get the first image
|
45 |
+
# The image data is a data URI: "data:image/png;base64,..."
|
46 |
+
header, encoded = image_data.split(",", 1)
|
47 |
+
image_bytes = base64.b64decode(encoded)
|
48 |
+
return image_bytes
|
49 |
+
else:
|
50 |
+
raise ValueError("Unexpected response format from Hugging Face API.")
|
51 |
else:
|
52 |
+
# Attempt to parse error message from response
|
53 |
+
try:
|
54 |
+
error_info = response.json()
|
55 |
+
error_message = error_info.get('error', 'No error message provided.')
|
56 |
+
except ValueError:
|
57 |
+
error_message = response.text
|
58 |
+
raise Exception(f"Request failed with status code {response.status_code}: {error_message}")
|
59 |
|
60 |
def generate_comic(story):
|
61 |
"""
|
62 |
Takes a short story, splits it into sentences, generates an image for each sentence,
|
63 |
+
and returns a list of PIL Image objects.
|
64 |
"""
|
65 |
# Split the story into sentences
|
66 |
sentences = sent_tokenize(story)
|
67 |
+
|
68 |
images = []
|
69 |
for idx, sentence in enumerate(sentences):
|
70 |
try:
|
71 |
print(f"Generating image for sentence {idx+1}/{len(sentences)}: {sentence}")
|
72 |
+
# Query the Hugging Face API
|
73 |
+
image_bytes = query(sentence)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
74 |
# Open the image
|
75 |
image = Image.open(BytesIO(image_bytes)).convert("RGB")
|
76 |
images.append(image)
|
77 |
except Exception as e:
|
78 |
print(f"Error generating image for sentence '{sentence}': {e}")
|
79 |
+
# Append a placeholder image with error text
|
80 |
+
placeholder = Image.new('RGB', (512, 512), color=(255, 0, 0))
|
81 |
+
draw = Image.Draw.Draw(placeholder)
|
82 |
+
draw.text((10, 10), "Error generating image", fill=(255, 255, 255))
|
83 |
+
images.append(placeholder)
|
84 |
+
|
85 |
return images
|
86 |
|
87 |
def create_comic_panel(images):
|
|
|
91 |
"""
|
92 |
# Filter out any None images
|
93 |
images = [img for img in images if img is not None]
|
94 |
+
|
95 |
if not images:
|
96 |
return None
|
97 |
+
|
98 |
# Define the size for each panel
|
99 |
panel_width, panel_height = 512, 512 # You can adjust as needed
|
100 |
+
|
101 |
# Resize images to uniform size
|
102 |
resized_images = [img.resize((panel_width, panel_height)) for img in images]
|
103 |
+
|
104 |
# Create a new blank image with enough width to hold all panels
|
105 |
total_width = panel_width * len(resized_images)
|
106 |
max_height = panel_height
|
107 |
comic_image = Image.new('RGB', (total_width, max_height), color=(255, 255, 255))
|
108 |
+
|
109 |
# Paste each panel image side by side
|
110 |
for i, img in enumerate(resized_images):
|
111 |
comic_image.paste(img, (i * panel_width, 0))
|
112 |
+
|
113 |
return comic_image
|
114 |
|
115 |
def process_story(story):
|