Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Select an option

  • Save JordaanFouche/4d54d0e2630e38e8d17aec26b419ddbe to your computer and use it in GitHub Desktop.

Select an option

Save JordaanFouche/4d54d0e2630e38e8d17aec26b419ddbe to your computer and use it in GitHub Desktop.
"OTV Fracture Analysis - Corrections Needed"
def detect_fractures(self, image, depth_top, depth_bottom):
"""Detect fractures in the image using specified method"""
# ... existing edge detection code ...
# For each detected line, calculate fracture parameters
fractures = []
for line in lines:
x1, y1, x2, y2 = line[0]
# Calculate the angle (dip)
angle_rad = np.arctan2(y2 - y1, x2 - x1)
dip_deg = abs(np.degrees(angle_rad))
if dip_deg > 90:
dip_deg = 180 - dip_deg
# Calculate depth (midpoint of the fracture)
depth_pixel = (y1 + y2) / 2
depth_m = depth_top + (depth_pixel / self.pixels_per_meter)
# Calculate length along borehole wall (arc length)
# The x-coordinate represents position around the borehole circumference
# The actual length is the arc length along the borehole wall
dx_pixels = x2 - x1
dy_pixels = y2 - y1
length_pixels = np.sqrt(dx_pixels**2 + dy_pixels**2)
# Convert to meters using the circumference
# The image width represents the full circumference
length_m = (length_pixels / self.image_width) * self.circumference_m
# Calculate azimuth (dip direction) from x-position
# In OTV images, x=0 maps to North (or reference direction)
x_center = (x1 + x2) / 2
azimuth_deg = (x_center / self.image_width) * 360
# Apply magnetic declination correction
true_azimuth = (azimuth_deg - self.declination) % 360
# Estimate aperture from line thickness
aperture_mm = self.estimate_aperture_from_line(line, image)
fractures.append({
'depth': depth_m,
'dip': dip_deg,
'azimuth': true_azimuth,
'length': length_m,
'aperture': aperture_mm
})
return fractures
def estimate_aperture_from_line(self, line, image):
"""Estimate fracture aperture from the line in the image"""
x1, y1, x2, y2 = line[0]
# Calculate line direction
dx = x2 - x1
dy = y2 - y1
length = np.sqrt(dx*dx + dy*dy)
if length < 3:
return 0.05 # Very small fracture
# Sample the line and estimate width from intensity profile
num_samples = min(30, int(length))
widths = []
for i in range(num_samples):
t = i / num_samples
x = int(x1 + t * dx)
y = int(y1 + t * dy)
# Get the intensity profile perpendicular to the line
# Simple approach: look at the line thickness in the Hough transform
# The line width can be estimated from the accumulator values
pass
# For now, use a heuristic based on line length and pixel intensity
# This is a simplified approach - in practice, you'd use the actual image data
line_thickness_pixels = max(1.0, length / 100)
# Convert to millimeters using the scale factor
aperture_mm = line_thickness_pixels / self.scale_factor
# Ensure reasonable bounds
aperture_mm = max(0.01, min(10.0, aperture_mm))
return aperture_mm
def detect_fractures_hybrid(self, edges, image):
"""Hybrid detection: combine Hough transform and contour detection"""
# Hough Transform detection
lines = cv2.HoughLinesP(
edges,
rho=1,
theta=np.pi/180,
threshold=self.hough_threshold,
minLineLength=self.min_line_length,
maxLineGap=self.max_line_gap
)
# Contour detection
contours, _ = cv2.findContours(edges, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
all_lines = []
# Add Hough lines
if lines is not None:
for line in lines:
all_lines.append(line)
# Add contour-based lines (simplified as line segments)
for contour in contours:
if len(contour) > 5:
# Fit a line to the contour
[vx, vy, x0, y0] = cv2.fitLine(contour, cv2.DIST_L2, 0, 0.01, 0.01)
# Convert to line segment
length = np.sqrt(vx*vx + vy*vy)
if length > 0:
# Extend the line to cover the contour extent
pts = contour.reshape(-1, 2)
min_dist = np.min(pts, axis=0)
max_dist = np.max(pts, axis=0)
# Create line segment from the fitted line
# ... (simplified for brevity)
return all_lines
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment