|
| 1 | +#lang racket |
| 2 | +(require plot racket/gui/base racket/draw rackunit) |
| 3 | + |
| 4 | +;; 2D interactive plots would occasionally thrown an exception if the user |
| 5 | +;; clicked on the plot. This was because the system would interpret it as a |
| 6 | +;; drag-select operation which started and finished at the same place, |
| 7 | +;; resulting in an empty selection -- empty selections are represented using |
| 8 | +;; +nan.0, which cannot be converted to an exact number. |
| 9 | +;; |
| 10 | +;; In this test we simulate an empty selection using mouse events sent |
| 11 | +;; directly to the snips `on-event` method. |
| 12 | + |
| 13 | +(define empty-selection-zoom |
| 14 | + (test-suite |
| 15 | + "empty-selection-zoom" |
| 16 | + (test-case "empty-selection-zoom" |
| 17 | + |
| 18 | + ;; Scaffolding, construct a pasteboard to hold our plot snip |
| 19 | + (define tl (new frame% [label "hello"] [width 800] [height 600])) |
| 20 | + (define pb [new pasteboard%]) |
| 21 | + (define editor (new editor-canvas% [parent tl] [editor pb])) |
| 22 | + |
| 23 | + ;; Construct the plot snip and add it to the pasteboard so it has an |
| 24 | + ;; administrator. |
| 25 | + (define snip (plot-snip (function sin -3 3))) |
| 26 | + (send pb insert snip) |
| 27 | + |
| 28 | + ;; Show the frame -- this is not strictly needed, but will ensure that |
| 29 | + ;; all widgets have their proper dimensions set and mouse events will be |
| 30 | + ;; "interpreted" according to correct snip positions. |
| 31 | + (send tl show #t) |
| 32 | + |
| 33 | + ;; Construct a dummy DC and the left-click, drag, left-release events |
| 34 | + ;; which will simulate the drag-selection on the snip. Note that the |
| 35 | + ;; start and end events have the same X, Y coordinates, which will result |
| 36 | + ;; in an empty rectangle being selected. |
| 37 | + (define dc (new record-dc% [width 800] [height 600])) |
| 38 | + (define click (new mouse-event% [event-type 'left-down] [x 10] [y 10])) |
| 39 | + (define drag (new mouse-event% [event-type 'motion] [left-down #t] [x 11] [y 11])) |
| 40 | + (define unclick (new mouse-event% [event-type 'left-up] [x 10] [y 10])) |
| 41 | + |
| 42 | + ;; Send the snip the events -- the snip will think the user is selecting |
| 43 | + ;; a region on the plot. |
| 44 | + (send snip on-event dc 0 0 0 0 click) |
| 45 | + (send snip on-event dc 0 0 0 0 drag) |
| 46 | + (after |
| 47 | + (check-not-exn |
| 48 | + ;; zoom is triggered when the user releases the mouse event -- this |
| 49 | + ;; used to throw an exception as it tried to operate on an empty |
| 50 | + ;; rectangle, containing +nan.0 numbers. |
| 51 | + (lambda () (send snip on-event dc 0 0 0 0 unclick))) |
| 52 | + (send tl show #f))))) |
| 53 | + |
| 54 | +(module+ test |
| 55 | + (require rackunit/text-ui) |
| 56 | + (run-tests empty-selection-zoom)) |
0 commit comments