File size: 5,300 Bytes
aae87aa 28c9014 aae87aa 28c9014 aae87aa 476c0f9 3280007 476c0f9 3280007 476c0f9 3280007 476c0f9 28c9014 3280007 28c9014 3280007 28c9014 aae87aa 3280007 476c0f9 3280007 aae87aa 3280007 aae87aa 28c9014 476c0f9 aae87aa 476c0f9 3280007 476c0f9 3280007 476c0f9 aae87aa 28c9014 aae87aa 3280007 aae87aa 28c9014 3280007 28c9014 3280007 28c9014 3280007 476c0f9 aae87aa 3280007 aae87aa 28c9014 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 |
import streamlit as st
import cv2
import numpy as np
import matplotlib.pyplot as plt
import pandas as pd
import plotly.express as px
from PIL import Image
def analyze_crack(image):
# Convert image to grayscale
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
# Edge detection
edges = cv2.Canny(gray, 50, 150)
# Finding contours
contours, _ = cv2.findContours(edges, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
# Calculate crack metrics
crack_data = []
for cnt in contours:
length = cv2.arcLength(cnt, True)
x, y, w, h = cv2.boundingRect(cnt)
width = w
severity = classify_crack(length, width)
crack_data.append({"Length": length, "Width": width, "Severity": severity, "X": x, "Y": y})
return edges, crack_data
def classify_crack(length, width):
if length > 150 or width > 20:
return "π΄ Major"
elif length > 80 or width > 10:
return "π Moderate"
else:
return "π’ Minor"
def generate_description(severity):
if "Major" in severity:
return "π¨ This crack is classified as **Major**, indicating significant structural distress. Major cracks can compromise the integrity of the structure and require **immediate intervention**. These are typically caused by foundation settlement, excessive load, or material failure. **Professional assessment is advised.**"
elif "Moderate" in severity:
return "β οΈ This crack is classified as **Moderate**. While not immediately critical, it suggests progressive structural movement or material fatigue. **Monitoring and remedial measures**, such as crack sealing or reinforcement, should be considered."
else:
return "β
This crack is **Minor** and likely due to **surface shrinkage or thermal expansion**. While not structurally concerning, periodic monitoring is recommended to ensure it does not propagate further."
def main():
st.set_page_config(page_title='ποΈ Structural Integrity Analyst', layout='wide', initial_sidebar_state='expanded')
# Custom Styling
st.markdown(
"""
<style>
.title {
text-align: center;
font-size: 36px;
font-weight: bold;
color: #003366;
}
.subheader {
font-size: 24px;
font-weight: bold;
color: #00509E;
}
</style>
""", unsafe_allow_html=True
)
st.markdown("<h1 class='title'>ποΈ Structural Integrity Analyst</h1>", unsafe_allow_html=True)
st.sidebar.header("π Upload Crack Image")
uploaded_file = st.sidebar.file_uploader("Choose an image...", type=["jpg", "jpeg", "png"])
if uploaded_file is not None:
image = Image.open(uploaded_file)
image = np.array(image)
edges, crack_data = analyze_crack(image)
# Organize layout
col1, col2 = st.columns(2)
with col1:
st.markdown("<h2 class='subheader'>πΈ Uploaded Image</h2>", unsafe_allow_html=True)
st.image(uploaded_file, caption="Uploaded Image", use_column_width=True)
with col2:
st.markdown("<h2 class='subheader'>π Processed Crack Detection</h2>", unsafe_allow_html=True)
fig, ax = plt.subplots()
ax.imshow(edges, cmap='gray')
ax.axis("off")
st.pyplot(fig)
# Data Analysis
data = pd.DataFrame(crack_data)
st.markdown("<h2 class='subheader'>π Crack Metrics & Classification</h2>", unsafe_allow_html=True)
st.dataframe(data.style.applymap(lambda val: 'background-color: #FFDDC1' if 'Major' in str(val) else ('background-color: #FFF3CD' if 'Moderate' in str(val) else 'background-color: #D4EDDA')))
# Description of Cracks
st.markdown("<h2 class='subheader'>π Crack Analysis & Recommendations</h2>", unsafe_allow_html=True)
for _, row in data.iterrows():
st.markdown(f"**Crack at (X: {row['X']}, Y: {row['Y']})** - {generate_description(row['Severity'])}")
# Discussion
st.markdown("<h2 class='subheader'>π‘ Discussion on Crack Severity</h2>", unsafe_allow_html=True)
st.write("- π΄ **Major:** Significant structural impact, requires **immediate repair and engineering assessment.**")
st.write("- π **Moderate:** Moderate concern, monitoring required, may need **localized reinforcement.**")
st.write("- π’ **Minor:** Surface-level cracks, **not structurally critical** but should be observed over time.")
# Visualization
fig1 = px.histogram(data, x="Length", color="Severity", title="π Crack Length Distribution", nbins=10, color_discrete_map={"π΄ Major": "red", "π Moderate": "orange", "π’ Minor": "green"})
fig2 = px.histogram(data, x="Width", color="Severity", title="π Crack Width Distribution", nbins=10, color_discrete_map={"π΄ Major": "red", "π Moderate": "orange", "π’ Minor": "green"})
st.plotly_chart(fig1, use_container_width=True)
st.plotly_chart(fig2, use_container_width=True)
if __name__ == "__main__":
main()
|