|
|
from fastai.vision.all import * |
|
|
import gradio as gr |
|
|
import fal_client |
|
|
from PIL import Image |
|
|
import io |
|
|
import random |
|
|
import requests |
|
|
from pathlib import Path |
|
|
import openai |
|
|
from dotenv import load_dotenv |
|
|
import os |
|
|
|
|
|
|
|
|
load_dotenv() |
|
|
|
|
|
|
|
|
openai.api_key = os.getenv("OPENAI_API_KEY") |
|
|
|
|
|
|
|
|
search_terms_wikipedia = { |
|
|
"blazing star": "https://en.wikipedia.org/wiki/Mentzelia", |
|
|
"bristlecone pine": "https://en.wikipedia.org/wiki/Pinus_longaeva", |
|
|
"california bluebell": "https://en.wikipedia.org/wiki/Phacelia_minor", |
|
|
"california buckeye": "https://en.wikipedia.org/wiki/Aesculus_californica", |
|
|
"california buckwheat": "https://en.wikipedia.org/wiki/Eriogonum_fasciculatum", |
|
|
"california fuchsia": "https://en.wikipedia.org/wiki/Epilobium_canum", |
|
|
"california checkerbloom": "https://en.wikipedia.org/wiki/Sidalcea_malviflora", |
|
|
"california lilac": "https://en.wikipedia.org/wiki/Ceanothus", |
|
|
"california poppy": "https://en.wikipedia.org/wiki/Eschscholzia_californica", |
|
|
"california sagebrush": "https://en.wikipedia.org/wiki/Artemisia_californica", |
|
|
"california wild grape": "https://en.wikipedia.org/wiki/Vitis_californica", |
|
|
"california wild rose": "https://en.wikipedia.org/wiki/Rosa_californica", |
|
|
"coyote mint": "https://en.wikipedia.org/wiki/Monardella", |
|
|
"elegant clarkia": "https://en.wikipedia.org/wiki/Clarkia_unguiculata", |
|
|
"baby blue eyes": "https://en.wikipedia.org/wiki/Nemophila_menziesii", |
|
|
"hummingbird sage": "https://en.wikipedia.org/wiki/Salvia_spathacea", |
|
|
"delphinium": "https://en.wikipedia.org/wiki/Delphinium", |
|
|
"matilija poppy": "https://en.wikipedia.org/wiki/Romneya_coulteri", |
|
|
"blue-eyed grass": "https://en.wikipedia.org/wiki/Sisyrinchium_bellum", |
|
|
"penstemon spectabilis": "https://en.wikipedia.org/wiki/Penstemon_spectabilis", |
|
|
"seaside daisy": "https://en.wikipedia.org/wiki/Erigeron_glaucus", |
|
|
"sticky monkeyflower": "https://en.wikipedia.org/wiki/Diplacus_aurantiacus", |
|
|
"tidy tips": "https://en.wikipedia.org/wiki/Layia_platyglossa", |
|
|
"wild cucumber": "https://en.wikipedia.org/wiki/Marah_(plant)", |
|
|
"douglas iris": "https://en.wikipedia.org/wiki/Iris_douglasiana", |
|
|
"goldfields coreopsis": "https://en.wikipedia.org/wiki/Coreopsis" |
|
|
} |
|
|
|
|
|
flowers_endangerment = { |
|
|
"blazing star": "Not considered endangered.", |
|
|
"bristlecone pine": "Least Concern (stable population).", |
|
|
"california bluebell": "Not listed as endangered or threatened.", |
|
|
"california buckeye": "Not endangered.", |
|
|
"california buckwheat": "Generally secure.", |
|
|
"california fuchsia": "Not endangered overall; some subspecies at risk.", |
|
|
"california checkerbloom": "Not generally endangered; some subspecies critically imperiled.", |
|
|
"california lilac": "Most species not endangered; some species are endangered.", |
|
|
"california poppy": "Generally secure; some subspecies face threats.", |
|
|
"california sagebrush": "Considered secure (G4-G5).", |
|
|
"california wild grape": "Apparently secure (G4).", |
|
|
"california wild rose": "Secure (G4).", |
|
|
"coyote mint": "Varies by species; some federally listed as endangered.", |
|
|
"elegant clarkia": "Secure (G5).", |
|
|
"baby blue eyes": "Secure.", |
|
|
"hummingbird sage": "Apparently secure (G4).", |
|
|
"delphinium": "Varies by species; some are endangered.", |
|
|
"matilija poppy": "Not currently endangered.", |
|
|
"blue-eyed grass": "Not endangered.", |
|
|
"penstemon spectabilis": "Not endangered.", |
|
|
"seaside daisy": "Not endangered.", |
|
|
"sticky monkeyflower": "Not endangered.", |
|
|
"tidy tips": "Generally not endangered; some subspecies may be at risk.", |
|
|
"wild cucumber": "Generally not endangered.", |
|
|
"douglas iris": "Not endangered.", |
|
|
"goldfields coreopsis": "Varies by species; many not endangered." |
|
|
} |
|
|
|
|
|
|
|
|
prompt_templates = [ |
|
|
"A dreamy watercolor scene of a {flower} on a misty morning trail, with golden sunbeams filtering through towering redwoods, and a curious hummingbird hovering nearby.", |
|
|
"A loose, expressive watercolor sketch of a {flower} in a wild meadow, surrounded by dancing butterflies and morning dew drops sparkling like diamonds in the dawn light.", |
|
|
"An artist's nature journal page featuring a detailed {flower} study, with delicate ink lines and soft watercolor washes, complete with small sketches of bees and field notes in the margins.", |
|
|
"A vibrant plein air painting of a {flower} patch along a coastal hiking trail, with crashing waves and rugged cliffs in the background, painted in bold, energetic brushstrokes.", |
|
|
"A whimsical mixed-media scene of a {flower} garden at sunrise, combining loose watercolor washes with detailed botanical illustrations, featuring hidden wildlife and morning fog rolling through the valley." |
|
|
] |
|
|
|
|
|
|
|
|
example_images = [ |
|
|
str(Path('example_images/example_1.jpg')), |
|
|
str(Path('example_images/example_2.jpg')), |
|
|
str(Path('example_images/example_3.jpg')), |
|
|
str(Path('example_images/example_4.jpg')), |
|
|
str(Path('example_images/example_5.jpg')) |
|
|
|
|
|
] |
|
|
|
|
|
|
|
|
def on_queue_update(update): |
|
|
if isinstance(update, fal_client.InProgress): |
|
|
for log in update.logs: |
|
|
print(log["message"]) |
|
|
|
|
|
|
|
|
|
|
|
def get_status(flower_name): |
|
|
"""Return the endangerment status of a given flower name.""" |
|
|
|
|
|
normalized_name = flower_name.title() |
|
|
return flowers_endangerment.get(normalized_name, "Flower not found in database.") |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def process_image(img): |
|
|
print("Starting prediction...") |
|
|
predicted_class, _, probs = learn.predict(img) |
|
|
print(f"Prediction complete: {predicted_class}") |
|
|
|
|
|
classification_results = dict(zip(learn.dls.vocab, map(float, probs))) |
|
|
|
|
|
|
|
|
wiki_url = search_terms_wikipedia.get(predicted_class, "No Wikipedia entry found.") |
|
|
|
|
|
|
|
|
endangerment_status = get_status(predicted_class) |
|
|
print(f"Status found: {endangerment_status}") |
|
|
|
|
|
|
|
|
print("Sending request to DALL-E...") |
|
|
try: |
|
|
response = openai.images.generate( |
|
|
model="dall-e-3", |
|
|
prompt=random.choice(prompt_templates).format(flower=predicted_class), |
|
|
size="1024x1024", |
|
|
quality="standard", |
|
|
n=1, |
|
|
) |
|
|
|
|
|
|
|
|
image_url = response.data[0].url |
|
|
print(f"Image URL: {image_url}") |
|
|
|
|
|
|
|
|
response = requests.get(image_url) |
|
|
generated_image = Image.open(io.BytesIO(response.content)) |
|
|
|
|
|
except Exception as e: |
|
|
print(f"Error generating image: {e}") |
|
|
generated_image = None |
|
|
|
|
|
print("Image retrieved and ready to return") |
|
|
return classification_results, generated_image, wiki_url, endangerment_status |
|
|
|
|
|
|
|
|
|
|
|
def clear_outputs(): |
|
|
return { |
|
|
label_output: None, |
|
|
generated_image: None, |
|
|
wiki_output: None, |
|
|
status_output: None |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
learn = load_learner('resnet50_30_categories.pkl') |
|
|
|
|
|
|
|
|
with gr.Blocks() as demo: |
|
|
|
|
|
with gr.Row(): |
|
|
input_image = gr.Image(height=230, width=230, label="Upload Image for Classification", type="pil") |
|
|
|
|
|
|
|
|
|
|
|
with gr.Row(): |
|
|
with gr.Column(): |
|
|
label_output = gr.Label(label="Classification Results") |
|
|
wiki_output = gr.Textbox(label="Wikipedia Article Link", lines=1) |
|
|
status_output = gr.Textbox(label="Endangerment Status", lines=1) |
|
|
generated_image = gr.Image(label="AI Generated Interpretation") |
|
|
|
|
|
|
|
|
gr.Examples( |
|
|
examples=example_images, |
|
|
inputs=input_image, |
|
|
examples_per_page=6, |
|
|
fn=process_image, |
|
|
outputs=[label_output, generated_image, wiki_output, status_output] |
|
|
) |
|
|
|
|
|
input_image.change( |
|
|
fn=process_image, |
|
|
inputs=input_image, |
|
|
outputs=[label_output, generated_image, wiki_output, status_output] |
|
|
) |
|
|
|
|
|
input_image.clear( |
|
|
fn=clear_outputs, |
|
|
inputs=[], |
|
|
outputs=[label_output, generated_image, wiki_output, status_output] |
|
|
) |
|
|
|
|
|
|
|
|
|
|
|
demo.launch(inline=False) |