initial +
Browse files- gradio_app_v2.py +299 -0
- instruction_assets/design_styles.png +0 -0
- instruction_assets/room_types.png +0 -0
- perfect_redesign/__pycache__/main.cpython-312.pyc +0 -0
- perfect_redesign/__pycache__/render_ai.cpython-312.pyc +0 -0
- perfect_redesign/__pycache__/render_app.cpython-312.pyc +0 -0
- perfect_redesign/main.py +82 -0
- perfect_redesign/render_ai.py +89 -0
- perfect_redesign/render_app.py +115 -0
- requirements.txt +5 -0
- sketch_design/__pycache__/main.cpython-312.pyc +0 -0
- sketch_design/__pycache__/render_ai.cpython-312.pyc +0 -0
- sketch_design/__pycache__/render_app.cpython-312.pyc +0 -0
- sketch_design/__pycache__/sk_render_ai.cpython-312.pyc +0 -0
- sketch_design/main.py +127 -0
- sketch_design/render_app.py +129 -0
- sketch_design/sk_render_ai.py +89 -0
gradio_app_v2.py
ADDED
@@ -0,0 +1,299 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
import gradio as gr
|
2 |
+
from perfect_redesign.main import flow as perfect_redesign_flow
|
3 |
+
from sketch_design.main import flow as sketch_to_render_flow
|
4 |
+
import random
|
5 |
+
import os
|
6 |
+
|
7 |
+
def get_image_path():
|
8 |
+
return os.path.join(os.getcwd(), "instruction_assets/design_styles.png")
|
9 |
+
|
10 |
+
with gr.Blocks(theme='JohnSmith9982/small_and_pretty') as demo:
|
11 |
+
# with gr.Blocks() as demo:
|
12 |
+
gr.HTML(
|
13 |
+
"""
|
14 |
+
<h1 style="font-size: 3.5em; text-align: center; color: #02c160; font-weight: bold;">Architecture Render Bot</h1>
|
15 |
+
"""
|
16 |
+
)
|
17 |
+
|
18 |
+
with gr.Tabs():
|
19 |
+
|
20 |
+
|
21 |
+
with gr.Tab("Design Process"):
|
22 |
+
|
23 |
+
with gr.Tabs():
|
24 |
+
|
25 |
+
with gr.Tab("Perfect Redesign (Interior)"):
|
26 |
+
with gr.Row():
|
27 |
+
with gr.Column():
|
28 |
+
with gr.Row(scale=1):
|
29 |
+
image_upload_pr = gr.Image(label="Upload an Image", type="filepath")
|
30 |
+
|
31 |
+
# Input for user prompt and button to start the design process
|
32 |
+
|
33 |
+
with gr.Column():
|
34 |
+
# with gr.Column(scale=1, min_width=30):
|
35 |
+
design_output_pr = gr.Image(label="Design Output")
|
36 |
+
|
37 |
+
with gr.Row():
|
38 |
+
# with gr.Column(scale=1, min_width=30):
|
39 |
+
user_prompt_input_pr = gr.Textbox(label="Enter your Prompt", placeholder="A bedroom in a scandanavian style.")
|
40 |
+
# Output for the design process
|
41 |
+
with gr.Row():
|
42 |
+
# with gr.Column(scale=1, min_width=30):
|
43 |
+
start_btn_pr = gr.Button("Start Design Process")
|
44 |
+
|
45 |
+
with gr.Tab("Sketch to Render (Interior)"):
|
46 |
+
with gr.Row():
|
47 |
+
with gr.Column():
|
48 |
+
with gr.Row(scale=1):
|
49 |
+
image_upload_sr = gr.Image(label="Upload an Image", type="filepath")
|
50 |
+
|
51 |
+
# Input for user prompt and button to start the design process
|
52 |
+
|
53 |
+
with gr.Column():
|
54 |
+
# with gr.Column(scale=1, min_width=30):
|
55 |
+
design_output_sr = gr.Image(label="Design Output")
|
56 |
+
|
57 |
+
with gr.Row():
|
58 |
+
|
59 |
+
with gr.Column():
|
60 |
+
|
61 |
+
ai_intervention_radio_sr = gr.Radio(label="AI Intervention", choices=["Very Low", "Low", "Mid", "Extreme"], info='Indicates the level of AI intervention in the design process. "Very Low" means minimal changes, while "Extreme" allows for significant alterations to the original design. (Required Parameter)')
|
62 |
+
with gr.Row():
|
63 |
+
# with gr.Column(scale=1, min_width=30):
|
64 |
+
user_prompt_input_sr = gr.Textbox(label="Enter your Prompt", placeholder="A bedroom in a scandanavian style.", info = "A natural language instruction which provides room type and design style. Check instructions for possible Room Types & Design Styles (Required Parameter)")
|
65 |
+
|
66 |
+
with gr.Row():
|
67 |
+
# with gr.Column(scale=1, min_width=30):
|
68 |
+
start_btn_sr = gr.Button("Start Design Process")
|
69 |
+
|
70 |
+
with gr.Tab("Sketch to Render (Exterior)"):
|
71 |
+
with gr.Row():
|
72 |
+
with gr.Column():
|
73 |
+
with gr.Row(scale=1):
|
74 |
+
image_upload_sr_ext = gr.Image(label="Upload an Image", type="filepath")
|
75 |
+
|
76 |
+
# Input for user prompt and button to start the design process
|
77 |
+
|
78 |
+
with gr.Column():
|
79 |
+
# with gr.Column(scale=1, min_width=30):
|
80 |
+
design_output_sr_ext = gr.Image(label="Design Output")
|
81 |
+
|
82 |
+
with gr.Row():
|
83 |
+
|
84 |
+
with gr.Column():
|
85 |
+
|
86 |
+
ai_intervention_radio_sr_ext = gr.Radio(label="AI Intervention", choices=["Very Low", "Low", "Mid", "Extreme"], info='Indicates the level of AI intervention in the design process. "Very Low" means minimal changes, while "Extreme" allows for significant alterations to the original design. (Required Parameter)')
|
87 |
+
|
88 |
+
with gr.Column():
|
89 |
+
|
90 |
+
house_angle_dp_sr_ext = gr.Dropdown(["Front of House", "Side of House", "Back of House"], label="House Angle", info="Indicates the angle of house for which the design is intended\n(Required Parameter)", interactive=True)
|
91 |
+
with gr.Row():
|
92 |
+
# with gr.Column(scale=1, min_width=30):
|
93 |
+
# user_prompt_input_sr_ext = gr.Textbox(label="Enter your Prompt", placeholder="A bedroom in a scandanavian style.", info = "A natural language instruction which provides room type and design style. (Required Parameter)")
|
94 |
+
# with gr.Column():
|
95 |
+
|
96 |
+
design_style_sr_ext = gr.Dropdown(["No Style", "Modern", "Mediterranean", "International", "Moody Colors", "Wood Accents", "Bohemian", "Industrial", "Retreat", "Elegant", "Painted Brick", "Red Brick", "Modern Blend", "Stone Clad", "Glass House", "Ranch", "Modern Farm House", "Portuguese", "Traditional", "Craftsman", "Tudor", "Prairie", "Chalet", "Colonial", "Dutch Colonial", "Georgian", "Green", "Contemporary", "Christmas", "Cottage", "Farmhouse", "French Country", "Futuristic", "Gothic", "Greek Revival", "Mansion", "Townhouse", "Victorian", "Corporate Building"], label="Design Style", info="Defines the overall aesthetic style you want to achieve. (Required Parameter)", interactive=True)
|
97 |
+
|
98 |
+
with gr.Row():
|
99 |
+
# with gr.Column(scale=1, min_width=30):
|
100 |
+
start_btn_sr_ext = gr.Button("Start Design Process")
|
101 |
+
|
102 |
+
with gr.Tab("Sketch to Render (Garden)"):
|
103 |
+
with gr.Row():
|
104 |
+
with gr.Column():
|
105 |
+
with gr.Row(scale=1):
|
106 |
+
image_upload_sr_garden = gr.Image(label="Upload an Image", type="filepath")
|
107 |
+
|
108 |
+
# Input for user prompt and button to start the design process
|
109 |
+
|
110 |
+
with gr.Column():
|
111 |
+
# with gr.Column(scale=1, min_width=30):
|
112 |
+
design_output_sr_garden = gr.Image(label="Design Output")
|
113 |
+
|
114 |
+
with gr.Row():
|
115 |
+
|
116 |
+
with gr.Column():
|
117 |
+
|
118 |
+
ai_intervention_radio_sr_garden = gr.Radio(label="AI Intervention", choices=["Very Low", "Low", "Mid", "Extreme"], info='Indicates the level of AI intervention in the design process. "Very Low" means minimal changes, while "Extreme" allows for significant alterations to the original design. (Required Parameter)')
|
119 |
+
|
120 |
+
with gr.Column():
|
121 |
+
|
122 |
+
garden_type_dp_sr_garden = gr.Dropdown(["Backyard", "Patio", "Terrace", "Front Yard", "Garden", "Courtyard", "Pool Area", "Porch", "Playground"], label="Garden Type", info="Indicates the type of garden for which the design is intended\n(Required Parameter)", interactive=True)
|
123 |
+
with gr.Row():
|
124 |
+
|
125 |
+
design_style_sr_garden = gr.Dropdown(["No Style", "Modern", "City", "Contemporary", "Luxury", "Apartment", "Small", "Vegetable", "Low Budget", "Beach", "Wedding", "Rural", "Mediterranean", "Restaurant", "Formal", "American", "English", "Traditional", "Meditation", "Coastal", "Tropical", "Christmas", "Japanese Zen", "Cottage", "Wildflower", "Desert", "Butterfly", "Herb", "Vertical", "Zen Rock", "Rooftop", "Perennial", "Water", "Shade", "Winter", "Zen Bamboo", "Sculpture"], label="Design Style", info="Defines the overall aesthetic style you want to achieve. (Required Parameter)", interactive=True)
|
126 |
+
|
127 |
+
with gr.Row():
|
128 |
+
# with gr.Column(scale=1, min_width=30):
|
129 |
+
start_btn_sr_garden = gr.Button("Start Design Process")
|
130 |
+
|
131 |
+
|
132 |
+
|
133 |
+
with gr.Tab("Instructions"):
|
134 |
+
gr.HTML(
|
135 |
+
f"""
|
136 |
+
|
137 |
+
<p style="text-align: center; font-weight: bold;">
|
138 |
+
Upload an image and a natural language prompt to generate a perfect redesign & Sketch to Render (Interior) of a room</p>
|
139 |
+
<p style="text-align: center; font-weight: bold;"> Example prompt: "A bedroom in a scandanavian style."</p>
|
140 |
+
|
141 |
+
<p style="text-align: center; font-weight: bold;"> For more information on design styles and room types, refer to the images below:</p>
|
142 |
+
<p style="text-align: center; padding-bottom: 60px; font-weight: bold;">
|
143 |
+
<span style="color: red;">Important:</span>
|
144 |
+
Please upload a .jpg image not less that 512x512 dimensions and clearly mention the room type and the desired design style in the prompt.</p>
|
145 |
+
|
146 |
+
"""
|
147 |
+
)
|
148 |
+
gr.Image("instruction_assets/design_styles.png", label="Design Styles")
|
149 |
+
gr.Image("instruction_assets/room_types.png", label="Room Types")
|
150 |
+
|
151 |
+
|
152 |
+
|
153 |
+
|
154 |
+
# Design process button functionality
|
155 |
+
def after_start_pr(user_prompt, image_path):
|
156 |
+
"""
|
157 |
+
Processes the user prompt and image path, then generates and saves the output image.
|
158 |
+
|
159 |
+
Args:
|
160 |
+
user_prompt (str): The prompt provided by the user to guide the image generation.
|
161 |
+
image_path (str): The path to the input image to be processed.
|
162 |
+
|
163 |
+
Returns:
|
164 |
+
response: The response from the flow function after processing the input.
|
165 |
+
"""
|
166 |
+
try:
|
167 |
+
output_path = "output_image.jpg" # Path to save the output image
|
168 |
+
response = perfect_redesign_flow(user_prompt, image_path, output_path)
|
169 |
+
print(response)
|
170 |
+
return response
|
171 |
+
|
172 |
+
except Exception as e:
|
173 |
+
# raise Exception(f"An error occurred in function after_start_pr: {e}")
|
174 |
+
return Exception(f"An error occurred in function after_start_pr: {e}")
|
175 |
+
|
176 |
+
start_btn_pr.click(after_start_pr, inputs=[user_prompt_input_pr, image_upload_pr], outputs=design_output_pr)
|
177 |
+
|
178 |
+
# Sketch to render button functionality
|
179 |
+
def after_start_sr(user_prompt, image_path, ai_intervention):
|
180 |
+
"""
|
181 |
+
Processes the user prompt and image path, then generates and saves the output image.
|
182 |
+
|
183 |
+
Args:
|
184 |
+
user_prompt (str): The prompt provided by the user to guide the image generation.
|
185 |
+
image_path (str): The path to the input image to be processed.
|
186 |
+
ai_intervention (str): The level of AI intervention in the design process.
|
187 |
+
|
188 |
+
Returns:
|
189 |
+
response: The response from the flow function after processing the input.
|
190 |
+
"""
|
191 |
+
try:
|
192 |
+
output_path = "output_image.jpg" # Path to save the output image
|
193 |
+
print("=====Gradio sr function=====")
|
194 |
+
# print("User Prompt: ", user_prompt, "Image Path: ", image_path, "AI Intervention: ", ai_intervention, "Output Path: ", output_path)
|
195 |
+
# as a dict
|
196 |
+
print({"User Prompt": user_prompt, "Image Path": image_path, "AI Intervention": ai_intervention, "Output Path": output_path})
|
197 |
+
print("=============================")
|
198 |
+
response = sketch_to_render_flow(user_prompt = user_prompt,
|
199 |
+
image_path = image_path,
|
200 |
+
output_path = output_path,
|
201 |
+
ai_intervention=ai_intervention,
|
202 |
+
design_type="Interior",
|
203 |
+
no_design=1,
|
204 |
+
house_angle=None,
|
205 |
+
garden_type=None)
|
206 |
+
|
207 |
+
print(response)
|
208 |
+
return response
|
209 |
+
|
210 |
+
except Exception as e:
|
211 |
+
# raise Exception(f"An error occurred in function after_start_sr: {e}")
|
212 |
+
return Exception(f"An error occurred in function after_start_sr: {e}")
|
213 |
+
|
214 |
+
start_btn_sr.click(after_start_sr, inputs=[user_prompt_input_sr, image_upload_sr, ai_intervention_radio_sr], outputs=design_output_sr)
|
215 |
+
|
216 |
+
|
217 |
+
# Sketch to render ext button functionality
|
218 |
+
def after_start_sr_ext(image_path, ai_intervention, house_angle, design_style):
|
219 |
+
"""
|
220 |
+
Processes the user prompt and image path, then generates and saves the output image.
|
221 |
+
|
222 |
+
Args:
|
223 |
+
user_prompt (str): The prompt provided by the user to guide the image generation.
|
224 |
+
image_path (str): The path to the input image to be processed.
|
225 |
+
ai_intervention (str): The level of AI intervention in the design process.
|
226 |
+
house_angle (str): The angle of the house for which the design is intended.
|
227 |
+
design_style (str): The design style to be applied to the output image.
|
228 |
+
|
229 |
+
Returns:
|
230 |
+
response: The response from the flow function after processing the input.
|
231 |
+
"""
|
232 |
+
try:
|
233 |
+
output_path = "output_image.jpg" # Path to save the output image
|
234 |
+
print("=====Gradio sr ext function=====")
|
235 |
+
# print("User Prompt: ", user_prompt, "Image Path: ", image_path, "AI Intervention: ", ai_intervention, "Output Path: ", output_path)
|
236 |
+
# as a dict
|
237 |
+
print({"Image Path": image_path, "AI Intervention": ai_intervention, "Output Path": output_path, "House Angle": house_angle, "Design Style": design_style})
|
238 |
+
print("=============================")
|
239 |
+
response = sketch_to_render_flow(
|
240 |
+
image_path = image_path,
|
241 |
+
output_path = output_path,
|
242 |
+
ai_intervention=ai_intervention,
|
243 |
+
design_type="Exterior",
|
244 |
+
no_design=1,
|
245 |
+
house_angle=house_angle,
|
246 |
+
# garden_type=None,
|
247 |
+
design_style=design_style)
|
248 |
+
|
249 |
+
print(response)
|
250 |
+
return response
|
251 |
+
|
252 |
+
except Exception as e:
|
253 |
+
# raise Exception(f"An error occurred in function after_start_sr: {e}")
|
254 |
+
return Exception(f"An error occurred in function after_start_sr: {e}")
|
255 |
+
|
256 |
+
start_btn_sr_ext.click(after_start_sr_ext, inputs=[image_upload_sr_ext, ai_intervention_radio_sr_ext, house_angle_dp_sr_ext, design_style_sr_ext], outputs=design_output_sr_ext)
|
257 |
+
|
258 |
+
|
259 |
+
def after_start_sr_garden(image_path, ai_intervention, garden_type, design_style):
|
260 |
+
"""
|
261 |
+
Processes the user prompt and image path, then generates and saves the output image.
|
262 |
+
|
263 |
+
Args:
|
264 |
+
user_prompt (str): The prompt provided by the user to guide the image generation.
|
265 |
+
image_path (str): The path to the input image to be processed.
|
266 |
+
ai_intervention (str): The level of AI intervention in the design process.
|
267 |
+
garden_type (str): The type of garden for which the design is intended.
|
268 |
+
design_style (str): The design style to be applied to the output image.
|
269 |
+
|
270 |
+
Returns:
|
271 |
+
response: The response from the flow function after processing the input.
|
272 |
+
"""
|
273 |
+
try:
|
274 |
+
output_path = "output_image.jpg" # Path to save the output image
|
275 |
+
print("=====Gradio sr garden function=====")
|
276 |
+
# print("User Prompt: ", user_prompt, "Image Path: ", image_path, "AI Intervention: ", ai_intervention, "Output Path: ", output_path)
|
277 |
+
# as a dict
|
278 |
+
print({"Image Path": image_path, "AI Intervention": ai_intervention, "Output Path": output_path, "Garden Type": garden_type, "Design Style": design_style})
|
279 |
+
print("=============================")
|
280 |
+
response = sketch_to_render_flow(
|
281 |
+
image_path = image_path,
|
282 |
+
output_path = output_path,
|
283 |
+
ai_intervention=ai_intervention,
|
284 |
+
design_type="Garden",
|
285 |
+
no_design=1,
|
286 |
+
house_angle=None,
|
287 |
+
garden_type=garden_type,
|
288 |
+
design_style=design_style)
|
289 |
+
|
290 |
+
print(response)
|
291 |
+
return response
|
292 |
+
|
293 |
+
except Exception as e:
|
294 |
+
# raise Exception(f"An error occurred in function after_start_sr: {e}")
|
295 |
+
return Exception(f"An error occurred in function after_start_sr: {e}")
|
296 |
+
|
297 |
+
start_btn_sr_garden.click(after_start_sr_garden, inputs=[image_upload_sr_garden, ai_intervention_radio_sr_garden, garden_type_dp_sr_garden, design_style_sr_garden], outputs=design_output_sr_garden)
|
298 |
+
|
299 |
+
demo.launch(share=True, pwa=True, debug=True)
|
instruction_assets/design_styles.png
ADDED
![]() |
instruction_assets/room_types.png
ADDED
![]() |
perfect_redesign/__pycache__/main.cpython-312.pyc
ADDED
Binary file (3.66 kB). View file
|
|
perfect_redesign/__pycache__/render_ai.cpython-312.pyc
ADDED
Binary file (6.83 kB). View file
|
|
perfect_redesign/__pycache__/render_app.cpython-312.pyc
ADDED
Binary file (5.04 kB). View file
|
|
perfect_redesign/main.py
ADDED
@@ -0,0 +1,82 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""
|
2 |
+
This script orchestrates the design process by utilizing the DesignAssistant and DesignProcess classes.
|
3 |
+
It extracts design parameters using the DesignAssistant and applies them using the DesignProcess.
|
4 |
+
"""
|
5 |
+
from .render_ai import DesignAssistant
|
6 |
+
from .render_app import DesignProcess
|
7 |
+
import requests
|
8 |
+
import time
|
9 |
+
|
10 |
+
|
11 |
+
|
12 |
+
def flow(user_prompt, image_path, output_path):
|
13 |
+
"""
|
14 |
+
Orchestrates the design process by extracting design parameters and applying them.
|
15 |
+
|
16 |
+
Args:
|
17 |
+
user_prompt (str): The prompt provided by the user to generate design parameters.
|
18 |
+
image_path (str): The path to the input image for the design process.
|
19 |
+
output_path (str): The path where the output image will be saved.
|
20 |
+
|
21 |
+
Returns:
|
22 |
+
str: The path to the saved output image if successful, or an error message if failed.
|
23 |
+
"""
|
24 |
+
try:
|
25 |
+
# Extract design parameters using render_ai.py
|
26 |
+
assistant = DesignAssistant()
|
27 |
+
thread = assistant.create_thread()
|
28 |
+
_user_prompt = f"The information can be in italian aswell, so choose the closest values from the above lists for the dict's values as the response will be always in english.\n{user_prompt}"
|
29 |
+
message = assistant.create_message(thread.id, _user_prompt)
|
30 |
+
run = assistant.run_and_poll(thread.id)
|
31 |
+
|
32 |
+
if run.status == 'completed':
|
33 |
+
messages = assistant.get_messages(thread.id)
|
34 |
+
design_info = eval(messages.data[0].content[0].text.value) # Assuming the response is a dict in string format
|
35 |
+
# Debugging information
|
36 |
+
print(design_info)
|
37 |
+
print(type(design_info))
|
38 |
+
print(design_info.keys())
|
39 |
+
print("---------------------------------------------")
|
40 |
+
else:
|
41 |
+
print("Failed to extract design information.")
|
42 |
+
return
|
43 |
+
|
44 |
+
# Use the extracted design parameters in render_app.py
|
45 |
+
design_process = DesignProcess(
|
46 |
+
image_path=image_path,
|
47 |
+
design_style=design_info['design_style'],
|
48 |
+
room_type=design_info['room_type']
|
49 |
+
)
|
50 |
+
response = design_process.start_process()
|
51 |
+
|
52 |
+
request_id = response['id']
|
53 |
+
print("_________!!!!!Perfect Redesign Request ID!!!!!_________")
|
54 |
+
print(request_id)
|
55 |
+
print(type(request_id))
|
56 |
+
|
57 |
+
while True:
|
58 |
+
status = design_process.check_status(request_id)
|
59 |
+
print(status) # Prints the status of the redesign request
|
60 |
+
# Wait for the process to complete or fail
|
61 |
+
|
62 |
+
# if status['status'] in ['succeeded', 'error']:
|
63 |
+
# break
|
64 |
+
if "status" not in status.keys():
|
65 |
+
break
|
66 |
+
|
67 |
+
time.sleep(7)
|
68 |
+
|
69 |
+
if "output_images" in status:
|
70 |
+
image_url = status['output_images'][0] # Assuming you want the first image
|
71 |
+
# Save the image to the specified output path
|
72 |
+
image_data = requests.get(image_url).content
|
73 |
+
with open(output_path, "wb") as f:
|
74 |
+
f.write(image_data)
|
75 |
+
print("Design process completed successfully. Image saved as new_design.jpg.")
|
76 |
+
return output_path
|
77 |
+
else:
|
78 |
+
print("Design process failed.")
|
79 |
+
return "Design process failed."
|
80 |
+
|
81 |
+
except Exception as e:
|
82 |
+
raise
|
perfect_redesign/render_ai.py
ADDED
@@ -0,0 +1,89 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""
|
2 |
+
This module provides the DesignAssistant class to interact with OpenAI's API
|
3 |
+
for creating and managing threads and messages related to design assistance.
|
4 |
+
"""
|
5 |
+
import os
|
6 |
+
from dotenv import load_dotenv
|
7 |
+
from openai import OpenAI
|
8 |
+
|
9 |
+
# Load environment variables from .env file
|
10 |
+
load_dotenv()
|
11 |
+
|
12 |
+
class DesignAssistant:
|
13 |
+
def __init__(self):
|
14 |
+
self.client = OpenAI(api_key=os.getenv("OPENAI_API_KEY"))
|
15 |
+
self.assistant = self.client.beta.assistants.create(
|
16 |
+
name="Extraction Assistant",
|
17 |
+
# instructions="You are a professional Bedroom renovator engine, you get an information and you respond with a dict each time with the following keys: 'design_style', 'room_type'. Respond with the dict only and no need to encapsulate between quotes.",
|
18 |
+
instructions= "You are a professional dictionary creator.\n\nFollowing are some important rules;\nYou get some information and you respond with a dict each time with the following keys: 'design_style', 'room_type' only and always. Respond with the dict only and no need to encapsulate between quotes.\n\nThe room_type and design_style has to be choosen from the following, incase of confusion choose the closest one;\nroom_types = [\"Living Room\", \"Bedroom\", \"Bathroom\", \"Kitchen\", \"Dining Room\", \"Attic\", \"Family Room\", \"Kids Room\", \"Study Room\", \"Home Office\", \"Meeting Room\", \"Coffee Shop\", \"Office\", \"Coworking Space\", \"Working Space\", \"Library\", \"Science Laboratory\", \"Photo Studio\", \"Exhibition Space\", \"Art Studio\", \"Multimedia Room\", \"Medical Exam Room\", \"Reception Area\", \"Formal Dining Room\", \"Home Theater\", \"Gaming Room\", \"Fitness Gym\", \"Restaurant\", \"Hotel Lobby\", \"Hotel Room\", \"Wine Cellar\", \"Home Spa\", \"Dressing Room\", \"Home Bar\", \"Music Room\", \"Workshop\", \"Craft Room\", \"Yoga Studio\", \"Auditorium\", \"Art Studio\", \"Balcony\", \"Rooftop Terrace\", \"Mudroom\", \"Guest Bedroom\", \"Wedding Room\", \"Outdoor Kitchen\", \"Utility Room\", \"Laundry Room\", \"Pet Room\", \"Walk-in Closet\", \"Lounge\", \"Reading Nook\", \"Foyer\", \"Open Kitchen Living Room\", \"Prayer Room\", \"Conservatory\", \"Playroom\", \"Man Cave\", \"She Shed\", \"Greenhouse\", \"Sauna\", \"Nursery\", \"Home Gym\"]\n\ndesign_styles = [\"No Style\", \"Eclectic\", \"Modern\", \"Contemporary\", \"Transitional\", \"Scandinavian\", \"Mediterranean\", \"Ikea\", \"Industrial\", \"Kids Room\", \"Shabby Chic\", \"Coastal\", \"Bauhaus\", \"Bohemian\", \"Traditional\", \"Rustic\", \"Minimalism\", \"Japandi\", \"Japanese Design\", \"Modern Arabic\", \"Traditional Arabic\", \"Bali\", \"Tropical\", \"Asian Decor\", \"Zen\", \"Hollywood Regency\", \"Hollywood Glam\", \"Minimalist\", \"Christmas\", \"Futuristic\", \"Luxurious\", \"Midcentury Modern\", \"Biophilic\", \"Cottage Core\", \"French Country\", \"Art Deco\", \"Art Nouveau\", \"South Western\", \"Modern Farm House\", \"Moroccan\", \"Gothic\", \"Victorian\", \"Steampunk\", \"Urban Modern\", \"Desert Modernism\", \"Colonial\", \"Brutalist\", \"Nordic Noir\", \"Postmodern\", \"Psychedelic\", \"Cosmic Chic\", \"Mexican Hacienda\", \"Coastal Modern\", \"Eco Friendly\", \"Pop Art\", \"Vintage Glam\", \"Candy Land\", \"Airbnb\", \"Glam Rock\", \"Barbie\", \"Doodle\", \"Sketch\", \"Maximalist\", \"Professional\", \"Halloween\", \"Retro\", \"Romantic\", \"Safari\", \"Tuscan\", \"Nautical\", \"Craftsman\", \"Farmhouse Chic\", \"Prairie\", \"Cubism\", \"Quiet Luxury\"]\n\nThe information can be in italian aswell, so choose the closest values from the above lists for the dict's values as the response will be always in english.",
|
19 |
+
tools=[],
|
20 |
+
model="gpt-4o",
|
21 |
+
)
|
22 |
+
|
23 |
+
def create_thread(self):
|
24 |
+
"""
|
25 |
+
Creates a new thread for communication.
|
26 |
+
|
27 |
+
Returns:
|
28 |
+
Thread object containing the details of the created thread.
|
29 |
+
"""
|
30 |
+
return self.client.beta.threads.create()
|
31 |
+
|
32 |
+
def create_message(self, thread_id, content):
|
33 |
+
"""
|
34 |
+
Sends a message in a thread.
|
35 |
+
|
36 |
+
Args:
|
37 |
+
thread_id (str): The ID of the thread.
|
38 |
+
content (str): The content of the message.
|
39 |
+
|
40 |
+
Returns:
|
41 |
+
Message object containing the details of the created message.
|
42 |
+
"""
|
43 |
+
return self.client.beta.threads.messages.create(
|
44 |
+
thread_id=thread_id,
|
45 |
+
role="user",
|
46 |
+
content=content
|
47 |
+
)
|
48 |
+
|
49 |
+
def run_and_poll(self, thread_id):
|
50 |
+
"""
|
51 |
+
Runs a process and polls for its completion.
|
52 |
+
|
53 |
+
Args:
|
54 |
+
thread_id (str): The ID of the thread.
|
55 |
+
|
56 |
+
Returns:
|
57 |
+
Run object containing the status and details of the run.
|
58 |
+
"""
|
59 |
+
return self.client.beta.threads.runs.create_and_poll(
|
60 |
+
thread_id=thread_id,
|
61 |
+
assistant_id=self.assistant.id,
|
62 |
+
instructions="Respond with a dict each time with the following keys: 'design_style', 'room_type'"
|
63 |
+
)
|
64 |
+
|
65 |
+
def get_messages(self, thread_id):
|
66 |
+
"""
|
67 |
+
Retrieves messages from a thread.
|
68 |
+
|
69 |
+
Args:
|
70 |
+
thread_id (str): The ID of the thread.
|
71 |
+
|
72 |
+
Returns:
|
73 |
+
List of Message objects containing the messages in the thread.
|
74 |
+
"""
|
75 |
+
return self.client.beta.threads.messages.list(
|
76 |
+
thread_id=thread_id
|
77 |
+
)
|
78 |
+
|
79 |
+
if __name__ == "__main__":
|
80 |
+
assistant = DesignAssistant()
|
81 |
+
thread = assistant.create_thread()
|
82 |
+
message = assistant.create_message(thread.id, "I want to generate a design for a scandanavian bedroom")
|
83 |
+
run = assistant.run_and_poll(thread.id)
|
84 |
+
|
85 |
+
if run.status == 'completed':
|
86 |
+
messages = assistant.get_messages(thread.id)
|
87 |
+
print(messages.data[0].content[0].text.value)
|
88 |
+
else:
|
89 |
+
print(run.status)
|
perfect_redesign/render_app.py
ADDED
@@ -0,0 +1,115 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""
|
2 |
+
This module provides the DesignProcess class to interact with the homedesigns.ai API
|
3 |
+
for starting and checking the status of a design process, as well as generating design ideas
|
4 |
+
using OpenAI's API.
|
5 |
+
"""
|
6 |
+
import os
|
7 |
+
import openai
|
8 |
+
# from flask import Flask, request, jsonify
|
9 |
+
from dotenv import load_dotenv
|
10 |
+
import time
|
11 |
+
load_dotenv()
|
12 |
+
import requests
|
13 |
+
from PIL import Image
|
14 |
+
|
15 |
+
class DesignProcess:
|
16 |
+
"""
|
17 |
+
A class to handle the design process using the homedesigns.ai API.
|
18 |
+
"""
|
19 |
+
|
20 |
+
def __init__(self, image_path, design_type="Interior", ai_intervention="Mid", no_design=1, design_style="Scandinavian", room_type="Bedroom"):
|
21 |
+
self.url = os.getenv("API_URL")
|
22 |
+
self.headers = {
|
23 |
+
"Authorization": os.getenv("AUTH_TOKEN"),
|
24 |
+
}
|
25 |
+
self.image_path = image_path
|
26 |
+
self.design_type = design_type
|
27 |
+
self.ai_intervention = ai_intervention
|
28 |
+
self.no_design = no_design
|
29 |
+
self.design_style = design_style
|
30 |
+
self.room_type = room_type
|
31 |
+
|
32 |
+
def start_process(self, max_retries=3, delay=2):
|
33 |
+
"""
|
34 |
+
Starts the design process by sending a POST request.
|
35 |
+
Retries the request if it fails.
|
36 |
+
"""
|
37 |
+
attempt = 0
|
38 |
+
while attempt < max_retries:
|
39 |
+
try:
|
40 |
+
with open(self.image_path, "rb") as image_file:
|
41 |
+
image = Image.open(image_file)
|
42 |
+
width, height = image.size
|
43 |
+
if width < 512 or height < 512:
|
44 |
+
raise ValueError("The image must have a minimum width and height of 512 pixels.")
|
45 |
+
image_file.seek(0)
|
46 |
+
|
47 |
+
files = {"image": open(self.image_path, "rb")}
|
48 |
+
data = {
|
49 |
+
"design_type": self.design_type,
|
50 |
+
"ai_intervention": self.ai_intervention,
|
51 |
+
"no_design": self.no_design,
|
52 |
+
"design_style": self.design_style,
|
53 |
+
"room_type": self.room_type,
|
54 |
+
}
|
55 |
+
|
56 |
+
|
57 |
+
response = requests.post(self.url, headers=self.headers, files=files, data=data)
|
58 |
+
response.raise_for_status() # Raise an HTTPError for bad responses
|
59 |
+
|
60 |
+
try:
|
61 |
+
return response.json() # Returns the JSON response from the API.
|
62 |
+
except requests.exceptions.JSONDecodeError:
|
63 |
+
print("Failed to decode JSON response")
|
64 |
+
print("Response content:", response.text)
|
65 |
+
raise requests.RequestException("Invalid JSON response")
|
66 |
+
except requests.RequestException as e:
|
67 |
+
print(f"Attempt {attempt + 1} failed: {e}")
|
68 |
+
attempt += 1
|
69 |
+
if attempt < max_retries:
|
70 |
+
time.sleep(delay)
|
71 |
+
else:
|
72 |
+
raise
|
73 |
+
|
74 |
+
# def generate_design_idea(self, prompt):
|
75 |
+
# """
|
76 |
+
# Generates a design idea using OpenAI's API.
|
77 |
+
# """
|
78 |
+
# openai.api_key = os.getenv("OPENAI_API_KEY")
|
79 |
+
# response = openai.ChatCompletion.create(
|
80 |
+
# model="gpt-3.5-turbo",
|
81 |
+
# messages=[
|
82 |
+
# {"role": "system", "content": "You are a helpful assistant."},
|
83 |
+
# {"role": "user", "content": prompt}
|
84 |
+
# ],
|
85 |
+
# max_tokens=150
|
86 |
+
# )
|
87 |
+
# return response.choices[0].message['content'].strip()
|
88 |
+
|
89 |
+
def check_status(self, request_id):
|
90 |
+
"""
|
91 |
+
Checks the status of the design process.
|
92 |
+
"""
|
93 |
+
status_url = f"https://homedesigns.ai/api/v2/perfect_redesign/status_check/{request_id}"
|
94 |
+
attempt = 0
|
95 |
+
max_retries = 3
|
96 |
+
delay = 5 # seconds
|
97 |
+
|
98 |
+
while attempt < max_retries:
|
99 |
+
try:
|
100 |
+
status_response = requests.get(status_url, headers=self.headers)
|
101 |
+
status_response.raise_for_status() # Raise an HTTPError for bad responses
|
102 |
+
|
103 |
+
try:
|
104 |
+
return status_response.json()
|
105 |
+
except requests.exceptions.JSONDecodeError:
|
106 |
+
print("Failed to decode JSON response")
|
107 |
+
print("Response content:", status_response.text)
|
108 |
+
raise requests.RequestException("Invalid JSON response")
|
109 |
+
except requests.RequestException as e:
|
110 |
+
print(f"Attempt {attempt + 1} failed: {e}")
|
111 |
+
attempt += 1
|
112 |
+
if attempt < max_retries:
|
113 |
+
time.sleep(delay)
|
114 |
+
else:
|
115 |
+
return {'status': 'error', 'message': 'Failed to get a valid response after multiple attempts'}
|
requirements.txt
ADDED
@@ -0,0 +1,5 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
flask
|
2 |
+
gradio
|
3 |
+
openai
|
4 |
+
python-dotenv
|
5 |
+
gradio
|
sketch_design/__pycache__/main.cpython-312.pyc
ADDED
Binary file (4.3 kB). View file
|
|
sketch_design/__pycache__/render_ai.cpython-312.pyc
ADDED
Binary file (6.83 kB). View file
|
|
sketch_design/__pycache__/render_app.cpython-312.pyc
ADDED
Binary file (6.02 kB). View file
|
|
sketch_design/__pycache__/sk_render_ai.cpython-312.pyc
ADDED
Binary file (6.83 kB). View file
|
|
sketch_design/main.py
ADDED
@@ -0,0 +1,127 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""
|
2 |
+
This script orchestrates the design process by utilizing the DesignAssistant and DesignProcess classes.
|
3 |
+
It extracts design parameters using the DesignAssistant and applies them using the DesignProcess.
|
4 |
+
"""
|
5 |
+
from .sk_render_ai import DesignAssistant
|
6 |
+
from .render_app import DesignProcess
|
7 |
+
import requests
|
8 |
+
import time
|
9 |
+
|
10 |
+
|
11 |
+
|
12 |
+
def flow(image_path, output_path, user_prompt="", design_type="Interior", ai_intervention="Mid", no_design=1, house_angle=None, garden_type=None, internal_prompt=None, design_style=None):
|
13 |
+
"""
|
14 |
+
Orchestrates the design process by extracting design parameters and applying them.
|
15 |
+
|
16 |
+
Args:
|
17 |
+
user_prompt (str): The prompt provided by the user to generate design parameters.
|
18 |
+
image_path (str): The path to the input image for the design process.
|
19 |
+
output_path (str): The path where the output image will be saved.
|
20 |
+
|
21 |
+
Returns:
|
22 |
+
str: The path to the saved output image if successful, or an error message if failed.
|
23 |
+
"""
|
24 |
+
|
25 |
+
|
26 |
+
try:
|
27 |
+
# print all args
|
28 |
+
print("=====Flow SR function=====")
|
29 |
+
print("User Prompt: ", user_prompt, "Image Path: ", image_path, "Output Path: ", output_path, "Design Type: ", design_type, "AI Intervention: ", ai_intervention, "No Design: ", no_design, "House Angle: ", house_angle, "Garden Type: ", garden_type, "Internal Prompt: ", internal_prompt, "Design Style: ", design_style)
|
30 |
+
print("=============================")
|
31 |
+
# Extract design parameters using render_ai.py
|
32 |
+
if design_style is None:
|
33 |
+
assistant = DesignAssistant()
|
34 |
+
thread = assistant.create_thread()
|
35 |
+
_user_prompt = f"The information can be in italian aswell, so choose the closest values from the above lists for the dict's values as the response will be always in english.\n{user_prompt}"
|
36 |
+
message = assistant.create_message(thread.id, _user_prompt)
|
37 |
+
run = assistant.run_and_poll(thread.id)
|
38 |
+
|
39 |
+
if run.status == 'completed':
|
40 |
+
messages = assistant.get_messages(thread.id)
|
41 |
+
design_info = eval(messages.data[0].content[0].text.value) # Assuming the response is a dict in string format
|
42 |
+
# Debugging information
|
43 |
+
print(design_info)
|
44 |
+
print(type(design_info))
|
45 |
+
print(design_info.keys())
|
46 |
+
print("---------------------------------------------")
|
47 |
+
else:
|
48 |
+
print("Failed to extract design information.")
|
49 |
+
return
|
50 |
+
else:
|
51 |
+
design_info = {
|
52 |
+
'design_style': design_style,
|
53 |
+
'room_type': None
|
54 |
+
}
|
55 |
+
|
56 |
+
# Use the extracted design parameters in render_app.py
|
57 |
+
design_process = DesignProcess(
|
58 |
+
image_path=image_path,
|
59 |
+
design_style=design_info['design_style'],
|
60 |
+
room_type=design_info['room_type'],
|
61 |
+
design_type=design_type,
|
62 |
+
ai_intervention=ai_intervention,
|
63 |
+
no_design=no_design,
|
64 |
+
house_angle=house_angle,
|
65 |
+
garden_type=garden_type,
|
66 |
+
internal_prompt=internal_prompt
|
67 |
+
)
|
68 |
+
|
69 |
+
response = design_process.start_process()
|
70 |
+
print(response)
|
71 |
+
# request_id = response['id']
|
72 |
+
# print(request_id)
|
73 |
+
# print(type(request_id))
|
74 |
+
|
75 |
+
if 'success' in response:
|
76 |
+
print("Design process completed successfully. Image saved as new_design.jpg.")
|
77 |
+
print("---------------------------------------------")
|
78 |
+
|
79 |
+
print(response['success']['generated_image'])
|
80 |
+
|
81 |
+
image_data = requests.get(response['success']['generated_image'][0]).content
|
82 |
+
with open(output_path, "wb") as f:
|
83 |
+
f.write(image_data)
|
84 |
+
print("Design process completed successfully. Image saved as new_design.jpg.")
|
85 |
+
return output_path
|
86 |
+
else:
|
87 |
+
print("Design process failed.")
|
88 |
+
|
89 |
+
# while True:
|
90 |
+
# status = design_process.check_status(request_id)
|
91 |
+
# print(status) # Prints the status of the redesign request
|
92 |
+
# # Wait for the process to complete or fail
|
93 |
+
|
94 |
+
# if status['status'] in ['succeeded', 'error']:
|
95 |
+
# break
|
96 |
+
|
97 |
+
# time.sleep(7)
|
98 |
+
|
99 |
+
# if status.get('status') == 'succeeded':
|
100 |
+
# image_url = status['output'][0] # Assuming you want the first image
|
101 |
+
# # Save the image to the specified output path
|
102 |
+
# image_data = requests.get(image_url).content
|
103 |
+
# with open(output_path, "wb") as f:
|
104 |
+
# f.write(image_data)
|
105 |
+
# print("Design process completed successfully. Image saved as new_design.jpg.")
|
106 |
+
# return output_path
|
107 |
+
# else:
|
108 |
+
# print("Design process failed.")
|
109 |
+
# return "Design process failed."
|
110 |
+
|
111 |
+
except Exception as e:
|
112 |
+
raise
|
113 |
+
|
114 |
+
|
115 |
+
|
116 |
+
|
117 |
+
if __name__ == "__main__":
|
118 |
+
|
119 |
+
flow(
|
120 |
+
image_path = "sketch_bedroom.jpg",
|
121 |
+
output_path = "new_design.jpg",
|
122 |
+
design_type = "Interior",
|
123 |
+
ai_intervention = "Mid",
|
124 |
+
no_design = 1,
|
125 |
+
house_angle = None,
|
126 |
+
garden_type = None,
|
127 |
+
user_prompt = "I want to generate a design for a scandanavian bedroom")
|
sketch_design/render_app.py
ADDED
@@ -0,0 +1,129 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""
|
2 |
+
This module provides the DesignProcess class to interact with the homedesigns.ai API
|
3 |
+
for starting and checking the status of a design process, as well as generating design ideas
|
4 |
+
using OpenAI's API.
|
5 |
+
"""
|
6 |
+
import os
|
7 |
+
import openai
|
8 |
+
# from flask import Flask, request, jsonify
|
9 |
+
from dotenv import load_dotenv
|
10 |
+
import time
|
11 |
+
load_dotenv()
|
12 |
+
import requests
|
13 |
+
from PIL import Image
|
14 |
+
|
15 |
+
class DesignProcess:
|
16 |
+
"""
|
17 |
+
A class to handle the design process using the homedesigns.ai API.
|
18 |
+
"""
|
19 |
+
|
20 |
+
def __init__(self, image_path, design_type="Interior", ai_intervention="Mid", no_design=1, design_style="Scandinavian", room_type="Bedroom", house_angle=None, garden_type=None, internal_prompt=None):
|
21 |
+
self.url = os.getenv("S2R_API_URL")
|
22 |
+
self.headers = {
|
23 |
+
"Authorization": os.getenv("AUTH_TOKEN"),
|
24 |
+
}
|
25 |
+
self.image_path = image_path
|
26 |
+
self.design_type = design_type
|
27 |
+
self.ai_intervention = ai_intervention
|
28 |
+
self.no_design = no_design
|
29 |
+
self.design_style = design_style
|
30 |
+
self.room_type = room_type
|
31 |
+
self.house_angle = house_angle
|
32 |
+
self.garden_type = garden_type
|
33 |
+
self.internal_prompt = internal_prompt
|
34 |
+
|
35 |
+
def start_process(self, max_retries=3, delay=2):
|
36 |
+
"""
|
37 |
+
Starts the design process by sending a POST request.
|
38 |
+
Retries the request if it fails.
|
39 |
+
"""
|
40 |
+
attempt = 0
|
41 |
+
while attempt < max_retries:
|
42 |
+
try:
|
43 |
+
with open(self.image_path, "rb") as image_file:
|
44 |
+
image = Image.open(image_file)
|
45 |
+
width, height = image.size
|
46 |
+
if width < 512 or height < 512:
|
47 |
+
raise ValueError("The image must have a minimum width and height of 512 pixels.")
|
48 |
+
image_file.seek(0)
|
49 |
+
|
50 |
+
files = {"image": open(self.image_path, "rb")}
|
51 |
+
data = {
|
52 |
+
"design_type": self.design_type,
|
53 |
+
"ai_intervention": self.ai_intervention,
|
54 |
+
"no_design": self.no_design,
|
55 |
+
"design_style": self.design_style,
|
56 |
+
"room_type": self.room_type,
|
57 |
+
"house_angle": self.house_angle,
|
58 |
+
"garden_type": self.garden_type,
|
59 |
+
"internal_prompt": self.internal_prompt
|
60 |
+
}
|
61 |
+
print("====================Data before filtering=======================")
|
62 |
+
print(data)
|
63 |
+
data = {k: v for k, v in data.items() if v is not None}
|
64 |
+
print("====================Data after filtering========================")
|
65 |
+
print(data)
|
66 |
+
print("================================================================")
|
67 |
+
response = requests.post(self.url, headers=self.headers, files=files, data=data)
|
68 |
+
print(response)
|
69 |
+
print("===========================Text============================")
|
70 |
+
print(response.text)
|
71 |
+
print("================================================================")
|
72 |
+
response.raise_for_status() # Raise an HTTPError for bad responses
|
73 |
+
# print(response.reason)
|
74 |
+
try:
|
75 |
+
return response.json() # Returns the JSON response from the API.
|
76 |
+
except requests.exceptions.JSONDecodeError:
|
77 |
+
print("Failed to decode JSON response")
|
78 |
+
print("Response content:", response.text)
|
79 |
+
raise requests.RequestException("Invalid JSON response")
|
80 |
+
except requests.RequestException as e:
|
81 |
+
print(f"Attempt {attempt + 1} failed: {e}")
|
82 |
+
attempt += 1
|
83 |
+
if attempt < max_retries:
|
84 |
+
time.sleep(delay)
|
85 |
+
else:
|
86 |
+
raise
|
87 |
+
|
88 |
+
# def generate_design_idea(self, prompt):
|
89 |
+
# """
|
90 |
+
# Generates a design idea using OpenAI's API.
|
91 |
+
# """
|
92 |
+
# openai.api_key = os.getenv("OPENAI_API_KEY")
|
93 |
+
# response = openai.ChatCompletion.create(
|
94 |
+
# model="gpt-3.5-turbo",
|
95 |
+
# messages=[
|
96 |
+
# {"role": "system", "content": "You are a helpful assistant."},
|
97 |
+
# {"role": "user", "content": prompt}
|
98 |
+
# ],
|
99 |
+
# max_tokens=150
|
100 |
+
# )
|
101 |
+
# return response.choices[0].message['content'].strip()
|
102 |
+
|
103 |
+
def check_status(self, request_id):
|
104 |
+
"""
|
105 |
+
Checks the status of the design process.
|
106 |
+
"""
|
107 |
+
status_url = f"https://homedesigns.ai/api/v2/perfect_redesign/status_check/{request_id}"
|
108 |
+
attempt = 0
|
109 |
+
max_retries = 3
|
110 |
+
delay = 5 # seconds
|
111 |
+
|
112 |
+
while attempt < max_retries:
|
113 |
+
try:
|
114 |
+
status_response = requests.get(status_url, headers=self.headers)
|
115 |
+
status_response.raise_for_status() # Raise an HTTPError for bad responses
|
116 |
+
|
117 |
+
try:
|
118 |
+
return status_response.json()
|
119 |
+
except requests.exceptions.JSONDecodeError:
|
120 |
+
print("Failed to decode JSON response")
|
121 |
+
print("Response content:", status_response.text)
|
122 |
+
raise requests.RequestException("Invalid JSON response")
|
123 |
+
except requests.RequestException as e:
|
124 |
+
print(f"Attempt {attempt + 1} failed: {e}")
|
125 |
+
attempt += 1
|
126 |
+
if attempt < max_retries:
|
127 |
+
time.sleep(delay)
|
128 |
+
else:
|
129 |
+
return {'status': 'error', 'message': 'Failed to get a valid response after multiple attempts'}
|
sketch_design/sk_render_ai.py
ADDED
@@ -0,0 +1,89 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""
|
2 |
+
This module provides the DesignAssistant class to interact with OpenAI's API
|
3 |
+
for creating and managing threads and messages related to design assistance.
|
4 |
+
"""
|
5 |
+
import os
|
6 |
+
from dotenv import load_dotenv
|
7 |
+
from openai import OpenAI
|
8 |
+
|
9 |
+
# Load environment variables from .env file
|
10 |
+
load_dotenv()
|
11 |
+
|
12 |
+
class DesignAssistant:
|
13 |
+
def __init__(self):
|
14 |
+
self.client = OpenAI(api_key=os.getenv("OPENAI_API_KEY"))
|
15 |
+
self.assistant = self.client.beta.assistants.create(
|
16 |
+
name="Extraction Assistant",
|
17 |
+
# instructions="You are a professional Bedroom renovator engine, you get an information and you respond with a dict each time with the following keys: 'design_style', 'room_type'. Respond with the dict only and no need to encapsulate between quotes.",
|
18 |
+
instructions= "You are a professional dictionary creator.\n\nFollowing are some important rules;\nYou get some information and you respond with a dict each time with the following keys: 'design_style', 'room_type' only and always. Respond with the dict only and no need to encapsulate between quotes.\n\nThe room_type and design_style has to be choosen from the following, incase of confusion choose the closest one;\nroom_types = [\"Living Room\", \"Bedroom\", \"Bathroom\", \"Kitchen\", \"Dining Room\", \"Attic\", \"Family Room\", \"Kids Room\", \"Study Room\", \"Home Office\", \"Meeting Room\", \"Coffee Shop\", \"Office\", \"Coworking Space\", \"Working Space\", \"Library\", \"Science Laboratory\", \"Photo Studio\", \"Exhibition Space\", \"Art Studio\", \"Multimedia Room\", \"Medical Exam Room\", \"Reception Area\", \"Formal Dining Room\", \"Home Theater\", \"Gaming Room\", \"Fitness Gym\", \"Restaurant\", \"Hotel Lobby\", \"Hotel Room\", \"Wine Cellar\", \"Home Spa\", \"Dressing Room\", \"Home Bar\", \"Music Room\", \"Workshop\", \"Craft Room\", \"Yoga Studio\", \"Auditorium\", \"Art Studio\", \"Balcony\", \"Rooftop Terrace\", \"Mudroom\", \"Guest Bedroom\", \"Wedding Room\", \"Outdoor Kitchen\", \"Utility Room\", \"Laundry Room\", \"Pet Room\", \"Walk-in Closet\", \"Lounge\", \"Reading Nook\", \"Foyer\", \"Open Kitchen Living Room\", \"Prayer Room\", \"Conservatory\", \"Playroom\", \"Man Cave\", \"She Shed\", \"Greenhouse\", \"Sauna\", \"Nursery\", \"Home Gym\"]\n\ndesign_styles = [\"No Style\", \"Eclectic\", \"Modern\", \"Contemporary\", \"Transitional\", \"Scandinavian\", \"Mediterranean\", \"Ikea\", \"Industrial\", \"Kids Room\", \"Shabby Chic\", \"Coastal\", \"Bauhaus\", \"Bohemian\", \"Traditional\", \"Rustic\", \"Minimalism\", \"Japandi\", \"Japanese Design\", \"Modern Arabic\", \"Traditional Arabic\", \"Bali\", \"Tropical\", \"Asian Decor\", \"Zen\", \"Hollywood Regency\", \"Hollywood Glam\", \"Minimalist\", \"Christmas\", \"Futuristic\", \"Luxurious\", \"Midcentury Modern\", \"Biophilic\", \"Cottage Core\", \"French Country\", \"Art Deco\", \"Art Nouveau\", \"South Western\", \"Modern Farm House\", \"Moroccan\", \"Gothic\", \"Victorian\", \"Steampunk\", \"Urban Modern\", \"Desert Modernism\", \"Colonial\", \"Brutalist\", \"Nordic Noir\", \"Postmodern\", \"Psychedelic\", \"Cosmic Chic\", \"Mexican Hacienda\", \"Coastal Modern\", \"Eco Friendly\", \"Pop Art\", \"Vintage Glam\", \"Candy Land\", \"Airbnb\", \"Glam Rock\", \"Barbie\", \"Doodle\", \"Sketch\", \"Maximalist\", \"Professional\", \"Halloween\", \"Retro\", \"Romantic\", \"Safari\", \"Tuscan\", \"Nautical\", \"Craftsman\", \"Farmhouse Chic\", \"Prairie\", \"Cubism\", \"Quiet Luxury\"]\n\nThe information can be in italian aswell, so choose the closest values from the above lists for the dict's values as the response will be always in english.",
|
19 |
+
tools=[],
|
20 |
+
model="gpt-4o",
|
21 |
+
)
|
22 |
+
|
23 |
+
def create_thread(self):
|
24 |
+
"""
|
25 |
+
Creates a new thread for communication.
|
26 |
+
|
27 |
+
Returns:
|
28 |
+
Thread object containing the details of the created thread.
|
29 |
+
"""
|
30 |
+
return self.client.beta.threads.create()
|
31 |
+
|
32 |
+
def create_message(self, thread_id, content):
|
33 |
+
"""
|
34 |
+
Sends a message in a thread.
|
35 |
+
|
36 |
+
Args:
|
37 |
+
thread_id (str): The ID of the thread.
|
38 |
+
content (str): The content of the message.
|
39 |
+
|
40 |
+
Returns:
|
41 |
+
Message object containing the details of the created message.
|
42 |
+
"""
|
43 |
+
return self.client.beta.threads.messages.create(
|
44 |
+
thread_id=thread_id,
|
45 |
+
role="user",
|
46 |
+
content=content
|
47 |
+
)
|
48 |
+
|
49 |
+
def run_and_poll(self, thread_id):
|
50 |
+
"""
|
51 |
+
Runs a process and polls for its completion.
|
52 |
+
|
53 |
+
Args:
|
54 |
+
thread_id (str): The ID of the thread.
|
55 |
+
|
56 |
+
Returns:
|
57 |
+
Run object containing the status and details of the run.
|
58 |
+
"""
|
59 |
+
return self.client.beta.threads.runs.create_and_poll(
|
60 |
+
thread_id=thread_id,
|
61 |
+
assistant_id=self.assistant.id,
|
62 |
+
instructions="Respond with a dict each time with the following keys: 'design_style', 'room_type'"
|
63 |
+
)
|
64 |
+
|
65 |
+
def get_messages(self, thread_id):
|
66 |
+
"""
|
67 |
+
Retrieves messages from a thread.
|
68 |
+
|
69 |
+
Args:
|
70 |
+
thread_id (str): The ID of the thread.
|
71 |
+
|
72 |
+
Returns:
|
73 |
+
List of Message objects containing the messages in the thread.
|
74 |
+
"""
|
75 |
+
return self.client.beta.threads.messages.list(
|
76 |
+
thread_id=thread_id
|
77 |
+
)
|
78 |
+
|
79 |
+
if __name__ == "__main__":
|
80 |
+
assistant = DesignAssistant()
|
81 |
+
thread = assistant.create_thread()
|
82 |
+
message = assistant.create_message(thread.id, "I want to generate a design for a scandanavian bedroom")
|
83 |
+
run = assistant.run_and_poll(thread.id)
|
84 |
+
|
85 |
+
if run.status == 'completed':
|
86 |
+
messages = assistant.get_messages(thread.id)
|
87 |
+
print(messages.data[0].content[0].text.value)
|
88 |
+
else:
|
89 |
+
print(run.status)
|