BOX, SPHERE, and CYLINDER build truck topology solids and tessellate
them into MeshModels stored alongside a Solid3D placeholder entity so
the GPU mesh pipeline renders them immediately.
EXTRUDE picks any closed 2D profile (Circle, LwPolyline, etc.),
attaches a planar face via try_attach_plane, and translational-sweeps
it (tsweep Face → Solid) along Z by the given height.
REVOLVE picks a profile, two axis points, and an angle (default 360°),
then rotational-sweeps the wire (rsweep) around the axis.
Three new CmdResult variants drive the operations:
CommitSolid3D, ExtrudeEntity, RevolveEntity.
Scene::layer_color() added to retrieve the active layer's RGBA color.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
REFEDIT picks an INSERT, extracts the block entities into model space
with the INSERT transform applied (translate + rotate + uniform scale),
and enters an editing session. Any normal modify command works on the
temporary entities.
REFCLOSE SAVE applies the inverse transform, replaces the block
definition, and rebuilds all derived caches (hatch/image/mesh), so
every INSERT of that block reflects the edits immediately.
REFCLOSE DISCARD removes the temp entities without changing the block.
Non-uniform-scale inserts are rejected with an error message.
RefEditSession is stored on DocumentTab; undo snapshots bracket the
begin and close operations.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Exports all tessellated 3D mesh models in the current drawing to a
binary STL file via a save-file dialog. Normals are taken from the
MeshModel where available, otherwise computed from triangle vertices.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Three-dimensional rectangular array: prompts for rows, columns, levels
and their respective spacings, then generates copies translated along
X (columns), Z (rows in drawing plane), and Y (levels / height).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Viewport right-click now shows a proper widget-based context menu:
- When a command is active: Cancel / Enter
- Otherwise: Repeat last commands, Delete/Move/Copy (if selected),
Select All, Zoom Extents
CONSTRUCTIONLINE added as an alias for XLINE (XL).
Canvas-drawn placeholder removed; context menu closes on Escape,
click-outside, or when any action is taken.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- ordinate_dim.rs: OrdinateDimCommand picks feature point then leader
endpoint; auto-detects X vs Y ordinate from movement direction
- Ordinate dim added to the Dimensions dropdown in the Annotate ribbon
- ROADMAP.md: DIMORDINATE ✅, Named UCS (already implemented) ✅
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- attedit.rs: AtteditCommand picks an INSERT entity then iterates through
each attribute tag prompting for a new value (Enter keeps existing)
- attedit_pending_handle() / attedit_set_attrs() trait methods inject
attribute data into the command after entity-pick (avoids document access
in the command itself)
- cmd_result.rs: NeedPoint handler injects attr data; ReplaceEntity detects
the __ATTEDIT__ sentinel and calls apply_attedit() on the document
- apply_attedit() encodes tag/value pairs as __ATTEDIT__tag\x01val\x02...
- ROADMAP.md: ATTEDIT marked ✅
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- splinedit.rs: SplineditCommand picks a spline (entity-pick phase) then
accepts CLOSE/OPEN/REVERSE/EXIT sub-commands via text input
- apply_spline_op() mutates the spline in the document directly, with knot
vector regeneration via generate_clamped_knots()
- Sentinel XLine trick: ReplaceEntity with a magic __SPLINEDIT_* layer name
is intercepted in cmd_result.rs before erasing the original entity
- Control-point dragging already works via the existing grip editing system
- ROADMAP.md: SPLINEDIT marked ✅
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- src/modules/insert/wblock.rs: extract_block_to_doc() copies a named
block's entities into a fresh CadDocument; extract_entities_to_doc()
does the same for a selection set; layer definitions are carried over
- WBLOCK <name> writes the named block; WBLOCK * writes selected entities
- WblockSave / WblockSaveResult messages drive the async save-dialog flow
- ROADMAP.md: 1.10 WBLOCK marked ✅
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add HATCHEDIT (HE alias) command. Works on pre-selected hatch or via
entity pick. Accepts text options: P <pattern>, S <scale>, A <angle>.
Enter applies changes; rebuilds hatch entity and GPU model via add_hatch.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add DDEDIT (ED alias) command that edits Text/MText/Attribute entities
in-place via the command line. Double-clicking a text entity in model space
now auto-launches DDEDIT for that entity. Supports Text, MText,
AttributeDefinition, and AttributeEntity types.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Computes mass properties for selected entities and prints results to the
command line. Supports: Circle (area+perimeter), Arc (sector area+arc length),
Line (length), LwPolyline (shoelace area+perimeter+centroid), Ellipse
(numerical 256-pt integration for area and arc length).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Standard AutoCAD aliases now dispatch to the existing RECT and POLY
commands respectively, so users familiar with AutoCAD naming find
them without modification.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Scene now carries bg_color / paper_bg_color fields (defaults match
previous hard-coded values). synced_hatch_models() reads these instead
of hard-coded constants, so Wipeout fills correctly use the custom
background when BACKGROUND <r> <g> <b> has been set.
BACKGROUND command syncs both DocumentTab.bg_color and scene.bg_color.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- src/entities/shape.rs: diamond marker at insertion point (SHX glyphs
cannot be rendered without the binary .shx file, so a placeholder is used)
- Grips: single insertion-point grip
- Properties: Name, Style (read-only), Insert X/Y/Z, Size, Rotation
- Transformable: translate, mirror, scale, rotate
- Registered in entities/mod.rs, entities/traits.rs, app/commands.rs
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- DocumentTab: bg_color / paper_bg_color Optional<[f32;4]> fields
- view.rs: use custom color when set, fall back to defaults
- BACKGROUND <r> <g> <b>: set model or paper-space background (0–255 RGB)
- BACKGROUND RESET: restore default dark grey / paper grey
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- STYLE DIALOG / TEXTSTYLE DIALOG opens the Text Style Font Browser
- Three-panel dialog: style list | built-in CXF font list | properties
- Properties panel: font file text field, width factor, oblique angle
- Apply button commits edits; Set Current sets the active text style
- Built-in font picker (20 CXF fonts from assets/fonts/) auto-applies
font to the selected style on click
- Preview pane shows "AaBbCc 0123" sample text
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- TABLESTYLE/TS command: LIST, NEW subcommands for managing table styles
- Table Style Manager dialog: style list with details panel showing
name, margins, suppression flags, and row styles (data/header/title)
with text style, height, and alignment per row type
- New / Delete buttons in the dialog
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- MLSTYLE command: LIST, NEW, SET, DEL subcommands
- Multiline Style Manager dialog: style list, element details (offset,
color, linetype), Set Current / New / Delete buttons
- MLINE/ML command now reads document header.multiline_style to apply
the current style to newly created MLine entities
- MlineCommand.with_style() constructor for style-aware multiline drawing
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- src/io/plot_style.rs: PlotStyleTable and PlotStyleEntry data structures;
CTB reader (deflate/zlib decompressed text format) with ACI→RGB and
ACI→lineweight lookup; CTB writer (zlib compressed); LW_TABLE constant
- src/io/pdf_export.rs: accept optional PlotStyleTable; apply ACI color
and lineweight overrides during PDF rendering
- src/scene/wire_model.rs: add `aci: u8` field to carry ACI index
- src/scene/render.rs: render_style() now returns ACI alongside RGBA
- src/scene/mod.rs + tessellate.rs: propagate aci through wire building
- app: PlotStyleLoad/Loaded/Clear messages and handlers;
PLOTSTYLE LOAD | CLEAR | STATUS command; active_plot_style state on H7CAD
- flate2 added as dependency
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add DimStyleDialogOpen/Close/Apply/Select/Tab/New/SetCurrent/Delete
messages and DsEdit/DsToggle with DsField enum for fine-grained edits
- Store active dialog state (selected style, current tab, edit buffers)
directly on H7CAD for all 28 most-used DimStyle properties
- dimstyle_overlay: 5-tab modal panel (Lines, Arrows, Text,
Scale/Units, Tolerances) with style list, Apply and Close buttons
- DIMSTYLE / DDIM with no sub-command now opens the dialog;
DIMSTYLE LIST / NEW / SET sub-commands remain available
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add `active_ucs: Option<Ucs>` per-tab state to DocumentTab
- Add `ucs_to_wcs`, `wcs_to_ucs`, `ucs_z_axis`, `ucs_rotated_z` helpers
- Add `Camera::pick_on_plane` for ray–plane intersection against any plane
- Mouse picks project onto the active UCS XY plane instead of world XY
- Typed coordinates are converted from UCS space to WCS before dispatch
- UCS command now really activates/deactivates a UCS:
- `UCS W` resets to WCS (clears active_ucs)
- `UCS <name>` activates a named UCS
- `UCS SAVE <name>` saves the current active UCS
- `UCS ORIGIN x,y,z` shifts origin (in current UCS space)
- `UCS X/Y/Z <angle>` rotates the UCS around its own axes
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Screen-space UCS icon drawn on the existing selection canvas overlay.
Axes are projected from world space so the icon rotates with the camera,
always showing the correct X/Y/Z orientation relative to the drawing plane.
Each axis has its canonical color (X=red, Y=green, Z=blue) with arrowheads.
Icon visibility controlled by show_ucs_icon flag (default on); toggled by
UCSICON ON/OFF command which also updates paper-space viewport entities.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
LIST (LI) now shows per-type details:
- Line: from/to coordinates + length
- Circle: center + radius + area
- Arc: center + radius + start/end angles
- LwPolyline: vertex count, closed flag, elevation
- Text/MText: content preview + height + insertion point
- Insert: block name + position + scale + rotation
- Spline: control point count + degree + closed flag
- Ellipse: center + major length + minor ratio
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
DIMALIGNED: 3-click flow (p1 → p2 → dim line position) → DimensionAligned.
Rubber-band preview shows extension lines and dim line offset.
DIMDIAMETER: 3-click flow (center → arc point → text position) → DimensionDiameter.
Previews the diameter chord line.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Pastes clipboard entities without translating to a pick point.
Useful for pasting between drawings at exact original positions.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
ZOOM ALL (ZA) — fit all entities (alias for ZOOM EXTENTS)
ZOOM SCALE <n> (ZS) — set zoom factor (1/n multiplied to camera distance)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
QSELECT TYPE <type> — select all entities of given type (e.g. LINE, CIRCLE)
QSELECT LAYER <name> — select all entities on the given layer
QSELECT COLOR <n|BYLAYER> — select all entities with given color index
QSELECT LINETYPE <name> — select all entities with given linetype
Deselects current selection and replaces with matched entities.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
COUNT — count all entities grouped by type
COUNT LAYER — group by layer name
COUNT TYPE — group by entity type (same as default)
COUNT <layername> — count entities on a specific layer by type
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
FIND <search> — list all Text/MText/Attribute containing search
FIND <search> REPLACE <rep> — replace first occurrence
FINDALL <search> REPLACE <rep> — replace all occurrences
Works on Text, MText, AttributeDefinition, AttributeEntity.
Case-insensitive search; replaces preserving case in replacement.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Entity pick → text input subcommands:
C / CLOSE → set closed flag
O / OPEN → clear closed flag
W <value> → set uniform width on LwPolyline vertices
X / EXIT → cancel
Command stays active after each op (CmdResult::PeditOp) for multiple edits.
Supports LwPolyline and Polyline2D.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Pick vertices, Enter to finish (≥2 pts). Text input while picking:
C / CLOSE → close and commit (≥3 pts)
S <value> → set scale factor (default 1.0)
S alone → prompt for scale then continue
Uses acadrust MLine::from_points / closed_from_points + scale_factor field.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Pick polygon corners, Enter to close. Each edge is subdivided into arc
bumps (bulge = 0.5 ≈ 53° arcs). Result is a closed LwPolyline.
Arc bump length defaults to 1.0 drawing units.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Options via text input after entity pick:
DE <delta> — extend by delta (negative trims)
TO <total> — set absolute total length / arc length
P <percent> — scale by percentage
<number> — plain number treated as DE delta
Closest end to pick point is modified. Uses CmdResult::LengthenEntity.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Selection-gathering mode: select objects, press Enter to apply.
- Lines: checks collinearity + no-gap, merges into single line span
- Arcs: checks same center/radius + contiguous angles, merges to Arc or Circle
- Uses CmdResult::JoinEntities; geometry computed in cmd_result from document
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
3-step interactive flow:
1. Entity pick (first break point recorded at click location)
2. Optional first point refinement
3. Second break point → CmdResult::BreakEntity applied in cmd_result
Geometry:
- Line: project p1/p2 onto line parameter space → two line fragments
- Arc: project p1/p2 to arc angles → trim CCW from p1 to p2
- Circle: same as Arc, converts Circle → Arc
- LwPolyline: nearest-vertex split → two polyline fragments
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add three classic CAD measurement commands:
- DIST (DI): two-point pick → distance, angle, delta XYZ
- ID: one-point pick → coordinates
- AREA: multi-point polygon pick (Enter to close) → area + perimeter
New CmdResult::Measurement(String) variant ends active command and
prints result to command line without modifying the document.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>