[racket] Picts in DrRacket

From: Matthew Flatt (mflatt at cs.utah.edu)
Date: Mon Mar 24 16:40:32 EDT 2014

Probably something like this function belongs in `pict`:

;; smoothed : pict -> pict
;;  Produces a pict like `p`, but that always draws in
;;  'smoothed mode
(define (smoothed p)
  (define draw-p (make-pict-drawer p))
  (define p2
    (dc (lambda (dc x y)
          (define s (send dc get-smoothing))
          (send dc set-smoothing 'smoothed)
          (draw-p dc x y)
          (send dc set-smoothing s))
        (pict-width p)
        (pict-height p)))
  (make-pict (pict-draw p2)
             (pict-width p)
             (pict-height p)
             (pict-ascent p)
             (pict-descent p)
             (list p)
             #f
             (pict-last p)))

At Mon, 24 Mar 2014 21:00:37 +0100, Jens Axel Søgaard wrote:
> Hi all,
> 
> DrRacket draws pict values in REPL. It seems DrRacket uses the
> smoothing mode 'aligned.
> 
> Is there a way to change this to 'smooth ?
> 
> Below is a program that draws graphs of functions of a single variable
> using Bezier curves.
> It turns out that the Bezier curves doesn't fit together nicely when
> the smoothing mode
> 'aligned is used. On the bitmap version below this results in a
> slightly jagged appearance.
> If rendered to pdf, it becomes painfully obvious when you zoom.
> 
> If on the other 'smooth is used everything fits nicely together.
> 
> [Does 'aligned move all control points?]
> 
> The program below draws the graph of x^2 in two ways: The first use DrRacket to
> convert a pict to bitmap without touching the smoothing mode, the second
> explicitly set smoothing to 'smooth.
> 
> #lang racket
> (require racket/draw pict)
> 
> (define (f x)     (* x x))
> (define (df/dx x) (* 2 x))
> 
> (struct pt  (x y) #:transparent)              ; point
> (struct vec (x y) #:transparent)              ; vector
> (struct bez (p0 p1 p2 p3) #:transparent)      ; Bezier curve
> 
> (define (vec* k v) ; multiply vector v with constant k
>   (vec (* k (vec-x v)) (* k (vec-y v))))
> 
> (define (pt+ p v)  ; add vector v to point p
>   (pt (+ (pt-x p) (vec-x v)) (+ (pt-y p) (vec-y v))))
> 
> 
> (define (draw-bezs dc bs) ; assumes the end and start points of each curve match
>   (define p (new dc-path%))
>   (match-define (list b0 b. ...) bs)
>   (match-define (bez (pt x0 y0) (pt x1 y1) (pt x2 y2) (pt x3 y3)) b0)
>   (send p move-to x0 y0)
>   (send p curve-to x1 y1 x2 y2 x3 y3)
>   (for ([b b.])
>     (match-define (bez (pt x0 y0) (pt x1 y1) (pt x2 y2) (pt x3 y3)) b)
>     (send p curve-to x1 y1 x2 y2 x3 y3))
>   (send dc draw-path p))
> 
> (define (graph #:samples [n 200])
>   (define-values (xmin xmax ymin ymax) (values -1 1 -1 1))
>   (define ε 1.0e-10)
>   (define (φ x) (pt x (f x)))      ; x -> (x,f(x))
>   (define (τ x) (vec 1 (df/dx x))) ; vector along tangent
>   (define Δx (/ (- xmax xmin) n))
>   (define x0 xmin)
>   (define (xi i) (+ x0 (* i Δx)))
>   (define bs (for/list ([i (in-range 0 (+ n 1))])
>                (define x0 (xi i))
>                (define x3 (xi (+ i 1)))
>                ; See page 7 of:
>                ; http://www.math.ubc.ca/~cass/graphics/manual/pdf/ch6.pdf
>                (bez (φ x0)
>                     (pt+ (φ x0) (vec* (/ Δx  3) (τ x0)))
>                     (pt+ (φ x3) (vec* (/ Δx -3) (τ x3)))
>                     (φ x3))))
>   ; return pict that draws the Bezier curves
>   (dc (lambda (dc x y)
>         (define-values (old-x0 old-y0)           (send dc get-origin))
>         (define-values (old-scale-x old-scale-y) (send dc get-scale))
>         (define old-pen    (send dc get-pen))
>         (send dc set-origin 200 200)
>         (send dc set-scale 200 -200)
>         (send dc set-pen "black" 0 'solid)
>         (draw-bezs dc bs)
>         (send dc set-pen    old-pen)
>         (send dc set-scale  old-scale-x old-scale-y)
>         (send dc set-origin old-x0 old-y0))
>       400 400))
> 
> (define bm (make-object bitmap% 400 400))
> (define bm-dc (new bitmap-dc% [bitmap bm]))
> (send bm-dc set-smoothing 'smoothed)
> 
> (define p (graph #:samples 100))
> (draw-pict p bm-dc 0 0)
> 
> (list p bm)
> 
> 
> --
> Jens Axel Søgaard
> 
> ____________________
>   Racket Users list:
>   http://lists.racket-lang.org/users


Posted on the users mailing list.