Spaces:
Sleeping
Sleeping
| import streamlit as st | |
| from google import genai | |
| from google.genai import types | |
| from PIL import Image | |
| import os | |
| import tempfile | |
| # Authentification et initialisation du client Gemini | |
| gen = os.environ['GOOGLE_API_KEY'] | |
| client = genai.Client(api_key=gen) | |
| # --- MISE EN PAGE ET STYLE --- | |
| st.set_page_config(page_title="Mariam Espagnol", page_icon="🇪🇸", layout="wide") | |
| # Style CSS personnalisé | |
| st.markdown(""" | |
| <style> | |
| body { | |
| background-color: #f0f2f6; | |
| } | |
| .title { | |
| color: #0077cc; | |
| font-size: 3em; | |
| font-weight: bold; | |
| text-align: center; | |
| margin-bottom: 20px; | |
| } | |
| .subtitle { | |
| color: #28a745; | |
| font-size: 1.5em; | |
| font-weight: bold; | |
| margin-top: 30px; | |
| } | |
| .sidebar { | |
| background-color: #e9ecef; | |
| padding: 20px; | |
| border-radius: 10px; | |
| } | |
| .important-info { | |
| background-color: #d4edda; | |
| border: 1px solid #c3e6cb; | |
| color: #155724; | |
| padding: 15px; | |
| border-radius: 5px; | |
| margin-bottom: 10px; | |
| } | |
| </style> | |
| """, unsafe_allow_html=True) | |
| # --- PROMPT --- | |
| prompt = """ | |
| je souhaite faire mon travail d'espagnol qui consiste à de l'analyse de documents iconographique. j'aimerais que tu le phase en respectant scrupuleusement la méthodologie suivante. j'aimerais que tu fasses ce travail en espagnol en donnant également la traduction française | |
| Metodología del comentario de un documento iconográfico | |
| Un documento iconográfico es un documento centrado en una imagen. Puede ser: una foto, un cuadro, una publicidad, un dibujo, un tebeo, una tira dibujada, una caricatura, etc. Su comentario respeta las etapas siguientes: la presentación, la descripción, el análisis y la conclusión. | |
| La presentación | |
| Se trata de resaltar los elementos esenciales para identificar el documento: | |
| El título (si existe) | |
| La naturaleza (si es una foto/dibujo/cuadro, en color o blanco y negro) | |
| El autor (el fotógrafo/el dibujante/el publicista...) | |
| La fuente (si existe) | |
| El tema evocado | |
| La descripción | |
| Se trata de decir lo que vemos. | |
| Dominar el vocabulario relativo a la imagen. | |
| Dominar el vocabulario de la situación en el espacio (arriba, abajo, delante, detrás, etc.) | |
| Conocer la organización interna de la descripción. | |
| ¿Qué debemos hacer concretamente? | |
| Determinar el número de planos o términos. | |
| (Ej: La imagen tiene dos planos/tres planos/un plan único) | |
| Hacer la descripción plano por plano y acabar antes de pasar al siguiente si hay más de un plano. | |
| Ej: en el primer plano vemos... | |
| Ordenar la descripción de cada plano ( a la derecha, a la izquierda, arriba, abajo, delante, detrás, en el centro, a lo lejos... | |
| ¿Qué se debe describir? | |
| Los protagonistas (los personajes): | |
| Los protagonistas | |
| Sexo, edad (hombre o mujer, joven o adulto) | |
| Las posturas (de pie, sentado, arrodillado, etc.) | |
| Los vestidos (ropas) | |
| Los rasgos físicos (color de pelo, gordo, flaco, etc.) | |
| Los rasgos sicológicos (triste, optimista, activo, pasivo, etc.) | |
| Las actitudes (está riendo, triste, llorando, contento, etc.) | |
| Las acciones (lo que están haciendo) | |
| Los objetos alrededor, los colores (fríos o cálidos), los contrastes... | |
| El análisis | |
| Interpretamos y comentamos los elementos de la descripción para comprender el mensaje del autor. | |
| La interpretación debe apoyarse en la descripción porque no se trata de un comentario libre. | |
| Empleamos fórmulas subjetivas porque expresamos hipótesis e impresiones. | |
| Ej: Cuando examinamos...podemos decir que.../ la postura de..., los vestidos...nos permiten imaginar que.../ lo que nos llama la atención es... porque/ los colores cálidos sugieren que... | |
| La conclusión | |
| Se trata de hacer un balance (resumen) de lo dicho de dar una impresión personal. Así: | |
| Anunciamos la conclusión: para concluir/ en suma/en conclusión... podemos decir que... | |
| Precisamos el medio de expresión utilizado: a través de esta foto/mediante este dibujo... | |
| Anunciamos la intención del autor: el dibujante quiere denunciar/ el fotógrafo pretende criticar/ el pintor quiere relevar, sensibilizar, mostrar. | |
| Dar la impresión personal: esta foto (no) me parece interesante/escandaloso/pertinente. | |
| Justificamos nuestra impresión: porque revela una realidad social/política/cultural... | |
| Un modelo: a través de este cuadro, el pintor quiere denunciar las injusticias sociales en África. El cuadro me parece interesante porque releva un fenómeno social recurrente que incita las autoridades a la responsabilidad. La propia imagen ilustra muy bien el tema de las injusticias entre ricos y ricos... | |
| """ | |
| # --- FONCTIONS --- | |
| def generate_response(image_path, question): | |
| """Génère une réponse au format texte brut à partir du modèle Gemini.""" | |
| try: | |
| image_data = Image.open(image_path) | |
| response = client.models.generate_content( | |
| model="gemini-2.5-flash-preview-04-17", | |
| contents=[image_data, prompt], | |
| config=types.GenerateContentConfig( | |
| thinking_config=types.ThinkingConfig( | |
| thinking_budget=8000 | |
| ) | |
| ), | |
| ) | |
| answer = response.candidates[0].content.parts[0].text | |
| return answer.strip() | |
| except Exception as e: | |
| st.error("Erreur lors de la génération de la réponse.") | |
| return None | |
| # --- APPLICATION PRINCIPALE --- | |
| def main(): | |
| st.markdown("<h1 class='title'>Mariam Espagnol( document iconographique seulement) 🇪🇸</h1>", unsafe_allow_html=True) | |
| # --- BARRE LATÉRALE --- | |
| with st.sidebar: | |
| st.markdown("<h2 class='subtitle'>Instructions</h2>", unsafe_allow_html=True) | |
| st.markdown(""" | |
| 1. **Téléchargez une image** que vous souhaitez analyser (PNG, JPG, JPEG). | |
| 2. L'application **générera une analyse** de l'image en espagnol et en français, en suivant la méthodologie fournie. | |
| """) | |
| # --- SECTION PRINCIPALE --- | |
| col1, col2 = st.columns([1, 2]) | |
| with col1: | |
| st.markdown("<h2 class='subtitle'>Télécharger une image</h2>", unsafe_allow_html=True) | |
| uploaded_file = st.file_uploader("", type=["png", "jpg", "jpeg"], label_visibility="collapsed") | |
| if uploaded_file is not None: | |
| with tempfile.NamedTemporaryFile(delete=False, suffix='.png') as tmp_file: | |
| tmp_file.write(uploaded_file.getvalue()) | |
| temp_image_path = tmp_file.name | |
| # Affichage de l'image | |
| image = Image.open(temp_image_path) | |
| st.image(image, use_container_width=True) | |
| with col2: | |
| if uploaded_file is not None: | |
| st.markdown("<h2 class='subtitle'>Analyse de l'image</h2>", unsafe_allow_html=True) | |
| question = "yusuf" # Question fixe pour l'instant | |
| if st.button("✨ Générer l'analyse ✨", type="primary"): | |
| with st.spinner("Analyse en cours..."): | |
| response = generate_response(temp_image_path, question) | |
| st.markdown(response) | |
| # --- EXÉCUTION --- | |
| if __name__ == "__main__": | |
| main() |