dschandra's picture
Update app.py
e918e64 verified
import cv2
import numpy as np
import gradio as gr
from pdf2image import convert_from_path
import os
import tempfile
import logging
from PIL import Image
# Set up logging
logging.basicConfig(filename='debug.log', level=logging.DEBUG)
logger = logging.getLogger(__name__)
def validate_poppler_path(poppler_path):
if not poppler_path:
return None
poppler_path = poppler_path.replace('\\', '/')
if not os.path.isdir(poppler_path):
return None
pdftoppm_path = os.path.join(poppler_path, "pdftoppm" + (".exe" if os.name == "nt" else ""))
if not os.path.isfile(pdftoppm_path):
return None
return poppler_path
def calculate_materials_from_dimensions(wall_area, foundation_area):
return {
"cement": round(wall_area * 10 + foundation_area * 20, 2),
"bricks": int(wall_area * 500 + foundation_area * 750),
"steel": round(wall_area * 2 + foundation_area * 5, 2)
}
def process_blueprint(uploaded_file, blueprint_width_m=27, blueprint_height_m=9.78, poppler_path=None):
try:
filename = uploaded_file.name
poppler_path = validate_poppler_path(poppler_path)
# Convert input to image
if filename.endswith(".pdf"):
images = convert_from_path(uploaded_file.name, poppler_path=poppler_path)
if not images:
return {"error": "No pages found in PDF"}
image = np.array(images[0])
else:
image = cv2.imdecode(np.frombuffer(uploaded_file.read(), np.uint8), cv2.IMREAD_COLOR)
if image is None:
return {"error": "Failed to load image"}
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
edges = cv2.Canny(gray, 50, 150)
lines = cv2.HoughLinesP(edges, 1, np.pi / 180, 100, minLineLength=50, maxLineGap=10)
total_wall_length_pixels = sum(
np.sqrt((x2 - x1) ** 2 + (y2 - y1) ** 2)
for line in lines for x1, y1, x2, y2 in [line[0]]
) if lines is not None else 0
img_h, img_w = image.shape[:2]
pixel_to_meter_w = blueprint_width_m / img_w
pixel_to_meter_h = blueprint_height_m / img_h
avg_pixel_to_meter = (pixel_to_meter_w + pixel_to_meter_h) / 2
total_wall_length_m = total_wall_length_pixels * avg_pixel_to_meter
wall_height_m = 3
wall_area = total_wall_length_m * wall_height_m
total_area = blueprint_width_m * blueprint_height_m
foundation_area = total_area * 0.1
materials = calculate_materials_from_dimensions(wall_area, foundation_area)
return {
"cement": f"{materials['cement']} kg",
"bricks": f"{materials['bricks']} units",
"steel": f"{materials['steel']} kg"
}
except Exception as e:
return {"error": f"Processing failed: {str(e)}"}
# Gradio UI
interface = gr.Interface(
fn=process_blueprint,
inputs=[
gr.File(label="Upload Blueprint (PDF or Image)", file_types=[".pdf", ".png", ".jpg", ".jpeg"]),
gr.Number(label="Blueprint Width (meters)", value=27),
gr.Number(label="Blueprint Height (meters)", value=9.78),
gr.Textbox(label="Poppler Path (Optional)", placeholder="e.g., C:/poppler/bin")
],
outputs=gr.JSON(label="Estimated Materials"),
title="Blueprint Estimator",
description="Upload a blueprint as PDF or image to estimate materials (cement, bricks, steel)."
)
if __name__ == "__main__":
interface.launch()