Kushalmanda's picture
Update app.py
2a9b4b2 verified
raw
history blame
4.4 kB
import cv2
import numpy as np
import gradio as gr
from pdf2image import convert_from_path
import os
import tempfile
# Function to calculate materials based on blueprint dimensions
def calculate_materials_from_dimensions(wall_area, foundation_area):
materials = {
"cement": 0,
"bricks": 0,
"steel": 0
}
# Wall calculations (in m²)
if wall_area > 0:
materials['cement'] += wall_area * 10 # 10 kg cement per m² for walls
materials['bricks'] += wall_area * 500 # 500 bricks per m² for walls
materials['steel'] += wall_area * 2 # 2 kg steel per m² for walls
# Foundation calculations (in m²)
if foundation_area > 0:
materials['cement'] += foundation_area * 20 # 20 kg cement per m² for foundation
materials['bricks'] += foundation_area * 750 # 750 bricks per m² for foundation
materials['steel'] += foundation_area * 5 # 5 kg steel per m² for foundation
return materials
# Function to process the blueprint from a PDF
def process_blueprint(pdf_path):
try:
# Convert PDF to images
images = convert_from_path(pdf_path, first_page=1, last_page=1) # Process only the first page
if not images:
raise ValueError("No images extracted from the PDF")
# Save the first page as a temporary image
with tempfile.NamedTemporaryFile(suffix=".png", delete=False) as temp_file:
images[0].save(temp_file.name, 'PNG')
temp_image_path = temp_file.name
# Open the image with OpenCV
image = cv2.imread(temp_image_path)
if image is None:
raise ValueError("Could not load the image from PDF")
# Clean up temporary file
os.unlink(temp_image_path)
# Convert to grayscale for easier processing
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
# Apply edge detection to find lines (walls)
edges = cv2.Canny(gray, 50, 150, apertureSize=3)
# Use Hough Transform to detect lines (walls)
lines = cv2.HoughLinesP(edges, 1, np.pi / 180, threshold=100, minLineLength=50, maxLineGap=10)
# Calculate total wall length (in pixels)
total_wall_length_pixels = 0
if lines is not None:
for line in lines:
x1, y1, x2, y2 = line[0]
length = np.sqrt((x2 - x1) ** 2 + (y2 - y1) ** 2)
total_wall_length_pixels += length
# From the blueprint, we assume dimensions (27 m × 9.78 m)
image_height, image_width = image.shape[:2]
blueprint_width_m = 27 # From the blueprint (27 m)
blueprint_height_m = 9.78 # From the blueprint (9.78 m)
# Calculate pixel-to-meter ratio
pixel_to_meter_width = blueprint_width_m / image_width
pixel_to_meter_height = blueprint_height_m / image_height
pixel_to_meter = (pixel_to_meter_width + pixel_to_meter_height) / 2 # Average for simplicity
# Convert wall length to meters
total_wall_length_m = total_wall_length_pixels * pixel_to_meter
# Estimate wall area (assume wall height of 3 m for simplicity)
wall_height_m = 3 # Standard room height
wall_area = total_wall_length_m * wall_height_m
# Estimate foundation area (based on the blueprint's total area)
total_area = blueprint_width_m * blueprint_height_m # 27 m × 9.78 m
foundation_area = total_area * 0.1 # Assume 10% of the total area is foundation
# Calculate materials
materials = calculate_materials_from_dimensions(wall_area, foundation_area)
# Format the output
formatted_materials = {
"cement": f"{materials['cement']:.2f} kg",
"bricks": f"{materials['bricks']:.0f} units",
"steel": f"{materials['steel']:.2f} kg"
}
return formatted_materials
except Exception as e:
return {"error": f"Failed to process PDF: {str(e)}"}
# Set up Gradio interface
interface = gr.Interface(
fn=process_blueprint,
inputs=gr.File(file_types=[".pdf"], label="Upload Blueprint PDF"),
outputs=gr.JSON(label="Material Estimates"),
title="Blueprint Material Estimator",
description="Upload a PDF containing a blueprint to estimate construction materials."
)
# Launch the interface
if __name__ == "__main__":
interface.launch(share=False)