Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion skills/beamletopticsprojects/FORMAT.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,8 @@ One line per entry; components first, then sources, then groups, then systems:
from that method when a person changes the shape on its card (see "Own code" in `SKILL.md`).
- `pos` is the absolute position (m), `rot` the rotation since construction in **degrees** (unlike
BeamletOptics, whose rotations take radians): first about the global x-axis, then y, then z. Both
are optional.
are optional. `pos` moves the object there from wherever its code builds it, also a source with a
start in its code; a line without `pos` keeps the position of its code.
- `catalog = (...)` belongs to the GUI (its page "Edit"); delete it when you change the constructor.
- `@system`: members are components; a component may be in several systems, a source in at most one.
`static = true` makes a `StaticSystem`. Each system is traced on its own (`trace(p, :S1)`); a detector that is in several systems is the exception in the window, which adds up their hits.
Expand Down
5 changes: 4 additions & 1 deletion skills/beamletopticsprojects/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,10 @@ Bench/
label = "fold", systems = [:S1], by = "claude")`: picks the next free id of its prefix in the
same write (no other participant can take it meanwhile) and returns it; a source goes into
the `sources` of one system. `pos` is in m, `rot` in degrees (not radians as in
BeamletOptics); the prefixes of the ids are listed in `FORMAT.md`.
BeamletOptics); the prefixes of the ids are listed in `FORMAT.md`. `pos` places the object
exactly, also a beam whose code has a start of its own; without `pos` it stays where its code
builds it, e.g. `add!(".", "Beam([0.0, -0.05, 0.0], [0.0, 1.0, 0.0], 1.064e-6)")` starts at
y = −0.05 m.
- `set!(".", :L9; pos, rot, code, label, by)` changes only the given fields of a line (a group:
its label; move groups with `move!`).
- `move!(".", [:G1, :FIOS1]; offset = (0.3, 0, 0), rot = (0, 0, 10), pivot = :center, by)` moves
Expand Down
8 changes: 5 additions & 3 deletions src/Edit.jl
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ Adding, changing, copying and removing lines of system.jl with checks, in one wr
=#

"""
add!(dir, code::AbstractString; id = nothing, pos = (0, 0, 0), rot = (0, 0, 0), label = nothing,
add!(dir, code::AbstractString; id = nothing, pos = nothing, rot = (0, 0, 0), label = nothing,
systems = Symbol[], by = nothing) -> Symbol

Adds a line for the object built by `code` (a constructor, e.g. `"RoundPlanoMirror(0.0254, 0.006)"`)
Expand All @@ -14,7 +14,9 @@ is a beam or a beam group, else a `@component`.
[`id_prefix`](@ref)), chosen in the same load and write, so no other participant can take it in
between; a given `id` that is taken throws. `pos` (in m) and `rot` (angles in degrees or a 3×3
matrix, see [`rotation_matrix`](@ref)) are the pose of the line, `label` the name shown instead of
the id. The new line becomes a member of the `systems` (ids of systems); a source goes into the
the id. `pos` places the object exactly, also one whose code has a position of its own (e.g. the
start of a beam); without `pos` the object stays where its code builds it, and the line has no
`pos`. The new line becomes a member of the `systems` (ids of systems); a source goes into the
`sources` of at most one system.

The changed project is checked before anything is written: the code builds in the module of the
Expand All @@ -36,7 +38,7 @@ add!(".", "Beam([0.0, 0.0, 0.0], [0.0, 1.0, 0.0], 1.064e-6)"; systems = [:S1])
add!(dir::AbstractString, code::AbstractString; kwargs...) =
_retry_changed(() -> _add_once!(dir, code; kwargs...))

function _add_once!(dir::AbstractString, code::AbstractString; id = nothing, pos = (0, 0, 0),
function _add_once!(dir::AbstractString, code::AbstractString; id = nothing, pos = nothing,
rot = (0, 0, 0), label = nothing, systems = Symbol[], by = nothing)
p = load_project(dir)
what = isnothing(id) ? "the new line" : "`$id`"
Expand Down
13 changes: 11 additions & 2 deletions test/TestEdit.jl
Original file line number Diff line number Diff line change
Expand Up @@ -94,10 +94,11 @@ end
@test maximum(abs, BMO.position(p[:M3]) - [0.1, 0.4, 0.0]) ≤ 1e-15
@test occursin("@component M3 = RoundPlanoMirror(0.0254, 0.006) pos = (0.1, 0.4, 0.0) rot = (0.0, 0.0, 45.0) uid",
String(text(dir)))
# zero angles are no rotation
# zero angles are no rotation; without `pos` the line has none, the object stays as built
@test P.add!(dir, "Detector(0.01)"; label = "Camera") === :D2
p = load_project(dir)
@test entry(p, :D2).rot === nothing && entry(p, :D2).pos == (0.0, 0.0, 0.0)
@test entry(p, :D2).rot === nothing && entry(p, :D2).pos === nothing
@test BMO.position(p[:D2]) == [0.0, 0.0, 0.0]
@test entry(p, :D2).label == "Camera"

id = P.add!(dir, "Beam([0.0, 0.0, 0.0], [1.0, 0.0, 0.0], 6.33e-7)"; pos = (0.0, 0.0, 0.01),
Expand All @@ -109,6 +110,14 @@ end
# a given id that is free
@test P.add!(dir, "Detector(0.01)"; id = :Cam) === :Cam
@test has(load_project(dir), :Cam)
# a source whose code has a start of its own starts there without `pos` (#11), and at `pos`
# with it
id = P.add!(dir, "GaussianBeamlet([0.0, -0.1, 0.0], [0.0, 1.0, 0.0], 1e-6, 1e-3)")
p = load_project(dir)
@test entry(p, id).pos === nothing && BMO.position(p[id]) ≈ [0.0, -0.1, 0.0]
@test !occursin("pos =", only(filter(l -> startswith(l, "@source $id ="), split(String(text(dir)), '\n'))))
id = P.add!(dir, "GaussianBeamlet([0.0, -0.1, 0.0], [0.0, 1.0, 0.0], 1e-6, 1e-3)"; pos = (0.0, 0.2, 0.0))
@test BMO.position(load_project(dir)[id]) ≈ [0.0, 0.2, 0.0]
end

@testset "a taken id, a source in two systems" begin
Expand Down
Loading