""" Streamlit App for PVD Consolidation Analysis Shows settlement vs time curve """ import streamlit as st import numpy as np import matplotlib.pyplot as plt from pvd_consolidation import PVDConsolidation, SoilLayer, PVDProperties # Page configuration st.set_page_config( page_title="PVD Consolidation Analysis", page_icon="📊", layout="wide" ) # Title st.title("🏗️ PVD Consolidation Analysis") st.markdown("### Settlement vs Time Calculator") # Sidebar for inputs st.sidebar.header("Input Parameters") # Soil Layer Inputs st.sidebar.subheader("Soil Properties") n_layers = st.sidebar.number_input( "Number of Layers", min_value=1, max_value=10, value=1 ) layers = [] for i in range(n_layers): st.sidebar.markdown(f"**Layer {i + 1}**") col1, col2 = st.sidebar.columns(2) with col1: thickness = st.number_input( f"Thickness (m)", min_value=0.1, value=10.0, step=0.5, key=f"thick_{i}" ) Cv = st.number_input( f"Cv (m²/yr)", min_value=0.01, value=0.5, step=0.1, key=f"cv_{i}" ) Ch = st.number_input( f"Ch (m²/yr)", min_value=0.01, value=2.0, step=0.1, key=f"ch_{i}" ) RR = st.number_input( f"RR", min_value=0.001, value=0.05, step=0.01, format="%.3f", key=f"rr_{i}" ) CR = st.number_input( f"CR", min_value=0.001, value=0.30, step=0.01, format="%.3f", key=f"cr_{i}" ) with col2: sigma_ini = st.number_input( f"σ'ini (kPa)", min_value=1.0, value=50.0, step=5.0, key=f"sini_{i}" ) sigma_p = st.number_input( f"σ'p (kPa)", min_value=1.0, value=80.0, step=5.0, key=f"sp_{i}" ) kh = st.number_input( f"kh (m/yr)", min_value=0.1, value=2.0, step=0.1, key=f"kh_{i}" ) ks = st.number_input( f"ks (m/yr)", min_value=0.1, value=1.0, step=0.1, key=f"ks_{i}" ) layers.append( SoilLayer( thickness=thickness, Cv=Cv, Ch=Ch, RR=RR, CR=CR, sigma_ini=sigma_ini, sigma_p=sigma_p, kh=kh, ks=ks, ) ) st.sidebar.markdown("---") # PVD Properties st.sidebar.subheader("PVD Properties") dw = st.sidebar.number_input( "Drain diameter dw (m)", min_value=0.01, value=0.05, step=0.01, format="%.3f" ) ds = st.sidebar.number_input( "Smear zone ds (m)", min_value=0.01, value=0.15, step=0.01, format="%.3f" ) De = st.sidebar.number_input("Unit cell De (m)", min_value=0.1, value=1.5, step=0.1) L_drain = st.sidebar.number_input( "Drain length L (m)", min_value=1.0, value=10.0, step=1.0 ) well_resistance = st.sidebar.selectbox( "Well Resistance", ["Negligible (qw → ∞)", "Custom qw"] ) if well_resistance == "Custom qw": qw = st.sidebar.number_input("qw (m³/yr)", min_value=1.0, value=100.0, step=10.0) else: qw = 1e12 # Very large value for negligible resistance pvd = PVDProperties(dw=dw, ds=ds, De=De, L_drain=L_drain, qw=qw) # Analysis Parameters st.sidebar.subheader("Analysis Parameters") surcharge = st.sidebar.number_input( "Surcharge (kPa)", min_value=1.0, value=100.0, step=10.0 ) t_max = st.sidebar.number_input("Max Time (years)", min_value=0.1, value=2.0, step=0.1) dt = st.sidebar.number_input( "Time Step (years)", min_value=0.001, value=0.01, step=0.001, format="%.3f" ) # Run Analysis Button if st.sidebar.button("🚀 Run Analysis", type="primary"): with st.spinner("Calculating consolidation..."): try: # Create analysis analysis = PVDConsolidation(layers, pvd, surcharge, dt) # Calculate settlement vs time time, settlement = analysis.settlement_vs_time(t_max=t_max, n_points=200) settlement_mm = settlement * 1000 # Convert to mm # Get PVD factors Fn, Fs, Fr = analysis.calculate_pvd_factors() F_total = Fn + Fs + Fr # Store results in session state st.session_state.time = time st.session_state.settlement = settlement_mm st.session_state.Fn = Fn st.session_state.Fs = Fs st.session_state.Fr = Fr st.session_state.F_total = F_total st.session_state.analysis_done = True except Exception as e: st.error(f"Error in analysis: {str(e)}") st.session_state.analysis_done = False # Display Results if hasattr(st.session_state, "analysis_done") and st.session_state.analysis_done: # Main plot - Settlement vs Time st.subheader("Settlement vs Time") fig, ax = plt.subplots(figsize=(12, 6)) ax.plot(st.session_state.time, st.session_state.settlement, "b-", linewidth=2.5) ax.set_xlabel("Time (years)", fontsize=14, fontweight="bold") ax.set_ylabel("Settlement (mm)", fontsize=14, fontweight="bold") ax.set_title( "PVD Consolidation - Settlement vs Time", fontsize=16, fontweight="bold" ) ax.grid(True, alpha=0.3, linestyle="--") ax.tick_params(labelsize=12) # Invert y-axis (settlement goes down) ax.invert_yaxis() # Add final settlement annotation final_settlement = st.session_state.settlement[-1] ax.axhline( y=final_settlement, color="r", linestyle="--", alpha=0.5, label=f"Final Settlement = {final_settlement:.1f} mm", ) ax.legend(fontsize=12) st.pyplot(fig) # Summary statistics st.subheader("Analysis Summary") col1, col2, col3, col4 = st.columns(4) with col1: st.metric("Final Settlement", f"{final_settlement:.1f} mm") with col2: # Find time to 90% consolidation target_settlement = 0.9 * final_settlement idx_90 = np.argmax(st.session_state.settlement >= target_settlement) t_90 = ( st.session_state.time[idx_90] if idx_90 > 0 else st.session_state.time[-1] ) st.metric("Time to 90% U", f"{t_90:.2f} years") with col3: # Find time to 50% consolidation target_settlement = 0.5 * final_settlement idx_50 = np.argmax(st.session_state.settlement >= target_settlement) t_50 = ( st.session_state.time[idx_50] if idx_50 > 0 else st.session_state.time[-1] ) st.metric("Time to 50% U", f"{t_50:.2f} years") with col4: st.metric("Total Resistance F", f"{st.session_state.F_total:.2f}") # PVD Factors st.subheader("PVD Influence Factors") col1, col2, col3 = st.columns(3) with col1: st.metric("Geometric Factor (Fn)", f"{st.session_state.Fn:.3f}") with col2: st.metric("Smear Factor (Fs)", f"{st.session_state.Fs:.3f}") with col3: st.metric("Well Resistance (Fr)", f"{st.session_state.Fr:.3f}") # Download data st.subheader("Download Results") # Prepare CSV data csv_data = "Time (years),Settlement (mm)\n" for t, s in zip(st.session_state.time, st.session_state.settlement): csv_data += f"{t:.4f},{s:.2f}\n" st.download_button( label="📥 Download Settlement Data (CSV)", data=csv_data, file_name="settlement_data.csv", mime="text/csv", ) else: # Initial instructions st.info( "👈 Configure your parameters in the sidebar and click **Run Analysis** to see results" ) st.markdown(""" ### Instructions: 1. **Soil Properties**: Enter the properties for each soil layer - Thickness (m) - Cv: Vertical coefficient of consolidation (m²/year) - Ch: Horizontal coefficient of consolidation (m²/year) - RR: Recompression ratio - CR: Compression ratio - σ'ini: Initial effective stress (kPa) - σ'p: Preconsolidation pressure (kPa) 2. **PVD Properties**: Configure the drain installation - dw: Equivalent drain diameter (m) - ds: Smear zone diameter (m) - De: Equivalent unit cell diameter (m) - L: Drain length (m) - kh: Horizontal permeability (m/year) - ks: Smear zone permeability (m/year) - qw: Well discharge capacity (m³/year) 3. **Analysis Parameters**: - Surcharge: Applied load (kPa) - Max Time: Analysis duration (years) - Time Step: Calculation step size (years) 4. Click **Run Analysis** to calculate and visualize results """) # Footer st.sidebar.markdown("---") st.sidebar.markdown("**PVD Consolidation Calculator**") st.sidebar.markdown("Version 1.0")