deepguess commited on
Commit
4d969fb
Β·
1 Parent(s): b56943b
Files changed (2) hide show
  1. app.py +325 -0
  2. requirements.txt +7 -0
app.py CHANGED
@@ -5,3 +5,328 @@ def greet(name):
5
 
6
  demo = gr.Interface(fn=greet, inputs="text", outputs="text")
7
  demo.launch()
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
5
 
6
  demo = gr.Interface(fn=greet, inputs="text", outputs="text")
7
  demo.launch()
8
+ import gradio as gr
9
+ import spaces
10
+ import torch
11
+ from transformers import Qwen2_5_VLForConditionalGeneration, AutoProcessor
12
+ import os
13
+ from datetime import datetime
14
+
15
+ # Model setup
16
+ processor = AutoProcessor.from_pretrained("deepguess/Qwen2.5-VL-7B-Meteorology", trust_remote_code=True)
17
+ model = Qwen2_5_VLForConditionalGeneration.from_pretrained(
18
+ "deepguess/Qwen2.5-VL-7B-Meteorology",
19
+ torch_dtype=torch.float16,
20
+ trust_remote_code=True
21
+ )
22
+ model.eval()
23
+
24
+ # Title and description
25
+ TITLE = "🌦️ Weather Analysis VLM (Qwen2.5-VL-7B Fine-tuned)"
26
+
27
+ DESCRIPTION = """
28
+ ## Advanced Weather Image Analysis
29
+
30
+ This model specializes in analyzing weather data including:
31
+ - **Model Outputs**: GFS, HRRR, ECMWF, NAM analysis
32
+ - **Soundings**: Skew-T diagrams, hodographs, SHARPpy analysis
33
+ - **Observations**: Surface obs, satellite, radar imagery
34
+ - **Forecasts**: Deterministic and ensemble model outputs
35
+ - **Severe Weather**: Convective parameters, SPC outlooks
36
+
37
+ ### ⚠️ Disclaimer
38
+ **For educational and research purposes only. Not for operational forecasting.**
39
+ """
40
+
41
+ # Enhanced prompts based on your data categories
42
+ PROMPT_TEMPLATES = {
43
+ "Quick Analysis": "Describe the weather in this image.",
44
+ "Model Output": "Analyze this model output. What patterns and features are shown?",
45
+ "Sounding Analysis": "Analyze this sounding. Discuss stability, shear, and severe potential.",
46
+ "Radar/Satellite": "Describe the features in this radar or satellite image.",
47
+ "Severe Weather": "Assess severe weather potential based on this image.",
48
+ "Technical Deep Dive": "Provide detailed technical analysis including parameters and meteorological significance.",
49
+ "Forecast Discussion": "Based on this image, what weather evolution is expected?",
50
+ "Pattern Recognition": "Identify synoptic patterns, jet streaks, troughs, ridges, and fronts.",
51
+ "Ensemble Analysis": "Analyze ensemble spread, uncertainty, and most likely scenarios.",
52
+ "Winter Weather": "Analyze precipitation type, accumulation potential, and impacts.",
53
+ }
54
+
55
+ # System prompts for different analysis modes
56
+ SYSTEM_PROMPTS = {
57
+ "technical": """You are an expert meteorologist providing technical analysis. Focus on:
58
+ - Specific parameter values and thresholds
59
+ - Physical processes and dynamics
60
+ - Pattern recognition and anomalies
61
+ - Forecast confidence and uncertainty
62
+ Use technical terminology appropriately.""",
63
+
64
+ "educational": """You are a meteorology instructor. Explain concepts clearly while maintaining accuracy.
65
+ Point out key features and explain their significance. Use some technical terms but define them.""",
66
+
67
+ "operational": """You are providing a weather briefing. Focus on:
68
+ - Current conditions and trends
69
+ - Expected evolution
70
+ - Impacts and hazards
71
+ - Timing of changes
72
+ Be concise but thorough.""",
73
+
74
+ "research": """You are analyzing meteorological data for research purposes. Discuss:
75
+ - Interesting features or anomalies
76
+ - Comparison to climatology
77
+ - Physical mechanisms
78
+ - Uncertainty quantification"""
79
+ }
80
+
81
+ # Analysis mode descriptions
82
+ MODE_INFO = {
83
+ "technical": "Detailed technical analysis for meteorologists",
84
+ "educational": "Clear explanations for learning",
85
+ "operational": "Focused briefing style",
86
+ "research": "In-depth research perspective"
87
+ }
88
+
89
+ @spaces.GPU(duration=90)
90
+ def analyze_weather_image(image, analysis_type, custom_prompt, analysis_mode, temperature, max_tokens, top_p):
91
+ if image is None:
92
+ return "Please upload an image to analyze."
93
+
94
+ # Move model to GPU
95
+ model.cuda()
96
+
97
+ # Use custom prompt if provided, otherwise use template
98
+ prompt = custom_prompt.strip() if custom_prompt.strip() else PROMPT_TEMPLATES.get(analysis_type, PROMPT_TEMPLATES["Quick Analysis"])
99
+
100
+ # Select system prompt based on mode
101
+ system_content = SYSTEM_PROMPTS.get(analysis_mode, SYSTEM_PROMPTS["technical"])
102
+
103
+ # Prepare messages
104
+ messages = [{
105
+ "role": "system",
106
+ "content": system_content
107
+ }, {
108
+ "role": "user",
109
+ "content": [
110
+ {"type": "text", "text": prompt},
111
+ {"type": "image", "image": image}
112
+ ]
113
+ }]
114
+
115
+ # Process inputs
116
+ text = processor.apply_chat_template(messages, tokenize=False, add_generation_prompt=True)
117
+ inputs = processor(text=[text], images=[image], return_tensors="pt").to("cuda")
118
+
119
+ # Generate with specified parameters
120
+ outputs = model.generate(
121
+ **inputs,
122
+ max_new_tokens=max_tokens,
123
+ temperature=temperature,
124
+ do_sample=True,
125
+ top_p=top_p,
126
+ repetition_penalty=1.05
127
+ )
128
+
129
+ # Decode response
130
+ response = processor.batch_decode(outputs[:, inputs.input_ids.shape[1]:], skip_special_tokens=True)[0]
131
+
132
+ # Add metadata
133
+ timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S UTC")
134
+ metadata = f"\n\n---\n*Analysis completed: {timestamp} | Mode: {analysis_mode} | Type: {analysis_type}*"
135
+
136
+ return response + metadata
137
+
138
+ # Create Gradio interface
139
+ with gr.Blocks(title=TITLE, theme=gr.themes.Base(), css="""
140
+ .gradio-container { font-family: 'Monaco', 'Menlo', 'Ubuntu Mono', monospace; }
141
+ .markdown-text { font-size: 14px; }
142
+ #analysis-output { font-family: 'Monaco', 'Menlo', monospace; font-size: 13px; }
143
+ .gr-button-primary { background-color: #2563eb; }
144
+ .gr-button-primary:hover { background-color: #1e40af; }
145
+ """) as demo:
146
+ gr.Markdown(f"# {TITLE}")
147
+ gr.Markdown(DESCRIPTION)
148
+
149
+ with gr.Row():
150
+ with gr.Column(scale=1):
151
+ # Image input
152
+ image_input = gr.Image(
153
+ label="Upload Weather Image",
154
+ type="pil",
155
+ elem_id="image-upload"
156
+ )
157
+
158
+ # Analysis type selector
159
+ analysis_type = gr.Dropdown(
160
+ label="Analysis Type",
161
+ choices=list(PROMPT_TEMPLATES.keys()),
162
+ value="Quick Analysis",
163
+ info="Select the type of analysis you need"
164
+ )
165
+
166
+ # Analysis mode selector
167
+ analysis_mode = gr.Radio(
168
+ label="Analysis Mode",
169
+ choices=list(MODE_INFO.keys()),
170
+ value="technical",
171
+ info="Choose the style and depth of analysis"
172
+ )
173
+
174
+ # Mode description
175
+ mode_description = gr.Markdown(value=MODE_INFO["technical"], elem_id="mode-desc")
176
+
177
+ # Custom prompt option
178
+ with gr.Accordion("Custom Prompt (Optional)", open=False):
179
+ custom_prompt = gr.Textbox(
180
+ label="Enter your specific question or analysis request",
181
+ placeholder="E.g., 'Focus on the 500mb vorticity patterns' or 'Explain the hodograph curvature'",
182
+ lines=3
183
+ )
184
+
185
+ # Advanced settings
186
+ with gr.Accordion("Advanced Settings", open=False):
187
+ with gr.Row():
188
+ temperature = gr.Slider(
189
+ minimum=0.1,
190
+ maximum=1.0,
191
+ value=0.7,
192
+ step=0.05,
193
+ label="Temperature",
194
+ info="Lower = more focused, Higher = more varied"
195
+ )
196
+
197
+ top_p = gr.Slider(
198
+ minimum=0.5,
199
+ maximum=1.0,
200
+ value=0.95,
201
+ step=0.05,
202
+ label="Top-p",
203
+ info="Nucleus sampling threshold"
204
+ )
205
+
206
+ max_tokens = gr.Slider(
207
+ minimum=128,
208
+ maximum=1024,
209
+ value=512,
210
+ step=64,
211
+ label="Max Output Length",
212
+ info="Longer for detailed analysis"
213
+ )
214
+
215
+ # Analyze button
216
+ analyze_btn = gr.Button("πŸ” Analyze Weather", variant="primary", size="lg")
217
+
218
+ with gr.Column(scale=1):
219
+ # Output area
220
+ output = gr.Textbox(
221
+ label="Analysis Results",
222
+ lines=25,
223
+ max_lines=30,
224
+ show_copy_button=True,
225
+ elem_id="analysis-output"
226
+ )
227
+
228
+ # Common weather data categories for quick access
229
+ with gr.Accordion("πŸ“Š Quick Templates for Common Data Types", open=False):
230
+ gr.Markdown("""
231
+ ### Click to load analysis templates:
232
+ """)
233
+ with gr.Row():
234
+ gr.Button("500mb Analysis", size="sm").click(
235
+ lambda: "Analyze the 500mb height and wind patterns. Identify troughs, ridges, jet streaks, and vorticity.",
236
+ outputs=custom_prompt
237
+ )
238
+ gr.Button("Sounding Analysis", size="sm").click(
239
+ lambda: "Analyze this sounding for stability, CAPE, shear, LCL, LFC, and severe weather parameters.",
240
+ outputs=custom_prompt
241
+ )
242
+ gr.Button("Composite Reflectivity", size="sm").click(
243
+ lambda: "Analyze radar reflectivity patterns, storm structure, intensity, and movement.",
244
+ outputs=custom_prompt
245
+ )
246
+ with gr.Row():
247
+ gr.Button("Surface Analysis", size="sm").click(
248
+ lambda: "Analyze surface features including fronts, pressure centers, convergence, and boundaries.",
249
+ outputs=custom_prompt
250
+ )
251
+ gr.Button("Ensemble Spread", size="sm").click(
252
+ lambda: "Analyze ensemble spread, clustering, and probabilistic information.",
253
+ outputs=custom_prompt
254
+ )
255
+ gr.Button("Convective Parameters", size="sm").click(
256
+ lambda: "Analyze CAPE, CIN, SRH, bulk shear, and composite parameters for severe potential.",
257
+ outputs=custom_prompt
258
+ )
259
+
260
+ # Examples section
261
+ example_data = [
262
+ ["examples/500mb_heights.jpg", "Model Output", "technical", 0.7, 512],
263
+ ["examples/sounding.jpg", "Sounding Analysis", "educational", 0.7, 512],
264
+ ["examples/radar_composite.jpg", "Radar/Satellite", "operational", 0.7, 384],
265
+ ["examples/spc_outlook.jpg", "Severe Weather", "operational", 0.7, 512],
266
+ ["examples/ensemble_spaghetti.jpg", "Ensemble Analysis", "research", 0.8, 640],
267
+ ] if os.path.exists("examples") else []
268
+
269
+ if example_data:
270
+ gr.Examples(
271
+ examples=example_data,
272
+ inputs=[image_input, analysis_type, analysis_mode, temperature, max_tokens],
273
+ outputs=output,
274
+ fn=lambda img, typ, mode, temp, tok: analyze_weather_image(img, typ, "", mode, temp, tok, 0.95),
275
+ cache_examples=False,
276
+ label="Example Analyses"
277
+ )
278
+
279
+ # Tips section
280
+ with gr.Accordion("πŸ’‘ Pro Tips for Best Results", open=False):
281
+ gr.Markdown("""
282
+ ### Image Guidelines:
283
+ - **Resolution**: Higher resolution images yield better analysis
284
+ - **Clarity**: Ensure text/contours are legible
285
+ - **Completeness**: Include colorbars, titles, valid times
286
+
287
+ ### Analysis Tips by Data Type:
288
+
289
+ **Model Output (GFS, HRRR, ECMWF, NAM):**
290
+ - Include initialization and valid times
291
+ - Specify if you want focus on particular features
292
+ - Ask about ensemble uncertainty if applicable
293
+
294
+ **Soundings (Skew-T, Hodographs):**
295
+ - Ensure all parameters are visible
296
+ - Ask about specific levels or layers
297
+ - Request shear calculations or thermodynamic analysis
298
+
299
+ **Radar/Satellite:**
300
+ - Include timestamp and location
301
+ - Specify interest in particular features
302
+ - Ask about storm motion or development
303
+
304
+ **Surface/Upper Air Charts:**
305
+ - Ensure contours and labels are clear
306
+ - Ask about specific features or patterns
307
+ - Request frontal analysis or jet stream discussion
308
+
309
+ ### Parameter Settings:
310
+ - **Temperature 0.3-0.5**: Factual, consistent analysis
311
+ - **Temperature 0.6-0.8**: Balanced analysis with some interpretation
312
+ - **Temperature 0.9-1.0**: More speculative, exploring possibilities
313
+ - **Max Tokens**: Use 256-384 for quick analysis, 512-768 for detailed
314
+ """)
315
+
316
+ # Update mode description when mode changes
317
+ analysis_mode.change(
318
+ lambda mode: MODE_INFO[mode],
319
+ inputs=analysis_mode,
320
+ outputs=mode_description
321
+ )
322
+
323
+ # Set up event handler
324
+ analyze_btn.click(
325
+ fn=analyze_weather_image,
326
+ inputs=[image_input, analysis_type, custom_prompt, analysis_mode, temperature, max_tokens, top_p],
327
+ outputs=output
328
+ )
329
+
330
+ # Launch the app
331
+ if __name__ == "__main__":
332
+ demo.launch()
requirements.txt ADDED
@@ -0,0 +1,7 @@
 
 
 
 
 
 
 
 
1
+
2
+ transformers
3
+ torch
4
+ torchvision
5
+ Pillow
6
+
7
+