nick-leland commited on
Commit
b43e654
1 Parent(s): 91b420f

Updated the app for demo purposes

Browse files
Files changed (1) hide show
  1. app.py +94 -89
app.py CHANGED
@@ -12,88 +12,88 @@ from fastai.vision.all import *
12
  from ultralytics import ASSETS, YOLO
13
  import cv2
14
 
15
- def apply_vector_field_transform(image, func, radius, center=(0.5, 0.5), strength=1, edge_smoothness=0.1, center_smoothness=0.20):
16
- rows, cols = image.shape[:2]
17
- max_dim = max(rows, cols)
18
- print()
19
- print(f"Max_dim is {max_dim}")
20
- print()
21
-
22
- center_y = int(center[1] * rows)
23
- center_x = int(center[0] * cols)
24
- center_y = abs(rows - center_y)
25
-
26
- print(f"Image shape: {rows}x{cols}")
27
- print(f"Center: ({center_x}, {center_y})")
28
- print(f"Radius: {radius}, Strength: {strength}")
29
- print(f"Edge smoothness: {edge_smoothness}, Center smoothness: {center_smoothness}")
30
-
31
- y, x = np.ogrid[:rows, :cols]
32
- y = (y - center_y) / max_dim
33
- x = (x - center_x) / max_dim
34
-
35
- dist_from_center = np.sqrt(x**2 + y**2)
36
-
37
- z = func(x, y)
38
- print(f"Function output - min: {np.min(z)}, max: {np.max(z)}")
39
-
40
- gy, gx = np.gradient(z)
41
- print(f"Initial gradient - gx min: {np.min(gx)}, max: {np.max(gx)}")
42
- print(f"Initial gradient - gy min: {np.min(gy)}, max: {np.max(gy)}")
43
-
44
- # Avoid division by zero
45
- edge_smoothness = np.maximum(edge_smoothness, 1e-6)
46
- center_smoothness = np.maximum(center_smoothness, 1e-6)
47
-
48
- edge_mask = np.clip((radius - dist_from_center) / (radius * edge_smoothness), 0, 1)
49
- center_mask = np.clip((dist_from_center - radius * center_smoothness) / (radius * center_smoothness), 0, 1)
50
- mask = edge_mask * center_mask
51
-
52
- gx = gx * mask
53
- gy = gy * mask
54
-
55
- magnitude = np.sqrt(gx**2 + gy**2)
56
- magnitude[magnitude == 0] = 1 # Avoid division by zero
57
- gx = gx / magnitude
58
- gy = gy / magnitude
59
-
60
- scale_factor = strength * np.log(max_dim) / 100
61
- gx = gx * scale_factor * mask
62
- gy = gy * scale_factor * mask
63
-
64
- print(f"Final gradient - gx min: {np.min(gx)}, max: {np.max(gx)}")
65
- print(f"Final gradient - gy min: {np.min(gy)}, max: {np.max(gy)}")
66
-
67
- # Forward transformation
68
- x_new = x + gx
69
- y_new = y + gy
70
-
71
- x_new = x_new * max_dim + center_x
72
- y_new = y_new * max_dim + center_y
73
-
74
- x_new = np.clip(x_new, 0, cols - 1)
75
- y_new = np.clip(y_new, 0, rows - 1)
76
-
77
- # Inverse transformation
78
- x_inv = x - gx
79
- y_inv = y - gy
80
-
81
- x_inv = x_inv * max_dim + center_x
82
- y_inv = y_inv * max_dim + center_y
83
-
84
- x_inv = np.clip(x_inv, 0, cols - 1)
85
- y_inv = np.clip(y_inv, 0, rows - 1)
86
-
87
- # Apply transformations
88
- channels_forward = [ndimage.map_coordinates(image[..., i], [y_new, x_new], order=1, mode='reflect')
89
- for i in range(image.shape[2])]
90
- channels_inverse = [ndimage.map_coordinates(image[..., i], [y_inv, x_inv], order=1, mode='reflect')
91
- for i in range(image.shape[2])]
92
-
93
- transformed_image = np.dstack(channels_forward).astype(image.dtype)
94
- inverse_transformed_image = np.dstack(channels_inverse).astype(image.dtype)
95
-
96
- return transformed_image, inverse_transformed_image, (gx, gy)
97
 
98
  def create_gradient_vector_field(gx, gy, image_shape, step=20, reverse=False):
99
  """
@@ -334,6 +334,8 @@ def transform_image(image, func_choice, randomization_check, radius, center_x, c
334
  # strength = strength * 2 # This allows for stronger effects
335
 
336
  try:
 
 
337
  # Generate gradients
338
  gx, gy = generate_function_gradient(func, I.shape, radius, (center_x, center_y), strength, edge_smoothness, center_smoothness)
339
 
@@ -358,16 +360,20 @@ def transform_image(image, func_choice, randomization_check, radius, center_x, c
358
 
359
  inverse_transformed = cv2.remap(I, x_inv, y_inv, cv2.INTER_LINEAR)
360
 
 
 
 
 
361
  applied_transformed = cv2.remap(transformed, x_inv, y_inv, cv2.INTER_LINEAR)
362
 
363
- print(f"Transformed image shape: {transformed.shape}")
364
- print(f"Inverse transformed image shape: {inverse_transformed.shape}")
365
 
366
  vector_field = create_gradient_vector_field(gx, gy, I.shape[:2], reverse=reverse_gradient)
367
  inverted_vector_field = create_gradient_vector_field(inv_gx, inv_gy, I.shape[:2], reverse=False)
368
 
369
- print(f"Vector field shape: {vector_field.shape}")
370
- print(f"Inverted vector field shape: {inverted_vector_field.shape}")
371
 
372
  # If we downsampled earlier, upsample the results back to original size
373
  if max(I.shape[:2]) != max(np.asarray(Image.open(image)).shape[:2]):
@@ -409,7 +415,6 @@ def transform_image(image, func_choice, randomization_check, radius, center_x, c
409
  # print(result_localization2, "modelv8x")
410
 
411
 
412
- YOLO_image = predict_image(transformed, model_bulge, 0.5, 0.5)
413
  # YOLO_image1 = predict_image(transformed, modelv8n, 0.5, 0.5)
414
  # YOLO_image2 = predict_image(transformed, modelv8x, 0.5, 0.5)
415
 
@@ -422,7 +427,7 @@ demo = gr.Interface(
422
  fn=transform_image,
423
  inputs=[
424
  gr.Image(type="filepath"),
425
- gr.Dropdown(["Pinch", "Spiral", "Shift Up", "Bulge", "Volcano"], value="Volcano", label="Function"),
426
  gr.Checkbox(label="Randomize inputs?"),
427
  gr.Slider(0, 0.5, value=0.25, label="Radius (as fraction of image size)"),
428
  gr.Slider(0, 1, value=0.5, label="Center X"),
@@ -452,7 +457,7 @@ demo = gr.Interface(
452
  ],
453
  title="Image Transformation Demo!",
454
  article="If you like this demo, please star the github repository for the project! Located [here!](https://github.com/nick-leland/DistortionML)",
455
- description="This is the baseline function that will be used to generate the database for a machine learning model I am working on called 'DistortionMl'! The goal of this model is to detect and then reverse image transformations that can be generated here!\nYou can read more about the project at [this repository link](https://github.com/nick-leland/DistortionML). The main function that I was working on is the 'Bulge'/'Volcano' function, I can't really guarantee that the others work as well!\nI have just added the first baseline ML model to detect if a distortion has taken place! It was only trained on mazes though ([Dataset Here](https://www.kaggle.com/datasets/nickleland/distorted-mazes)) so in order for it to detect a distortion you have to use one of the images provided in the examples! Feel free to mess around wtih other images in the meantime though!"
456
  )
457
 
458
  demo.launch(share=True)
 
12
  from ultralytics import ASSETS, YOLO
13
  import cv2
14
 
15
+ # def apply_vector_field_transform(image, func, radius, center=(0.5, 0.5), strength=1, edge_smoothness=0.1, center_smoothness=0.20):
16
+ # rows, cols = image.shape[:2]
17
+ # max_dim = max(rows, cols)
18
+ # print()
19
+ # print(f"Max_dim is {max_dim}")
20
+ # print()
21
+ #
22
+ # center_y = int(center[1] * rows)
23
+ # center_x = int(center[0] * cols)
24
+ # center_y = abs(rows - center_y)
25
+ #
26
+ # print(f"Image shape: {rows}x{cols}")
27
+ # print(f"Center: ({center_x}, {center_y})")
28
+ # print(f"Radius: {radius}, Strength: {strength}")
29
+ # print(f"Edge smoothness: {edge_smoothness}, Center smoothness: {center_smoothness}")
30
+ #
31
+ # y, x = np.ogrid[:rows, :cols]
32
+ # y = (y - center_y) / max_dim
33
+ # x = (x - center_x) / max_dim
34
+ #
35
+ # dist_from_center = np.sqrt(x**2 + y**2)
36
+ #
37
+ # z = func(x, y)
38
+ # print(f"Function output - min: {np.min(z)}, max: {np.max(z)}")
39
+ #
40
+ # gy, gx = np.gradient(z)
41
+ # print(f"Initial gradient - gx min: {np.min(gx)}, max: {np.max(gx)}")
42
+ # print(f"Initial gradient - gy min: {np.min(gy)}, max: {np.max(gy)}")
43
+ #
44
+ # # Avoid division by zero
45
+ # edge_smoothness = np.maximum(edge_smoothness, 1e-6)
46
+ # center_smoothness = np.maximum(center_smoothness, 1e-6)
47
+ #
48
+ # edge_mask = np.clip((radius - dist_from_center) / (radius * edge_smoothness), 0, 1)
49
+ # center_mask = np.clip((dist_from_center - radius * center_smoothness) / (radius * center_smoothness), 0, 1)
50
+ # mask = edge_mask * center_mask
51
+ #
52
+ # gx = gx * mask
53
+ # gy = gy * mask
54
+ #
55
+ # magnitude = np.sqrt(gx**2 + gy**2)
56
+ # magnitude[magnitude == 0] = 1 # Avoid division by zero
57
+ # gx = gx / magnitude
58
+ # gy = gy / magnitude
59
+ #
60
+ # scale_factor = strength * np.log(max_dim) / 100
61
+ # gx = gx * scale_factor * mask
62
+ # gy = gy * scale_factor * mask
63
+ #
64
+ # print(f"Final gradient - gx min: {np.min(gx)}, max: {np.max(gx)}")
65
+ # print(f"Final gradient - gy min: {np.min(gy)}, max: {np.max(gy)}")
66
+ #
67
+ # # Forward transformation
68
+ # x_new = x + gx
69
+ # y_new = y + gy
70
+ #
71
+ # x_new = x_new * max_dim + center_x
72
+ # y_new = y_new * max_dim + center_y
73
+ #
74
+ # x_new = np.clip(x_new, 0, cols - 1)
75
+ # y_new = np.clip(y_new, 0, rows - 1)
76
+ #
77
+ # # Inverse transformation
78
+ # x_inv = x - gx
79
+ # y_inv = y - gy
80
+ #
81
+ # x_inv = x_inv * max_dim + center_x
82
+ # y_inv = y_inv * max_dim + center_y
83
+ #
84
+ # x_inv = np.clip(x_inv, 0, cols - 1)
85
+ # y_inv = np.clip(y_inv, 0, rows - 1)
86
+ #
87
+ # # Apply transformations
88
+ # channels_forward = [ndimage.map_coordinates(image[..., i], [y_new, x_new], order=1, mode='reflect')
89
+ # for i in range(image.shape[2])]
90
+ # channels_inverse = [ndimage.map_coordinates(image[..., i], [y_inv, x_inv], order=1, mode='reflect')
91
+ # for i in range(image.shape[2])]
92
+ #
93
+ # transformed_image = np.dstack(channels_forward).astype(image.dtype)
94
+ # inverse_transformed_image = np.dstack(channels_inverse).astype(image.dtype)
95
+ #
96
+ # return transformed_image, inverse_transformed_image, (gx, gy)
97
 
98
  def create_gradient_vector_field(gx, gy, image_shape, step=20, reverse=False):
99
  """
 
334
  # strength = strength * 2 # This allows for stronger effects
335
 
336
  try:
337
+ strength = 0.8
338
+
339
  # Generate gradients
340
  gx, gy = generate_function_gradient(func, I.shape, radius, (center_x, center_y), strength, edge_smoothness, center_smoothness)
341
 
 
360
 
361
  inverse_transformed = cv2.remap(I, x_inv, y_inv, cv2.INTER_LINEAR)
362
 
363
+ # Apply Inverse to detected location
364
+ YOLO_image = predict_image(transformed, model_bulge, 0.5, 0.5)
365
+
366
+
367
  applied_transformed = cv2.remap(transformed, x_inv, y_inv, cv2.INTER_LINEAR)
368
 
369
+ # print(f"Transformed image shape: {transformed.shape}")
370
+ # print(f"Inverse transformed image shape: {inverse_transformed.shape}")
371
 
372
  vector_field = create_gradient_vector_field(gx, gy, I.shape[:2], reverse=reverse_gradient)
373
  inverted_vector_field = create_gradient_vector_field(inv_gx, inv_gy, I.shape[:2], reverse=False)
374
 
375
+ # print(f"Vector field shape: {vector_field.shape}")
376
+ # print(f"Inverted vector field shape: {inverted_vector_field.shape}")
377
 
378
  # If we downsampled earlier, upsample the results back to original size
379
  if max(I.shape[:2]) != max(np.asarray(Image.open(image)).shape[:2]):
 
415
  # print(result_localization2, "modelv8x")
416
 
417
 
 
418
  # YOLO_image1 = predict_image(transformed, modelv8n, 0.5, 0.5)
419
  # YOLO_image2 = predict_image(transformed, modelv8x, 0.5, 0.5)
420
 
 
427
  fn=transform_image,
428
  inputs=[
429
  gr.Image(type="filepath"),
430
+ gr.Dropdown(["Pinch", "Spiral", "Shift Up", "Bulge", "Volcano"], value="Bulge", label="Function"),
431
  gr.Checkbox(label="Randomize inputs?"),
432
  gr.Slider(0, 0.5, value=0.25, label="Radius (as fraction of image size)"),
433
  gr.Slider(0, 1, value=0.5, label="Center X"),
 
457
  ],
458
  title="Image Transformation Demo!",
459
  article="If you like this demo, please star the github repository for the project! Located [here!](https://github.com/nick-leland/DistortionML)",
460
+ description=""
461
  )
462
 
463
  demo.launch(share=True)