Noursine commited on
Commit
fff1d29
·
verified ·
1 Parent(s): 7e2cb69

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +37 -39
app.py CHANGED
@@ -1,3 +1,4 @@
 
1
  import gradio as gr
2
  from PIL import Image
3
  import matplotlib.pyplot as plt
@@ -7,61 +8,58 @@ import os
7
  import numpy as np
8
  from pycocotools.coco import COCO
9
  import io
 
10
 
11
- # ==== Update these paths to match your environment ====
12
  annotation_path = "test/test_annotations.coco.json"
13
  image_folder = "test/images"
14
- # ======================================================
15
 
16
- # Load COCO annotations once at start
17
  coco = COCO(annotation_path)
18
  categories = coco.loadCats(coco.getCatIds())
19
  cat_id_to_name = {cat['id']: cat['name'] for cat in categories}
20
  image_ids = coco.getImgIds()
21
- image_file_name_map = {coco.loadImgs(img_id)[0]['file_name']: coco.loadImgs(img_id)[0] for img_id in image_ids}
 
 
 
 
 
 
 
 
 
 
 
 
 
 
22
 
23
  def show_annotated_teeth_image(image_file):
24
- # === Handle various image input types ===
25
- if isinstance(image_file, str): # example image from filepath
26
- filename = os.path.basename(image_file)
27
  image_np = cv2.imread(image_file)
28
  image_np = cv2.cvtColor(image_np, cv2.COLOR_BGR2RGB)
29
- elif isinstance(image_file, Image.Image): # uploaded PIL image
30
- filename = getattr(image_file, 'filename', None)
31
  image_np = np.array(image_file.convert("RGB"))
32
- else: # raw file upload
33
- filename = getattr(image_file, 'name', None)
34
  image_np = cv2.imdecode(np.frombuffer(image_file.read(), np.uint8), cv2.IMREAD_COLOR)
35
  image_np = cv2.cvtColor(image_np, cv2.COLOR_BGR2RGB)
36
 
37
- filename = os.path.basename(filename) if filename else None
38
- print(f"Input filename: {filename}")
39
-
40
- # === Try to match by filename ===
41
- matched_info = image_file_name_map.get(filename)
42
-
43
- # === Fallback: Try to match by content ===
44
- if not matched_info:
45
- print("⚠️ No direct filename match. Trying to match image by content...")
46
- for fname, info in image_file_name_map.items():
47
- test_img_path = os.path.join(image_folder, fname)
48
- test_img = cv2.imread(test_img_path)
49
- test_img = cv2.cvtColor(test_img, cv2.COLOR_BGR2RGB)
50
-
51
- # Match by shape and pixel similarity
52
- if test_img.shape == image_np.shape and np.allclose(test_img, image_np, atol=5):
53
- matched_info = info
54
- print(f"✅ Matched by content with: {fname}")
55
- break
56
 
 
57
  if not matched_info:
58
- print("No annotation match found. Returning plain image.")
59
  return Image.fromarray(image_np)
60
 
61
- # === Load annotations and draw ===
62
  ann_ids = coco.getAnnIds(imgIds=matched_info['id'])
63
  annotations = coco.loadAnns(ann_ids)
64
 
 
65
  fig, ax = plt.subplots(1, figsize=(8, 8))
66
  ax.imshow(image_np)
67
 
@@ -69,8 +67,7 @@ def show_annotated_teeth_image(image_file):
69
  x, y, w, h = ann['bbox']
70
  class_id = ann['category_id']
71
  class_name = cat_id_to_name.get(class_id, "Unknown")
72
- rect = patches.Rectangle((x, y), w, h, linewidth=2, edgecolor='blue', facecolor='none')
73
- ax.add_patch(rect)
74
  ax.text(x, y, class_name, fontsize=10, color='blue', backgroundcolor='black')
75
 
76
  ax.axis('off')
@@ -84,16 +81,17 @@ def show_annotated_teeth_image(image_file):
84
 
85
  return annotated_image
86
 
87
- # === Prepare examples ===
88
- example_files = list(image_file_name_map.keys())[:3]
89
- example_paths = [os.path.join(image_folder, fname) for fname in example_files]
90
 
 
91
  interface = gr.Interface(
92
  fn=show_annotated_teeth_image,
93
- inputs=gr.Image(type="filepath", label="Upload a Dental X-ray or choose an example"),
94
  outputs=gr.Image(type="pil", label="Annotated Image"),
95
  title="🦷 Dental X-ray Annotator",
96
- description="Upload a dental X-ray or select a sample to visualize tooth annotations (COCO format).",
97
  examples=example_paths,
98
  )
99
 
 
1
+ # app.py
2
  import gradio as gr
3
  from PIL import Image
4
  import matplotlib.pyplot as plt
 
8
  import numpy as np
9
  from pycocotools.coco import COCO
10
  import io
11
+ import hashlib
12
 
13
+ # ==== Paths (update if needed) ====
14
  annotation_path = "test/test_annotations.coco.json"
15
  image_folder = "test/images"
16
+ # ==================================
17
 
18
+ # Load COCO annotations once
19
  coco = COCO(annotation_path)
20
  categories = coco.loadCats(coco.getCatIds())
21
  cat_id_to_name = {cat['id']: cat['name'] for cat in categories}
22
  image_ids = coco.getImgIds()
23
+
24
+ # Helper to compute image content hash (used for matching uploads)
25
+ def compute_md5(image_array):
26
+ return hashlib.md5(image_array.tobytes()).hexdigest()
27
+
28
+ # Precompute hashes for all dataset images
29
+ image_hash_map = {}
30
+ for img_id in image_ids:
31
+ img_info = coco.loadImgs(img_id)[0]
32
+ img_path = os.path.join(image_folder, img_info['file_name'])
33
+ if os.path.exists(img_path):
34
+ img_np = cv2.imread(img_path)
35
+ img_np = cv2.cvtColor(img_np, cv2.COLOR_BGR2RGB)
36
+ img_hash = compute_md5(img_np)
37
+ image_hash_map[img_hash] = img_info
38
 
39
  def show_annotated_teeth_image(image_file):
40
+ # Convert uploaded image to numpy
41
+ if isinstance(image_file, str): # example file
 
42
  image_np = cv2.imread(image_file)
43
  image_np = cv2.cvtColor(image_np, cv2.COLOR_BGR2RGB)
44
+ elif isinstance(image_file, Image.Image):
 
45
  image_np = np.array(image_file.convert("RGB"))
46
+ else:
 
47
  image_np = cv2.imdecode(np.frombuffer(image_file.read(), np.uint8), cv2.IMREAD_COLOR)
48
  image_np = cv2.cvtColor(image_np, cv2.COLOR_BGR2RGB)
49
 
50
+ # Compute hash of input image
51
+ image_hash = compute_md5(image_np)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
52
 
53
+ matched_info = image_hash_map.get(image_hash)
54
  if not matched_info:
55
+ print("No matching annotation found for this image.")
56
  return Image.fromarray(image_np)
57
 
58
+ # Load annotations
59
  ann_ids = coco.getAnnIds(imgIds=matched_info['id'])
60
  annotations = coco.loadAnns(ann_ids)
61
 
62
+ # Plot the image and annotations
63
  fig, ax = plt.subplots(1, figsize=(8, 8))
64
  ax.imshow(image_np)
65
 
 
67
  x, y, w, h = ann['bbox']
68
  class_id = ann['category_id']
69
  class_name = cat_id_to_name.get(class_id, "Unknown")
70
+ ax.add_patch(patches.Rectangle((x, y), w, h, linewidth=2, edgecolor='blue', facecolor='none'))
 
71
  ax.text(x, y, class_name, fontsize=10, color='blue', backgroundcolor='black')
72
 
73
  ax.axis('off')
 
81
 
82
  return annotated_image
83
 
84
+ # Example paths for Gradio buttons
85
+ example_files = list(image_hash_map.values())[:3]
86
+ example_paths = [os.path.join(image_folder, img['file_name']) for img in example_files]
87
 
88
+ # Gradio Interface
89
  interface = gr.Interface(
90
  fn=show_annotated_teeth_image,
91
+ inputs=gr.Image(type="filepath", label="Upload a Dental X-ray or choose a default example"),
92
  outputs=gr.Image(type="pil", label="Annotated Image"),
93
  title="🦷 Dental X-ray Annotator",
94
+ description="Upload a dental X-ray image or select a default example to visualize teeth annotations using COCO format.",
95
  examples=example_paths,
96
  )
97