Cauchy Desktop

Native FEA Application for 2D Structural Analysis

Mesh. Solve. Visualize. -- A complete finite element analysis workflow in a single application.

Qt 6 • C++20 • Cross-platform
Video Walkthrough Placeholder (1920x1080)

Engineering Design Process

Problem Statement

Commercial FEA tools like Abaqus and ANSYS are powerful, but their black-box nature hides implementation details. A native desktop application provides direct access to the solver internals, custom visualization of intermediate results, and a transparent workflow for educational and prototyping use. The goal is not to replace commercial tools, but to build a working application that demonstrates the full FEA pipeline from mesh generation to stress recovery.

Why Qt 6?

The GUI framework choice was driven by three constraints: direct C++ solver linkage (no IPC overhead), native look and feel, and cross-platform packaging. Qt 6 satisfies all three. The comparison below shows why alternatives were rejected.

Framework Why Not for Cauchy
Dear ImGui No native file dialogs, no dock widgets, custom-only look, less industry recognition
Rust + Tauri C++/Rust FFI overhead makes no sense for a solver-heavy app; two languages to maintain
Flutter Dart/C++ FFI adds complexity; Material Design looks like a phone app on desktop
wxWidgets Sparse documentation, no built-in plotting, manual packaging on macOS
GTK Poor macOS/Windows support, C API is painful from C++, tiny scientific ecosystem

Solver Integration

The desktop application links directly to the existing header-only solver. A SolveConfig struct is populated from the GUI, passed to run_case(), and the returned SolveResult struct feeds into visualization models. No JSON serialization, no process spawning, no IPC -- direct struct passing at function-call speed.

struct SolveConfig {
    CaseType case_type;
    ElementType element_type;
    PlaneType plane_type;
    int nx, ny;
    Material material;
    std::vector<BoundaryCondition> boundary_conditions;
    SolverType solver_type;
    double cg_tolerance;
    int cg_max_iterations;
    bool use_adaptivity;
    int adaptive_iterations;
};

struct SolveResult {
    bool success;
    std::string error_message;
    Mesh mesh;
    std::vector<NodeDisplacement> displacements;
    std::vector<ElementStress> stresses;
    double max_displacement;
    double strain_energy;
    // ... convergence data, timing, etc.
};

Async Execution

Solver runs execute on a dedicated QThread. The main thread remains responsive -- the progress bar updates, the cancel button works, and the viewport stays interactive. The thread emits finished(SolveResult) when complete, and the UI switches to the results view automatically.

Visualization Strategy

All rendering uses QPainter on CPU. For a 2D FEA tool with meshes under 100K elements, CPU rendering is more than sufficient. It avoids GPU driver dependencies, works on headless systems, and produces deterministic output. The tradeoff is acceptable for the target use case: engineering analysis, not real-time gaming.

Cross-Platform Packaging

CMake builds a native .app bundle on macOS, a .desktop entry on Linux, and an NSIS installer on Windows. The same build system produces all three artifacts from a single CMakeLists.txt. No separate build scripts per platform.

Application Walkthrough

Cauchy Desktop provides a complete FEA workflow organized into dockable panels. The left dock handles input (mesh, boundary conditions, materials), the center is the 2D viewport, and the right dock controls the solver and displays results. A collapsible bottom dock holds analysis plots.

a. Mesh Editor

Screenshot: Mesh Editor panel with nx/ny spinboxes, element type selector, mesh grading controls, and quality metrics display

Generate structured Q4 or Q8 meshes with configurable element counts (nx, ny). Mesh grading allows biased element sizing toward edges or corners. Real-time quality metrics show aspect ratio, skewness, and Jacobian ratio for each element before solving.

b. Boundary Condition Editor

Screenshot: Boundary condition editor with node/edge selection, Dirichlet/Neumann toggle, DOF checkboxes, and value input

Point-and-click boundary condition assignment. Select nodes or edges in the viewport, choose Dirichlet (fixed displacement) or Neumann (applied force), pick the active DOFs (ux, uy), and enter the value. Boundary conditions appear as colored symbols on the mesh: yellow triangles for fixed, green arrows for forces.

c. Material Properties

Screenshot: Material properties panel with E, nu, rho, thickness, and thermal expansion fields

Configure material properties for the analysis: Young's modulus (E), Poisson's ratio (ν), density (ρ), thickness (t), and thermal expansion coefficient (α). Preset materials (steel, aluminum, titanium) fill common values. The plane stress/strain toggle adjusts the constitutive matrix automatically.

d. Solver Panel

Screenshot: Solver panel with Cholesky/CG selection, tolerance input, progress bar, and solve/cancel buttons

Choose between Cholesky (direct, for small meshes) or Conjugate Gradient (iterative, for large meshes). Set the CG tolerance and maximum iterations. The progress bar shows assembly and solve phases in real time. The cancel button interrupts the solver mid-run without crashing the application.

e. 2D Viewport

Screenshot: 2D viewport showing deformed mesh with contour coloring, zoomed in on a region of interest

Pan and zoom the mesh with mouse controls. The viewport renders the wireframe mesh, deformed shape (with adjustable scale factor), and contour coloring for any selected field. Toggle between original and deformed configurations. Coordinate axes and grid snapping provide spatial reference.

f. Stress Analysis

Screenshot: Stress contour with Von Mises field, colorbar at bottom, min/max labels

Visualize six stress components: sigma_xx, sigma_yy, sigma_xy, Von Mises, sigma_1 (max principal), and sigma_2 (min principal). Scientific colormaps (turbo, viridis, RdBu_r) ensure perceptual accuracy. The colorbar at the bottom shows the exact min/max range. Nodal stress recovery via superconvergent patch recovery (SPR) provides smooth contours.

g. Principal Stress Arrows

Screenshot: Principal stress arrow overlay on mesh, red/blue arrows at element centroids

Element-based arrow visualization shows the principal stress directions at each element centroid. Red arrows indicate tension (sigma > 0), blue arrows indicate compression (sigma < 0). Arrow length is proportional to stress magnitude. Toggle on/off via the toolbar to reduce visual clutter.

h. Mesh Quality Overlay

Screenshot: Mesh quality heatmap showing aspect ratio per element, red for poor quality, green for good

A color-coded overlay shows mesh quality metrics per element: aspect ratio, Jacobian ratio, and skewness. Red elements indicate poor quality that may affect solution accuracy. This overlay helps identify problematic regions before running the solver, saving computation time on meshes that need refinement.

i. Probe Tool

Screenshot: Probe tool tooltip showing stress/displacement values at clicked point

Click any point in the viewport to read the local stress and displacement values. The probe tool performs ray-casting from the mouse position to the mesh, interpolates shape functions at the hit point, and displays a tooltip with all six stress components, both displacement components, and the element ID. Essential for quick spot-checks without exporting data.

j. Analysis Plots (Bottom Dock)

A collapsible bottom dock contains a QTabWidget with six analysis plots. Each tab provides a different perspective on the solution data, all rendered with custom QPainter widgets.

Tab Widget Description
Stress Distribution StressHistogram Histogram of sigma_xx, sigma_yy, von_mises across all elements
Energy Balance EnergyBalanceChart Bar chart comparing strain energy 0.5*u^T*K*u vs work done 0.5*f^T*u
Displacement Profile DisplacementLineChart uy along top edge of mesh (FEA data points connected by lines)
Load-Displacement LoadDisplacementChart Applied force vs max displacement, accumulates across multiple solves
Error Map ErrorHeatmap Per-element ZZ error indicator rendered as a colored overlay
Convergence ConvergenceChart Log-log plot of mesh refinement convergence (GCI, observed order)
Screenshot: Bottom dock with all 6 analysis tabs, showing the Stress Distribution histogram as the active tab

k. Project Files

Screenshot: File dialog showing .cauchy project file save/load

Save and load complete project state as JSON files with the .cauchy extension. Project files store the mesh, boundary conditions, material properties, solver settings, and results. Reopen a project to resume analysis without re-entering parameters. The JSON format is human-readable and compatible with the existing CLI pipeline.

l. PNG Export

Screenshot: Exported PNG at 1920x1080 showing the viewport with contour, colorbar, and boundary symbols

Export the current viewport state as a high-resolution PNG at 1920x1080. The export includes the mesh contour, colorbar with min/max labels, boundary condition symbols, and title text. Suitable for reports, presentations, and the portfolio website.

Architecture Deep-Dive

System Architecture

+-------------------------------------------------------------+
|                      Cauchy Desktop                         |
+-------------------------------------------------------------+
|                                                             |
|  +------------------+   +------------------+   +----------+ |
|  |   Mesh Editor    |   |  2D Viewport     |   | Solver   | |
|  |   (Left Dock)    |   |  (Center)        |   | Panel    | |
|  |                  |   |                  |   | (Right)  | |
|  |  - nx, ny        |   |  - QPainter      |   |          | |
|  |  - Element type  |   |  - Mesh wire     |   | - Cholesky| |
|  |  - Grading       |   |  - Deformed shape|   | - CG     | |
|  |  - Quality       |   |  - Contours      |   | - Progress| |
|  +------------------+   |  - Arrows        |   | - Cancel  | |
|                         |  - Probes        |   +----------+ |
|  +------------------+   +------------------+                  |
|  |  BC Editor       |          |               +----------+  |
|  |  Material Props  |          |               | Analysis |  |
|  |  (Left Dock)     |          |               | Plots    |  |
|  +------------------+          |               | (Bottom) |  |
|                                |               | - 6 tabs |  |
|                     +----------+----------+    +----------+  |
|                     |   Qt Signal/Slot    |                  |
|                     |   Communication     |                  |
|                     +----------+----------+                  |
|                                |                             |
|                     +----------+----------+                  |
|                     |   Solver Runner     |                  |
|                     |   (QThread)         |                  |
|                     |   - Assembly        |                  |
|                     |   - Solve           |                  |
|                     |   - Postprocess     |                  |
|                     +----------+----------+                  |
|                                |                             |
|                     +----------+----------+                  |
|                     |   Solver Backend    |                  |
|                     |   (Header-only C++) |                  |
|                     |   - fea.hpp         |                  |
|                     |   - elements.hpp    |                  |
|                     |   - sparse.hpp      |                  |
|                     |   - solver.hpp      |                  |
|                     |   - mesh.hpp        |                  |
|                     +---------------------+                  |
+-------------------------------------------------------------+

Component Breakdown

Component File Responsibility
Application Entry main.cpp QApplication setup, style, window creation
Main Window main_window.hpp/cpp QMainWindow with menu, toolbar, dock layout
Mesh Editor mesh_editor.hpp/cpp Mesh generation parameters, quality display
BC Editor bc_editor.hpp/cpp Boundary condition assignment and editing
Viewport viewport_widget.hpp/cpp 2D rendering with QPainter, pan/zoom, overlays
Solver Panel solver_panel.hpp/cpp Solver settings, progress, results summary
Solver Runner solver_runner.hpp/cpp QThread wrapper for async solver execution
Result Model result_model.hpp/cpp QAbstractItemModel for stress/displacement tables
Project I/O project_io.hpp/cpp Save/load .cauchy JSON project files
Convergence Chart convergence_chart.hpp/cpp Log-log mesh refinement convergence plot
Stress Histogram stress_histogram.hpp/cpp Element stress distribution histogram
Energy Balance energy_balance_chart.hpp/cpp Strain energy vs work done bar chart
Probe Tool probe_tool.hpp/cpp Click-to-probe stress/displacement at any point
Mesh Quality Overlay mesh_quality_overlay.hpp/cpp Aspect ratio / Jacobian heatmap overlay

Data Flow

User Input
    |
    v
Mesh Editor / BC Editor / Material Props
    |
    v
SolveConfig (struct)
    |
    v
SolverRunner (QThread)  -->  run_case(config)
    |                            |
    |                            v
    |                       Solver Backend (fea.hpp)
    |                            |
    |                            v
    |                       SolveResult (struct)
    |                            |
    v                            v
Result Model  <-----------  UI Update
    |
    v
Viewport / Analysis Plots / Probe Tool

Thread Model

Thread Responsibility Communication
Main Thread (UI) Event loop, rendering, user input, menu actions Receives signals from solver thread
Solver Thread (QThread) Assembly, solve, postprocess, convergence Emits progress(int), finished(SolveResult), error(QString)

The solver thread is short-lived: created when the user clicks "Solve," destroyed when results are received. No shared state between threads -- the solver reads from a const SolveConfig and returns a new SolveResult. The UI thread never blocks.

Technical Specifications

Specification Detail
Framework Qt 6 (QWidgets)
Language C++20
Solver Header-only, linked directly (no IPC)
Rendering QPainter (CPU), no GPU dependency
Async Execution QThread with progress signals
Project Format JSON (.cauchy), human-readable
Packaging MACOSX_BUNDLE, .desktop, NSIS
Build System CMake with AUTOMOC / AUTORCC / AUTOUIC
Export Resolution 1920x1080 PNG
Colormaps Scientific: turbo, viridis, RdBu_r (never rainbow)
License MIT (consistent with solver backend)

Build & Install

One command builds, installs, and launches the application:

./build-desktop.sh

Under the hood, this script runs:

# Build
cmake -B build-desktop -S . -DCMAKE_BUILD_TYPE=Release
cmake --build build-desktop -j$(nproc)

# Install (macOS: copies to /Applications)
cmake --install build-desktop

# Launch
open /Applications/Cauchy.app  # macOS
# or: ./build-desktop/bin/Cauchy  # Linux

Prerequisites: Qt 6 (Homebrew on macOS, apt on Linux), C++20 compiler (Clang 14+ or GCC 12+), CMake 3.20+.

Comparison with Commercial Tools

Feature Cauchy Desktop Abaqus ANSYS CalculiX
Price Free (MIT) $20K+/year $20K+/year Free (GPL)
Source Code Open source Closed Closed Open source
Element Types Q4, Q8, Bar, T3 200+ elements 200+ elements ~30 elements
3D Support In progress Full 3D Full 3D Full 3D
Nonlinear Planned Full Full Partial
GUI Native Qt 6 Full GUI Full GUI Pre/post only
Adaptive Refinement ZZ estimator Built-in Built-in Manual
API / Scripting JSON + CLI Python (Abaqus API) APDL / Python Keywords
Target Audience Learning / Portfolio Industry / Research Industry / Research Academic

Cauchy Desktop is not a commercial FEA replacement. It is a portfolio piece that demonstrates understanding of element formulation, sparse assembly, solver implementation, and engineering visualization -- skills directly transferable to commercial tool development at companies like SpaceX, Lockheed Martin, or ANSYS.

Verification Checklist

Status Item
Done Solver runs asynchronously without blocking UI
Done Mesh generation produces correct mesh for all 6 cases
Done BC editor assigns and persists boundary conditions correctly
In Progress Results visualization matches web viewer output
In Progress Convergence study produces correct GCI and order of convergence
Planned Project save/load round-trips correctly
Planned Error handling shows user-friendly messages for invalid inputs
Planned Probe tool reads correct stress/displacement values at clicked points
Planned Mesh quality overlay correctly identifies invalid elements
Done Cross-platform build passes on macOS
Planned Installer packages build correctly for all target platforms
Done All existing 22 Google Test cases still pass
Done Stress histogram displays sigma_xx, sigma_yy, von_mises distributions
Done Energy balance chart shows strain energy vs work done
Done Displacement line chart plots uy along top edge
Done Load-displacement chart accumulates across multiple solves
Done Error heatmap renders per-element ZZ error indicators
Done Convergence chart wired into bottom dock
Done macOS .app bundle builds and launches correctly