rU-ShawJI-07 commited on
Commit
1f1baf3
·
verified ·
1 Parent(s): 445aec6

Update image.py

Browse files
Files changed (1) hide show
  1. image.py +52 -97
image.py CHANGED
@@ -1,4 +1,3 @@
1
- # image.py
2
  import gradio as gr
3
  import sympy as sp
4
  from pix2text import Pix2Text
@@ -25,50 +24,47 @@ except Exception as e:
25
  p2t_model = None
26
 
27
  def clean_latex_expression(latex_str):
28
- """Clean and normalize LaTeX expression for better parsing"""
29
  if not latex_str:
30
  return ""
31
 
32
- # Remove common LaTeX artifacts
33
  latex_str = latex_str.strip()
 
34
  latex_str = re.sub(r'\\[a-zA-Z]+\{([^}]*)\}', r'\1', latex_str) # Remove LaTeX commands
35
- latex_str = re.sub(r'\\\\', r'\\', latex_str) # Fix double backslashes
36
  latex_str = re.sub(r'\s+', ' ', latex_str) # Normalize whitespace
37
-
38
- return latex_str
 
 
 
39
 
40
  def parse_equation_type(latex_str):
41
  """Determine if the equation is polynomial or linear system"""
42
  try:
43
- # Clean the latex string
44
  cleaned = clean_latex_expression(latex_str)
45
-
46
- # Check if it contains system indicators
47
- if '\\\\' in cleaned or '\n' in cleaned or 'system' in cleaned.lower():
48
  return 'linear_system'
49
 
50
- # Check for polynomial indicators
51
- if 'x^' in cleaned or '^' in cleaned:
 
 
 
 
 
 
 
 
 
 
 
 
 
 
52
  return 'polynomial'
53
-
54
- # Check for linear equation indicators
55
- if ('x' in cleaned and 'y' in cleaned) or ('=' in cleaned and any(op in cleaned for op in ['+', '-'])):
56
- # Could be either, try to parse as polynomial first
57
- try:
58
- expr = sp.sympify(cleaned.split('=')[0] if '=' in cleaned else cleaned)
59
- if x in expr.free_symbols:
60
- degree = sp.degree(expr, x)
61
- if degree > 1:
62
- return 'polynomial'
63
- elif degree == 1 and y in expr.free_symbols:
64
- return 'linear_system'
65
- else:
66
- return 'polynomial'
67
- except:
68
- pass
69
-
70
- return 'polynomial' # Default fallback
71
-
72
  except Exception as e:
73
  logger.error(f"Error determining equation type: {e}")
74
  return 'polynomial'
@@ -76,19 +72,19 @@ def parse_equation_type(latex_str):
76
  def extract_polynomial_coefficients(latex_str):
77
  """Extract polynomial coefficients from LaTeX string"""
78
  try:
79
- # Clean and parse the expression
80
  cleaned = clean_latex_expression(latex_str)
81
- if '=' in cleaned:
82
- cleaned = cleaned.split('=')[0].strip()
83
-
84
- # Try to parse with SymPy
85
- expr = sp.sympify(cleaned)
86
 
 
 
87
  if x not in expr.free_symbols:
88
  raise ValueError("No variable x found in expression")
89
 
90
  # Get polynomial degree
91
  degree = sp.degree(expr, x)
 
 
92
 
93
  # Extract coefficients
94
  poly = sp.Poly(expr, x)
@@ -101,13 +97,12 @@ def extract_polynomial_coefficients(latex_str):
101
  "latex": latex_str,
102
  "success": True
103
  }
104
-
105
  except Exception as e:
106
  logger.error(f"Error extracting polynomial coefficients: {e}")
107
  return {
108
  "type": "polynomial",
109
  "degree": 2,
110
- "coeffs": "1 0 0", # Default quadratic
111
  "latex": latex_str,
112
  "success": False,
113
  "error": str(e)
@@ -116,13 +111,9 @@ def extract_polynomial_coefficients(latex_str):
116
  def extract_linear_system_coefficients(latex_str):
117
  """Extract linear system coefficients from LaTeX string"""
118
  try:
119
- # Clean and split equations
120
  cleaned = clean_latex_expression(latex_str)
121
-
122
- # Split by common separators
123
  equations = re.split(r'\\\\|\n|;', cleaned)
124
  if len(equations) < 2:
125
- # Try to detect two equations in one line
126
  equations = re.split(r'(?<=[0-9])\s*(?=[+-]?\s*[0-9]*[xy])', cleaned)
127
 
128
  if len(equations) < 2:
@@ -131,16 +122,14 @@ def extract_linear_system_coefficients(latex_str):
131
  eq1_str = equations[0].strip()
132
  eq2_str = equations[1].strip()
133
 
134
- # Parse each equation
135
  def parse_linear_eq(eq_str):
136
  # Convert to standard form ax + by = c
137
- if '=' not in eq_str:
138
- raise ValueError("No equals sign found")
139
 
140
- left, right = eq_str.split('=')
141
- expr = sp.sympify(left) - sp.sympify(right)
142
 
143
- # Extract coefficients
144
  a = float(expr.coeff(x, 1)) if expr.coeff(x, 1) else 0
145
  b = float(expr.coeff(y, 1)) if expr.coeff(y, 1) else 0
146
  c = float(-expr.as_coefficients_dict()[1]) if 1 in expr.as_coefficients_dict() else 0
@@ -157,12 +146,11 @@ def extract_linear_system_coefficients(latex_str):
157
  "latex": latex_str,
158
  "success": True
159
  }
160
-
161
  except Exception as e:
162
  logger.error(f"Error extracting linear system coefficients: {e}")
163
  return {
164
  "type": "linear",
165
- "eq1_coeffs": "1 1 3", # Default system
166
  "eq2_coeffs": "1 -1 1",
167
  "latex": latex_str,
168
  "success": False,
@@ -170,7 +158,7 @@ def extract_linear_system_coefficients(latex_str):
170
  }
171
 
172
  def extract_equation_from_image(image_file):
173
- """Extract equation from image using Pix2Text with improved error handling"""
174
  try:
175
  if p2t_model is None:
176
  return {
@@ -192,15 +180,12 @@ def extract_equation_from_image(image_file):
192
  else:
193
  image = Image.open(image_file.name)
194
 
195
- # Convert to RGB if needed
196
  if image.mode != 'RGB':
197
  image = image.convert('RGB')
198
 
199
  logger.info(f"Processing image of size: {image.size}")
200
 
201
- # Extract text and formulas using Pix2Text
202
  result = p2t_model.recognize_text_formula(image)
203
-
204
  if not result or result.strip() == "":
205
  return {
206
  "type": "error",
@@ -210,14 +195,11 @@ def extract_equation_from_image(image_file):
210
 
211
  logger.info(f"Extracted text: {result}")
212
 
213
- # Determine equation type
214
  eq_type = parse_equation_type(result)
215
-
216
  if eq_type == 'polynomial':
217
  return extract_polynomial_coefficients(result)
218
  else:
219
  return extract_linear_system_coefficients(result)
220
-
221
  except Exception as e:
222
  logger.error(f"Error processing image: {e}")
223
  return {
@@ -226,9 +208,8 @@ def extract_equation_from_image(image_file):
226
  "success": False
227
  }
228
 
229
- # Import solve functions from other modules
230
  def solve_polynomial(degree, coeff_string, real_only):
231
- """Solve polynomial equation (imported from polynomial.py logic)"""
232
  try:
233
  coeffs = list(map(float, coeff_string.strip().split()))
234
  if len(coeffs) != degree + 1:
@@ -247,13 +228,13 @@ def solve_polynomial(degree, coeff_string, real_only):
247
  ) + "\n$$"
248
 
249
  steps_output = f"""
250
- ### 🧐 Polynomial Expression
251
  $$ {sp.latex(poly)} = 0 $$
252
- ### ✏️ Simplified
253
  $$ {sp.latex(simplified)} = 0 $$
254
- ### 🤩 Factored
255
  $$ {sp.latex(factored)} = 0 $$
256
- ### 🥮 Roots {'(Only Real)' if real_only else '(All Roots)'}
257
  {roots_output}
258
  """
259
 
@@ -265,7 +246,7 @@ $$ {sp.latex(factored)} = 0 $$
265
  ax.axhline(0, color='black', linewidth=0.5)
266
  ax.axvline(0, color='black', linewidth=0.5)
267
  ax.grid(True)
268
- ax.set_title("📈 Graph of the Polynomial")
269
  ax.set_xlabel("x")
270
  ax.set_ylabel("f(x)")
271
  ax.legend()
@@ -275,7 +256,7 @@ $$ {sp.latex(factored)} = 0 $$
275
  return f"❌ Error: {e}", None, ""
276
 
277
  def solve_linear_system_from_coeffs(eq1_str, eq2_str):
278
- """Solve linear system (imported from linear.py logic)"""
279
  try:
280
  coeffs1 = list(map(float, eq1_str.strip().split()))
281
  coeffs2 = list(map(float, eq2_str.strip().split()))
@@ -297,7 +278,7 @@ def solve_linear_system_from_coeffs(eq1_str, eq2_str):
297
  eq_latex = f"$$ {sp.latex(eq1)} \\ {sp.latex(eq2)} $$"
298
 
299
  steps = rf"""
300
- ### 📌 Step-by-step Solution
301
  1. **Original Equations:**
302
  $$ {sp.latex(eq1)} $$
303
  $$ {sp.latex(eq2)} $$
@@ -323,7 +304,7 @@ def solve_linear_system_from_coeffs(eq1_str, eq2_str):
323
  ax.axhline(0, color='black', linewidth=0.5)
324
  ax.axvline(0, color='black', linewidth=0.5)
325
  ax.legend()
326
- ax.set_title("📊 Graph of the Equations")
327
  ax.grid(True)
328
 
329
  return eq_latex, steps, fig, ""
@@ -340,50 +321,36 @@ def solve_extracted_equation(eq_data, real_only):
340
  return "❌ Unknown equation type", None, ""
341
 
342
  def image_tab():
343
- """Create the Image Upload Solver tab with improved functionality"""
344
- with gr.Tab("📷 Image Upload Solver"):
345
- gr.Markdown("## 📷 Solve Equations from Image")
346
 
347
  with gr.Row():
348
- # File input for uploading images
349
  image_input = gr.File(
350
  label="Upload Question Image",
351
  file_types=[".pdf", ".png", ".jpg", ".jpeg"],
352
  file_count="single"
353
  )
354
- # Button to trigger image processing
355
  image_upload_btn = gr.Button("📤 Process Image")
356
 
357
  gr.Markdown("**Supported Formats:** .pdf, .png, .jpg, .jpeg")
358
 
359
  with gr.Row():
360
- # Checkbox to toggle real roots only for polynomials
361
  real_image_checkbox = gr.Checkbox(label="Show Only Real Roots (for Polynomials)", value=False)
362
- # Button to preview the extracted equation
363
  preview_image_btn = gr.Button("🔍 Preview Equation")
364
 
365
- # Markdown component to display the extracted equation
366
  image_equation_display = gr.Markdown()
367
 
368
  with gr.Row():
369
- # Button to confirm and display the solution (initially hidden)
370
  confirm_image_btn = gr.Button("✅ Display Solution", visible=False)
371
- # Button to edit the equation manually (initially hidden)
372
  edit_image_btn = gr.Button("✏️ Make Changes Manually", visible=False)
373
 
374
- # Textbox for manual LaTeX editing (initially hidden)
375
  edit_latex_input = gr.Textbox(label="Edit LaTeX Equation", visible=False, lines=3)
376
- # Button to save manual changes (initially hidden)
377
  save_edit_btn = gr.Button("💾 Save Changes", visible=False)
378
 
379
- # Markdown component to display solution steps
380
  image_steps_md = gr.Markdown()
381
- # Plot component to display the graph
382
  image_plot_output = gr.Plot()
383
- # Textbox to display errors
384
  image_error_box = gr.Textbox(label="Status", visible=True, interactive=False)
385
-
386
- # State to store the extracted equation data
387
  extracted_eq_state = gr.State()
388
 
389
  def handle_image_upload(image_file):
@@ -402,7 +369,6 @@ def image_tab():
402
  except Exception as e:
403
  return f"❌ Error processing image: {str(e)}", None, "", None, None
404
 
405
- # Event handler for image upload button
406
  image_upload_btn.click(
407
  fn=handle_image_upload,
408
  inputs=[image_input],
@@ -419,7 +385,6 @@ def image_tab():
419
  if eq_data["type"] == "error":
420
  return (eq_data["latex"], gr.update(visible=False), gr.update(visible=False), "", None)
421
 
422
- # Create preview display
423
  if eq_data["type"] == "polynomial":
424
  eq_type_display = "Polynomial Equation"
425
  details = f"Degree: {eq_data['degree']}, Coefficients: {eq_data['coeffs']}"
@@ -429,17 +394,13 @@ def image_tab():
429
 
430
  preview_text = f"""
431
  ### ✅ Confirm {eq_type_display}
432
-
433
  **Extracted LaTeX:** {eq_data['latex']}
434
-
435
  **Parsed Details:** {details}
436
-
437
  **Status:** {'✅ Successfully parsed' if eq_data.get('success', True) else '⚠️ Parsing had issues but proceeding with defaults'}
438
  """
439
 
440
  return (preview_text, gr.update(visible=True), gr.update(visible=True), "", None)
441
 
442
- # Event handler for preview button
443
  preview_image_btn.click(
444
  fn=preview_image_equation,
445
  inputs=[extracted_eq_state, real_image_checkbox],
@@ -465,7 +426,6 @@ def image_tab():
465
  except Exception as e:
466
  return f"❌ Error solving equation: {str(e)}", None, str(e)
467
 
468
- # Event handler for confirm button
469
  confirm_image_btn.click(
470
  fn=confirm_image_solution,
471
  inputs=[extracted_eq_state, real_image_checkbox],
@@ -486,7 +446,6 @@ def image_tab():
486
  gr.update(visible=False),
487
  gr.update(visible=False))
488
 
489
- # Event handler for edit button
490
  edit_image_btn.click(
491
  fn=enable_manual_edit,
492
  inputs=[extracted_eq_state],
@@ -499,9 +458,7 @@ def image_tab():
499
  if not latex_input or latex_input.strip() == "":
500
  return "⚠️ Please enter a valid equation.", None, "Empty input"
501
 
502
- # Determine equation type from manual input
503
  eq_type = parse_equation_type(latex_input)
504
-
505
  if eq_type == 'polynomial':
506
  eq_data = extract_polynomial_coefficients(latex_input)
507
  steps, plot, error = solve_polynomial(eq_data["degree"], eq_data["coeffs"], real_only)
@@ -511,11 +468,9 @@ def image_tab():
511
  eq_data["eq1_coeffs"], eq_data["eq2_coeffs"])
512
 
513
  return steps, plot, error if error else "✅ Manual equation solved"
514
-
515
  except Exception as e:
516
  return f"❌ Error parsing manual input: {str(e)}", None, str(e)
517
 
518
- # Event handler for save button
519
  save_edit_btn.click(
520
  fn=save_manual_changes,
521
  inputs=[edit_latex_input, real_image_checkbox],
 
 
1
  import gradio as gr
2
  import sympy as sp
3
  from pix2text import Pix2Text
 
24
  p2t_model = None
25
 
26
  def clean_latex_expression(latex_str):
27
+ """Clean and normalize LaTeX expression for SymPy parsing"""
28
  if not latex_str:
29
  return ""
30
 
31
+ # Remove LaTeX delimiters and normalize
32
  latex_str = latex_str.strip()
33
+ latex_str = re.sub(r'^\$\$|\$\$$', '', latex_str) # Remove $$ delimiters
34
  latex_str = re.sub(r'\\[a-zA-Z]+\{([^}]*)\}', r'\1', latex_str) # Remove LaTeX commands
35
+ latex_str = re.sub(r'\\{2,}', r'\\', latex_str) # Fix multiple backslashes
36
  latex_str = re.sub(r'\s+', ' ', latex_str) # Normalize whitespace
37
+ latex_str = re.sub(r'\^{([^}]+)}', r'**\1', latex_str) # Convert x^{n} to x**n
38
+ latex_str = re.sub(r'(\d+|\w)\s*([xy])', r'\1*\2', latex_str) # Add multiplication sign: 2x -> 2*x
39
+ latex_str = re.sub(r'\s*([+\-*/=])\s*', r'\1', latex_str) # Remove spaces around operators
40
+ latex_str = latex_str.replace('=', '-') # Move right-hand side to left for SymPy
41
+ return latex_str.strip()
42
 
43
  def parse_equation_type(latex_str):
44
  """Determine if the equation is polynomial or linear system"""
45
  try:
 
46
  cleaned = clean_latex_expression(latex_str)
47
+ # Check for system indicators
48
+ if '\\\\' in latex_str or '\n' in latex_str or 'system' in latex_str.lower():
 
49
  return 'linear_system'
50
 
51
+ # Parse with SymPy to determine type
52
+ try:
53
+ expr = sp.sympify(cleaned.split('-')[0] if '-' in cleaned else cleaned)
54
+ if x in expr.free_symbols and y in expr.free_symbols:
55
+ return 'linear_system'
56
+ elif x in expr.free_symbols:
57
+ degree = sp.degree(expr, x)
58
+ return 'polynomial' if degree > 0 else 'linear_system'
59
+ else:
60
+ return 'polynomial'
61
+ except:
62
+ # Fallback to regex-based detection
63
+ if 'x**' in cleaned or '^' in latex_str:
64
+ return 'polynomial'
65
+ elif 'x' in cleaned and 'y' in cleaned:
66
+ return 'linear_system'
67
  return 'polynomial'
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
68
  except Exception as e:
69
  logger.error(f"Error determining equation type: {e}")
70
  return 'polynomial'
 
72
  def extract_polynomial_coefficients(latex_str):
73
  """Extract polynomial coefficients from LaTeX string"""
74
  try:
 
75
  cleaned = clean_latex_expression(latex_str)
76
+ if '-' in cleaned:
77
+ cleaned = cleaned.split('-')[0].strip()
 
 
 
78
 
79
+ # Parse with SymPy
80
+ expr = sp.sympify(cleaned, evaluate=False)
81
  if x not in expr.free_symbols:
82
  raise ValueError("No variable x found in expression")
83
 
84
  # Get polynomial degree
85
  degree = sp.degree(expr, x)
86
+ if degree < 1 or degree > 8:
87
+ raise ValueError(f"Polynomial degree {degree} is out of supported range (1-8)")
88
 
89
  # Extract coefficients
90
  poly = sp.Poly(expr, x)
 
97
  "latex": latex_str,
98
  "success": True
99
  }
 
100
  except Exception as e:
101
  logger.error(f"Error extracting polynomial coefficients: {e}")
102
  return {
103
  "type": "polynomial",
104
  "degree": 2,
105
+ "coeffs": "1 0 0",
106
  "latex": latex_str,
107
  "success": False,
108
  "error": str(e)
 
111
  def extract_linear_system_coefficients(latex_str):
112
  """Extract linear system coefficients from LaTeX string"""
113
  try:
 
114
  cleaned = clean_latex_expression(latex_str)
 
 
115
  equations = re.split(r'\\\\|\n|;', cleaned)
116
  if len(equations) < 2:
 
117
  equations = re.split(r'(?<=[0-9])\s*(?=[+-]?\s*[0-9]*[xy])', cleaned)
118
 
119
  if len(equations) < 2:
 
122
  eq1_str = equations[0].strip()
123
  eq2_str = equations[1].strip()
124
 
 
125
  def parse_linear_eq(eq_str):
126
  # Convert to standard form ax + by = c
127
+ if '-' not in eq_str:
128
+ raise ValueError("No equals sign (converted to '-') found")
129
 
130
+ left, right = eq_str.split('-')
131
+ expr = sp.sympify(left) - sp.sympify(right or '0')
132
 
 
133
  a = float(expr.coeff(x, 1)) if expr.coeff(x, 1) else 0
134
  b = float(expr.coeff(y, 1)) if expr.coeff(y, 1) else 0
135
  c = float(-expr.as_coefficients_dict()[1]) if 1 in expr.as_coefficients_dict() else 0
 
146
  "latex": latex_str,
147
  "success": True
148
  }
 
149
  except Exception as e:
150
  logger.error(f"Error extracting linear system coefficients: {e}")
151
  return {
152
  "type": "linear",
153
+ "eq1_coeffs": "1 1 3",
154
  "eq2_coeffs": "1 -1 1",
155
  "latex": latex_str,
156
  "success": False,
 
158
  }
159
 
160
  def extract_equation_from_image(image_file):
161
+ """Extract equation from image using Pix2Text"""
162
  try:
163
  if p2t_model is None:
164
  return {
 
180
  else:
181
  image = Image.open(image_file.name)
182
 
 
183
  if image.mode != 'RGB':
184
  image = image.convert('RGB')
185
 
186
  logger.info(f"Processing image of size: {image.size}")
187
 
 
188
  result = p2t_model.recognize_text_formula(image)
 
189
  if not result or result.strip() == "":
190
  return {
191
  "type": "error",
 
195
 
196
  logger.info(f"Extracted text: {result}")
197
 
 
198
  eq_type = parse_equation_type(result)
 
199
  if eq_type == 'polynomial':
200
  return extract_polynomial_coefficients(result)
201
  else:
202
  return extract_linear_system_coefficients(result)
 
203
  except Exception as e:
204
  logger.error(f"Error processing image: {e}")
205
  return {
 
208
  "success": False
209
  }
210
 
 
211
  def solve_polynomial(degree, coeff_string, real_only):
212
+ """Solve polynomial equation"""
213
  try:
214
  coeffs = list(map(float, coeff_string.strip().split()))
215
  if len(coeffs) != degree + 1:
 
228
  ) + "\n$$"
229
 
230
  steps_output = f"""
231
+ ### Polynomial Expression
232
  $$ {sp.latex(poly)} = 0 $$
233
+ ### Simplified
234
  $$ {sp.latex(simplified)} = 0 $$
235
+ ### Factored
236
  $$ {sp.latex(factored)} = 0 $$
237
+ ### Roots {'(Only Real)' if real_only else '(All Roots)'}
238
  {roots_output}
239
  """
240
 
 
246
  ax.axhline(0, color='black', linewidth=0.5)
247
  ax.axvline(0, color='black', linewidth=0.5)
248
  ax.grid(True)
249
+ ax.set_title("Graph of the Polynomial")
250
  ax.set_xlabel("x")
251
  ax.set_ylabel("f(x)")
252
  ax.legend()
 
256
  return f"❌ Error: {e}", None, ""
257
 
258
  def solve_linear_system_from_coeffs(eq1_str, eq2_str):
259
+ """Solve linear system"""
260
  try:
261
  coeffs1 = list(map(float, eq1_str.strip().split()))
262
  coeffs2 = list(map(float, eq2_str.strip().split()))
 
278
  eq_latex = f"$$ {sp.latex(eq1)} \\ {sp.latex(eq2)} $$"
279
 
280
  steps = rf"""
281
+ ### Step-by-step Solution
282
  1. **Original Equations:**
283
  $$ {sp.latex(eq1)} $$
284
  $$ {sp.latex(eq2)} $$
 
304
  ax.axhline(0, color='black', linewidth=0.5)
305
  ax.axvline(0, color='black', linewidth=0.5)
306
  ax.legend()
307
+ ax.set_title("Graph of the Linear System")
308
  ax.grid(True)
309
 
310
  return eq_latex, steps, fig, ""
 
321
  return "❌ Unknown equation type", None, ""
322
 
323
  def image_tab():
324
+ """Create the Image Upload Solver tab"""
325
+ with gr.Tab("Image Upload Solver"):
326
+ gr.Markdown("## Solve Equations from Image")
327
 
328
  with gr.Row():
 
329
  image_input = gr.File(
330
  label="Upload Question Image",
331
  file_types=[".pdf", ".png", ".jpg", ".jpeg"],
332
  file_count="single"
333
  )
 
334
  image_upload_btn = gr.Button("📤 Process Image")
335
 
336
  gr.Markdown("**Supported Formats:** .pdf, .png, .jpg, .jpeg")
337
 
338
  with gr.Row():
 
339
  real_image_checkbox = gr.Checkbox(label="Show Only Real Roots (for Polynomials)", value=False)
 
340
  preview_image_btn = gr.Button("🔍 Preview Equation")
341
 
 
342
  image_equation_display = gr.Markdown()
343
 
344
  with gr.Row():
 
345
  confirm_image_btn = gr.Button("✅ Display Solution", visible=False)
 
346
  edit_image_btn = gr.Button("✏️ Make Changes Manually", visible=False)
347
 
 
348
  edit_latex_input = gr.Textbox(label="Edit LaTeX Equation", visible=False, lines=3)
 
349
  save_edit_btn = gr.Button("💾 Save Changes", visible=False)
350
 
 
351
  image_steps_md = gr.Markdown()
 
352
  image_plot_output = gr.Plot()
 
353
  image_error_box = gr.Textbox(label="Status", visible=True, interactive=False)
 
 
354
  extracted_eq_state = gr.State()
355
 
356
  def handle_image_upload(image_file):
 
369
  except Exception as e:
370
  return f"❌ Error processing image: {str(e)}", None, "", None, None
371
 
 
372
  image_upload_btn.click(
373
  fn=handle_image_upload,
374
  inputs=[image_input],
 
385
  if eq_data["type"] == "error":
386
  return (eq_data["latex"], gr.update(visible=False), gr.update(visible=False), "", None)
387
 
 
388
  if eq_data["type"] == "polynomial":
389
  eq_type_display = "Polynomial Equation"
390
  details = f"Degree: {eq_data['degree']}, Coefficients: {eq_data['coeffs']}"
 
394
 
395
  preview_text = f"""
396
  ### ✅ Confirm {eq_type_display}
 
397
  **Extracted LaTeX:** {eq_data['latex']}
 
398
  **Parsed Details:** {details}
 
399
  **Status:** {'✅ Successfully parsed' if eq_data.get('success', True) else '⚠️ Parsing had issues but proceeding with defaults'}
400
  """
401
 
402
  return (preview_text, gr.update(visible=True), gr.update(visible=True), "", None)
403
 
 
404
  preview_image_btn.click(
405
  fn=preview_image_equation,
406
  inputs=[extracted_eq_state, real_image_checkbox],
 
426
  except Exception as e:
427
  return f"❌ Error solving equation: {str(e)}", None, str(e)
428
 
 
429
  confirm_image_btn.click(
430
  fn=confirm_image_solution,
431
  inputs=[extracted_eq_state, real_image_checkbox],
 
446
  gr.update(visible=False),
447
  gr.update(visible=False))
448
 
 
449
  edit_image_btn.click(
450
  fn=enable_manual_edit,
451
  inputs=[extracted_eq_state],
 
458
  if not latex_input or latex_input.strip() == "":
459
  return "⚠️ Please enter a valid equation.", None, "Empty input"
460
 
 
461
  eq_type = parse_equation_type(latex_input)
 
462
  if eq_type == 'polynomial':
463
  eq_data = extract_polynomial_coefficients(latex_input)
464
  steps, plot, error = solve_polynomial(eq_data["degree"], eq_data["coeffs"], real_only)
 
468
  eq_data["eq1_coeffs"], eq_data["eq2_coeffs"])
469
 
470
  return steps, plot, error if error else "✅ Manual equation solved"
 
471
  except Exception as e:
472
  return f"❌ Error parsing manual input: {str(e)}", None, str(e)
473
 
 
474
  save_edit_btn.click(
475
  fn=save_manual_changes,
476
  inputs=[edit_latex_input, real_image_checkbox],