cetz-package / cetz

CeTZ: ein Typst Zeichenpaket - A library for drawing stuff with Typst.
https://cetz-package.github.io
GNU Lesser General Public License v3.0
733 stars 34 forks source link

[bug] in the `rotate()` function #600

Closed tapyu closed 1 month ago

tapyu commented 1 month ago

Consider the following MWE:

#import "@preview/cetz:0.2.2": canvas, plot, draw, coordinate, vector
#set page(width: auto, height: auto, margin: .5cm)

#let draw-satelite(height, angle) = {
  draw.group(
      name: "sattelite", {
        draw.set-origin("ground-station.tip")
        draw.translate(x: height*calc.cos(90deg-angle), y: height*calc.sin(90deg-angle))
        draw.rotate(-angle)
          draw.line(
            (-0.2,+0.2),
            (rel: (+0.2,-0.2)),
            (rel: (+0.2,+0.2)),
          )
          draw.circle((rel: (-0.2, 0.07)), radius: (0.5,0.2), name: "antenna-base")
          draw.rect((rel: (0,0.1)), (rel: (1, 1)), name: "body", anchor: "east")
          draw.rect("body.east", (rel: (0.5, 0.5)), anchor: "north")
          draw.rect("body.west", (rel: (-0.5, 0.5)), anchor: "north")
      }
    )
}

#let draw-ground-station() = {
  draw.group(name: "ground-station", {
      draw.line(name:"base", "earth.80deg", (v => vector.add(v, (0,1)), "earth.90deg"), "earth.100deg")

      draw.move-to("base.50%")
      draw.move-to((rel: (y: 1)))
      draw.move-to((rel: (angle: 320deg, radius: 1)))
      draw.arc((), start: 320deg, stop: 220deg, mode: "CLOSE", name: "antenna-arc")

      draw.anchor("tip", (rel: (0, 0.4), to: "antenna-arc.chord-center"))

      draw.line("tip", (rel:(0.2,0), to: "antenna-arc.chord-center"))
      draw.line("tip", (rel:(-0.2,0), to: "antenna-arc.chord-center"))
  })
}

#canvas({
  draw.arc((0,0), start: 45deg, stop: 135deg, radius: 5, name: "earth")

  draw-ground-station()
  draw-satelite(5, 26deg)
})

This produces

image

There is a crazy bug when draw-satelite(5, 26deg) is changed by draw-satelite(5, 25deg)

image

I am almost sure that is an internal problem with the Cetz package as any variation around 25deg produces very different positions, as if there is a numeric issue when the rotation() function is applied to the group.

johannes-wolf commented 1 month ago

Fixed with #582.

johannes-wolf commented 1 month ago

Workaround for current 0.2.2:

draw.set-ctx(ctx => {
  ctx.transform = ctx.transform.map(r => r.map(calc.round.with(digits: 6)))
  return ctx
})

Place this after rotate/translate and before drawing.