Carlexx commited on
Commit
639b7e9
·
verified ·
1 Parent(s): 678662b

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +45 -111
app.py CHANGED
@@ -3,13 +3,13 @@ import cv2
3
  import numpy as np
4
  from skimage.metrics import structural_similarity as ssim
5
  import matplotlib.pyplot as plt
6
- from PIL import Image, ImageDraw, ImageFont
7
  import imagehash
8
  import torch
9
  from scipy.stats import pearsonr
10
- import os
11
 
12
- # --- MÓDULOS DE ANÁLISE (CLIP E SALIÊNCIA) ---
 
13
  CLIP_AVAILABLE, SALIENCY_AVAILABLE = False, False
14
  try:
15
  from transformers import CLIPProcessor, CLIPModel
@@ -17,117 +17,57 @@ try:
17
  clip_model = CLIPModel.from_pretrained(MODEL_ID)
18
  clip_processor = CLIPProcessor.from_pretrained(MODEL_ID)
19
  CLIP_AVAILABLE = True
20
- print("Modelo CLIP carregado.")
21
  except Exception as e:
22
- print(f"Aviso CLIP: {e}")
23
 
24
  try:
25
- saliency = cv2.saliency.StaticSaliencySpectralResidual_create()
 
26
  SALIENCY_AVAILABLE = True
27
- print("Módulo de Saliência carregado.")
 
 
 
28
  except Exception as e:
29
- print(f"Aviso Saliência: {e}")
30
-
31
-
32
- # --- FUNÇÕES DE ANÁLISE CORE ---
33
- # (As funções de análise de fidelidade, foco e semântica permanecem as mesmas)
34
- def analisar_cor_iluminacao(frames, progress):
35
- """Executa o novo teste de consistência cromática e de iluminação."""
36
- lum_corr_scores, color_corr_scores = [], []
37
-
38
- progress(0.3, desc="Analisando cor e iluminação...")
39
- for i in range(len(frames) - 1):
40
- frame1 = frames[i]
41
- frame2 = frames[i+1]
42
-
43
- # 1. Análise de Luminância (Brilho)
44
- gray1 = cv2.cvtColor(frame1, cv2.COLOR_RGB2GRAY)
45
- gray2 = cv2.cvtColor(frame2, cv2.COLOR_RGB2GRAY)
46
- hist1_lum = cv2.calcHist([gray1], [0], None, [256], [0, 256])
47
- hist2_lum = cv2.calcHist([gray2], [0], None, [256], [0, 256])
48
- cv2.normalize(hist1_lum, hist1_lum, alpha=0, beta=1, norm_type=cv2.NORM_MINMAX)
49
- cv2.normalize(hist2_lum, hist2_lum, alpha=0, beta=1, norm_type=cv2.NORM_MINMAX)
50
- lum_corr = cv2.compareHist(hist1_lum, hist2_lum, cv2.HISTCMP_CORREL)
51
- lum_corr_scores.append(lum_corr)
52
-
53
- # 2. Análise de Cor (RGB)
54
- corr_r, corr_g, corr_b = 0, 0, 0
55
- for chan in range(3):
56
- hist1_color = cv2.calcHist([frame1], [chan], None, [256], [0, 256])
57
- hist2_color = cv2.calcHist([frame2], [chan], None, [256], [0, 256])
58
- cv2.normalize(hist1_color, hist1_color, alpha=0, beta=1, norm_type=cv2.NORM_MINMAX)
59
- cv2.normalize(hist2_color, hist2_color, alpha=0, beta=1, norm_type=cv2.NORM_MINMAX)
60
- if chan == 0: corr_r = cv2.compareHist(hist1_color, hist2_color, cv2.HISTCMP_CORREL)
61
- if chan == 1: corr_g = cv2.compareHist(hist1_color, hist2_color, cv2.HISTCMP_CORREL)
62
- if chan == 2: corr_b = cv2.compareHist(hist1_color, hist2_color, cv2.HISTCMP_CORREL)
63
-
64
- # Média da correlação dos 3 canais de cor
65
- avg_color_corr = (corr_r + corr_g + corr_b) / 3.0
66
- color_corr_scores.append(avg_color_corr)
67
-
68
- return lum_corr_scores, color_corr_scores
69
-
70
-
71
- # --- FUNÇÕES DE PLOTAGEM ADICIONAIS ---
72
- def gerar_grafico_cor(lum_scores, color_scores, num_frames, fps):
73
- x_axis_time = [i / fps for i in range(num_frames - 1)]
74
- fig, (ax1, ax2) = plt.subplots(2, 1, figsize=(16, 10), sharex=True)
75
- fig.suptitle('Análise de Consistência Cromática e de Iluminação', fontsize=16)
76
-
77
- ax1.plot(x_axis_time, color_scores, color='magenta', lw=2, label='Correlação de Cor (RGB)')
78
- ax1.set_ylabel('Correlação de Histograma')
79
- ax1.set_title('Consistência da Paleta de Cores da Cena')
80
- ax1.set_ylim(0, 1.05)
81
- ax1.grid(True, linestyle='--'); ax1.legend()
82
-
83
- ax2.plot(x_axis_time, lum_scores, color='gold', lw=2, label='Correlação de Luminância (Brilho)')
84
- ax2.set_ylabel('Correlação de Histograma')
85
- ax2.set_title('Consistência da Iluminação da Cena')
86
- ax2.set_xlabel('Tempo (segundos)')
87
- ax2.set_ylim(0, 1.05)
88
- ax2.grid(True, linestyle='--'); ax2.legend()
89
-
90
- plt.tight_layout(rect=[0, 0.03, 1, 0.95])
91
- path = 'analise_cor_luz.png'
92
- plt.savefig(path)
93
- plt.close()
94
- return path
95
 
 
 
 
 
 
96
 
97
  # --- FUNÇÃO DE CALLBACK PRINCIPAL ---
98
  def run_full_analysis(video_path, descriptions_text, progress=gr.Progress()):
99
- if video_path is None: raise gr.Error("Faça o upload de um vídeo.")
100
 
101
- # Análise de Fidelidade
 
102
  frames, fps, ssim_scores, phash_distances = analisar_fidelidade(video_path, progress)
103
- fidelidade_plot = gerar_grafico_fidelidade_plot(ssim_scores, phash_distances, len(frames), fps)
104
- timeline_path = gerar_timeline_visual(frames, len(frames), fps)
105
 
106
- # Análise de Cor e Iluminação
107
- lum_scores, color_scores = analisar_cor_iluminacao(frames, progress)
108
- cor_plot_path = gerar_grafico_cor(lum_scores, color_scores, len(frames), fps)
 
 
 
109
 
110
- # Análise de Foco Móvel
111
- foco_plot_path = None
112
  if SALIENCY_AVAILABLE:
 
113
  ssim_foco, jitter_foco = analisar_estabilidade_foco(frames, progress)
114
  foco_plot_path = gerar_grafico_foco(ssim_scores, ssim_foco, jitter_foco, len(frames), fps)
115
 
116
- # Análise Semântica
117
- semantico_path = None
118
  if CLIP_AVAILABLE and descriptions_text.strip():
119
  progress(0.8, desc="Executando teste semântico...")
120
  semantico_path, error_msg = executar_teste_semantico(phash_distances, descriptions_text)
121
  if error_msg: gr.Warning(error_msg)
122
 
123
- state_data = {"frames": frames, "fps": fps, "ssim_scores": ssim_scores, "phash_distances": phash_distances}
124
-
125
- return fidelidade_plot, timeline_path, semantico_path, foco_plot_path, cor_plot_path, state_data, None, None, ""
126
 
127
- # --- INTERFACE GRADIO COMPLETA ---
128
  with gr.Blocks(theme=gr.themes.Soft()) as demo:
129
  gr.Markdown("# Suíte de Validação Completa para Geração de Vídeo (ADUC-SDR)")
130
- shared_state = gr.State(value={})
131
 
132
  with gr.Row():
133
  with gr.Column(scale=1):
@@ -136,34 +76,28 @@ with gr.Blocks(theme=gr.themes.Soft()) as demo:
136
  analyze_button = gr.Button("3. Executar Análise Completa", variant="primary")
137
 
138
  with gr.Tabs():
139
- with gr.TabItem("1. Análise Principal e Diagnóstico"):
140
- plot_fidelidade = gr.Plot(label="Gráfico de Análise de Fidelidade (Clique para inspecionar)")
141
- with gr.Row():
142
- frame_antes = gr.Image(label="Frame Antes")
143
- frame_depois = gr.Image(label="Frame Depois")
144
- info_box = gr.Textbox(label="Dados do Ponto Selecionado")
145
- timeline_output = gr.Image(label="Timeline Visual", interactive=False)
146
-
147
- with gr.TabItem("2. Análise de Cor e Iluminação"):
148
- gr.Markdown("### Teste de Consistência Cromática e de Iluminação")
149
  plot_cor = gr.Image(label="Gráfico de Análise de Cor e Luminância")
150
-
151
- with gr.TabItem("3. Análise para Vídeo Móvel"):
152
- gr.Markdown("### Teste de Estabilidade de Foco")
153
  plot_foco = gr.Image(label="Gráfico de Análise de Foco e Jitter")
 
 
 
154
 
155
- with gr.TabItem("4. Teste de Inteligência Adaptativa"):
156
- gr.Markdown("### Validação da Decisão Adaptativa")
157
  plot_semantico = gr.Image(label="Gráfico de Estresse Semântico")
158
 
159
- # --- Lógica de Eventos ---
 
160
  analyze_button.click(
161
  fn=run_full_analysis,
162
  inputs=[video_input, descriptions_input],
163
- outputs=[plot_fidelidade, timeline_output, plot_semantico, plot_foco, plot_cor, shared_state, frame_antes, frame_depois, info_box]
164
  )
165
- plot_fidelidade.select(
166
- fn=inspect_transition,
167
- inputs=[shared_state],
168
- outputs=[frame_antes, frame_depois, info_box]
169
- )
 
3
  import numpy as np
4
  from skimage.metrics import structural_similarity as ssim
5
  import matplotlib.pyplot as plt
6
+ from PIL import Image
7
  import imagehash
8
  import torch
9
  from scipy.stats import pearsonr
 
10
 
11
+ # --- MÓDULO DE INICIALIZAÇÃO ---
12
+ # Tenta carregar os modelos e módulos, definindo flags de disponibilidade.
13
  CLIP_AVAILABLE, SALIENCY_AVAILABLE = False, False
14
  try:
15
  from transformers import CLIPProcessor, CLIPModel
 
17
  clip_model = CLIPModel.from_pretrained(MODEL_ID)
18
  clip_processor = CLIPProcessor.from_pretrained(MODEL_ID)
19
  CLIP_AVAILABLE = True
20
+ print("Modelo CLIP carregado com sucesso.")
21
  except Exception as e:
22
+ print(f"AVISO: Modelo CLIP não carregado. Teste de Inteligência desabilitado. Erro: {e}")
23
 
24
  try:
25
+ # A instalação de 'opencv-contrib-python-headless' deve resolver isso.
26
+ saliency_detector = cv2.saliency.StaticSaliencySpectralResidual_create()
27
  SALIENCY_AVAILABLE = True
28
+ print("Módulo de Saliência carregado com sucesso.")
29
+ except AttributeError:
30
+ print("AVISO: Módulo de Saliência não encontrado. Análise de Foco Móvel desabilitada.")
31
+ print("Certifique-se de que 'opencv-contrib-python-headless' está no requirements.txt")
32
  except Exception as e:
33
+ print(f"AVISO: Módulo de Saliência não carregado. Erro: {e}")
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
34
 
35
+ # --- FUNÇÕES DE ANÁLISE E PLOTAGEM ---
36
+ # (Cole aqui TODAS as suas funções de análise e plotagem que já funcionavam.
37
+ # analisar_fidelidade, analisar_cor_iluminacao, analisar_anomalias_movimento,
38
+ # executar_teste_semantico, etc.)
39
+ # ...
40
 
41
  # --- FUNÇÃO DE CALLBACK PRINCIPAL ---
42
  def run_full_analysis(video_path, descriptions_text, progress=gr.Progress()):
43
+ if video_path is None: raise gr.Error("Por favor, faça o upload de um vídeo.")
44
 
45
+ # Executa as análises principais que sempre funcionam
46
+ progress(0, desc="Analisando fidelidade...")
47
  frames, fps, ssim_scores, phash_distances = analisar_fidelidade(video_path, progress)
 
 
48
 
49
+ fidelidade_plot_path = gerar_grafico_fidelidade(ssim_scores, phash_distances, len(frames), fps)
50
+ cor_plot_path = gerar_grafico_cor_luz(ssim_scores, phash_distances, len(frames), fps) # Supondo que você tenha essa função
51
+ anomalias_plot_path = gerar_grafico_anomalias(ssim_scores, phash_distances, len(frames), fps) # Supondo que você tenha essa função
52
+
53
+ # Executa análises opcionais apenas se os módulos estiverem disponíveis
54
+ foco_plot_path, semantico_path = None, None
55
 
 
 
56
  if SALIENCY_AVAILABLE:
57
+ progress(0.6, desc="Analisando foco móvel...")
58
  ssim_foco, jitter_foco = analisar_estabilidade_foco(frames, progress)
59
  foco_plot_path = gerar_grafico_foco(ssim_scores, ssim_foco, jitter_foco, len(frames), fps)
60
 
 
 
61
  if CLIP_AVAILABLE and descriptions_text.strip():
62
  progress(0.8, desc="Executando teste semântico...")
63
  semantico_path, error_msg = executar_teste_semantico(phash_distances, descriptions_text)
64
  if error_msg: gr.Warning(error_msg)
65
 
66
+ return fidelidade_plot_path, cor_plot_path, foco_plot_path, semantico_path, anomalias_plot_path
 
 
67
 
68
+ # --- INTERFACE GRADIO ---
69
  with gr.Blocks(theme=gr.themes.Soft()) as demo:
70
  gr.Markdown("# Suíte de Validação Completa para Geração de Vídeo (ADUC-SDR)")
 
71
 
72
  with gr.Row():
73
  with gr.Column(scale=1):
 
76
  analyze_button = gr.Button("3. Executar Análise Completa", variant="primary")
77
 
78
  with gr.Tabs():
79
+ with gr.TabItem("1. Fidelidade e Coerência"):
80
+ plot_fidelidade = gr.Image(label="Gráfico de Análise de Fidelidade (SSIM e pHash)")
81
+
82
+ with gr.TabItem("2. Cor e Iluminação"):
 
 
 
 
 
 
83
  plot_cor = gr.Image(label="Gráfico de Análise de Cor e Luminância")
84
+
85
+ with gr.TabItem("3. Foco (Vídeo Móvel)"):
 
86
  plot_foco = gr.Image(label="Gráfico de Análise de Foco e Jitter")
87
+
88
+ with gr.TabItem("4. Glitches de Movimento"):
89
+ plot_anomalias = gr.Image(label="Gráfico do Detector de Anomalias de Movimento")
90
 
91
+ with gr.TabItem("5. Inteligência Adaptativa"):
 
92
  plot_semantico = gr.Image(label="Gráfico de Estresse Semântico")
93
 
94
+ # A interatividade foi removida para garantir que o app inicie
95
+ # O callback do botão agora é mais simples
96
  analyze_button.click(
97
  fn=run_full_analysis,
98
  inputs=[video_input, descriptions_input],
99
+ outputs=[plot_fidelidade, plot_cor, plot_foco, plot_semantico, plot_anomalias]
100
  )
101
+
102
+ if __name__ == "__main__":
103
+ demo.queue().launch(share=True)