source: tol/tolbaseBLT/lib/mkWidgets1.3/Aclock.tcl @ 56ade3b

1941-docker-image-to-testdevel
Last change on this file since 56ade3b was 56ade3b, checked in by Jorge Pérez <josp.jorge@…>, 10 years ago

fixes #1932, se ha creado la rama trunk/tolbaseBLT copia de trunk/tolbase

git-svn-id: ​https://www.tol-project.org/svn/tolp/trunk@7330 be4846ae-f051-483a-831f-b64e7d08527f

  • Property mode set to 100644
File size: 8.3 KB
RevLine 
[56ade3b]1package require Metawidget
2
3# name: Clock
4# args: args: option-value pairs
5# defines icons for the left/right arrows. creates the internal widgets and
6# all bindings for scrolling.
7metawidget create Aclock {
8  if { ! [ourinfo exists pLeft] } {
9    our pPrev [image create bitmap -data {
10      #define _width 5
11      #define _height 9
12      static char _bits[] = { 0x10,0x18,0x1c,0x1e,0x1f,0x1e,0x1c,0x18,0x10 };
13    }]
14    our pNext [image create bitmap -data {
15      #define _width 5
16      #define _height 9
17      static char _bits[] = { 0x01,0x03,0x07,0x0f,0x1f,0x0f,0x07,0x03,0x01 };
18    }]
19
20    our fPi [expr 2*acos(0)]
21  }
22
23  pack [frame $this.ctrl -border 1 -relief raised] -fill x
24  pack [label $this.ctrl.prev -border 0 -image [our pPrev]] -ipadx 4 -side left -fill y
25  pack [entry $this.ctrl.cuti -border 0 -bg white -width 0 -textvar ::${this}::sTime] -ipady 1 -side left -expand 1
26  pack [label $this.ctrl.next -border 0 -image [our pNext]] -ipadx 4 -side right -fill y
27  pack [canvas $this.time] -fill both -expand 1
28
29  bind $this.ctrl      <Double-1>        "$this set"
30  bind $this.ctrl.prev <1>               "$this _scroll -1"
31  bind $this.ctrl.next <1>               "$this _scroll  1"
32  bind $this.ctrl.prev <Control-1>       "$this _scroll -60"
33  bind $this.ctrl.next <Control-1>       "$this _scroll  60"
34  bind $this.ctrl.prev <ButtonRelease-1> "$this _scroll 0"
35  bind $this.ctrl.next <ButtonRelease-1> "$this _scroll 0"
36  bind $this.ctrl.cuti <Return>          "$this set \[$this.ctrl.cuti get\]"
37  bind $this.ctrl.cuti <Up>              "$this scroll -1"
38  bind $this.ctrl.cuti <Down>            "$this scroll  1"
39  bind $this.ctrl.cuti <Control-Left>    "$this scroll -60"
40  bind $this.ctrl.cuti <Control-Right>   "$this scroll  60"
41  bind $this.time      <Configure>       "$this _drawClock"
42
43  -font [$this.ctrl.cuti cget -font]
44  -controls top
45
46  my -format %H:%M
47
48  _drawClock
49  set_
50
51  focus $this.ctrl.cuti
52} {} -default time
53
54# name: _scroll
55# args: iStep: step width
56# scrolls and asynchronuously calls the function again by means of a timer,
57# as long as the mouse button is pressed. if released, iStep is zero and
58# the last timer job is cancelled.
59metawidget proc Aclock _scroll { iStep } {
60  if { $iStep == 0 } {
61    catch { after cancel [my iJob] }
62  } else {
63    scroll $iStep
64    my iJob [after 50 $this _scroll $iStep]
65  }
66}
67
68# name: _t2c
69# args: iDegrees: degrees
70#       iRadius: radius in pixel
71# transforms polar coordinates into rectangular (x/y) coordinates.
72metawidget proc Aclock _t2c { iDegrees iRadius } {
73  set iX [expr round(cos(($iDegrees-90)/360.*2*[our fPi])*$iRadius)+[my iX0]]
74  set iY [expr round(sin(($iDegrees-90)/360.*2*[our fPi])*$iRadius)+[my iY0]]
75  return [list $iX $iY]
76}
77
78# name: _drawClock
79# args: -
80# draws the clock in the canvas. called on init and when resized.
81metawidget proc Aclock _drawClock {} {
82  # center and radiuses for dial, minute and hour pointer.
83  my iX0 [expr [winfo width  $this.time]/2]
84  my iY0 [expr [winfo height $this.time]/2]
85  set iR0 [expr int(([my iX0]<[my iY0]?[my iX0]:[my iY0])*.9)]
86
87  my iRm [expr int($iR0*.9)]
88  my iRh [expr int($iR0*.7)]
89  my iRp [expr int($iR0*.1)]
90
91  $this.time delete all
92
93  # draw dial elements
94  for { set i 0 } { $i < 360 } { incr i 30 } {
95    mkw.lassign [_t2c $i $iR0] iX iY
96    $this.time create arc [expr $iX-1] [expr $iY-1] [expr $iX+2] [expr $iY+2] -start 225 -extent 180 -style arc -outline white
97    $this.time create arc [expr $iX-1] [expr $iY-1] [expr $iX+2] [expr $iY+2] -start 45 -extent 180 -style arc -outline gray40
98  }
99
100  # create polygon. coordinates set by _setClock
101  eval $this.time create polygon 0 0 0 0 0 0 -fill white -tags tHour
102  eval $this.time create polygon 0 0 0 0 0 0 -fill black -tags tMinute
103
104  # pointers can be dragged nicely
105  $this.time bind tMinute <B1-Motion> "$this _turn M %X %Y"
106  $this.time bind tHour   <B1-Motion> "$this _turn H %X %Y"
107
108  if { [myinfo exists iMinute] } {
109    _setClock
110  }
111}
112
113# name: _setClock
114# args: -
115# draws the pointers by calculating and setting the coordinates for the two
116# polygons.
117metawidget proc Aclock _setClock {} {
118  set iM [expr [my iMinute]*6]
119  set iH [expr round(([my iHour]+[my iMinute]/60.)*30)]
120
121  eval $this.time coords tHour \
122  [_t2c [expr $iH-90] [my iRp]] [_t2c $iH [my iRh]] \
123  [_t2c [expr $iH+90] [my iRp]] [_t2c [expr $iH+180] [my iRp]]
124
125  eval $this.time coords tMinute \
126  [_t2c [expr $iM-90] [my iRp]] [_t2c $iM [my iRm]] \
127  [_t2c [expr $iM+90] [my iRp]] [_t2c [expr $iM+180] [my iRp]]
128
129  set iClock [clock scan [expr ([my iHour]?[my iHour]:12)]:[my iMinute][my sAmpm]]
130  my sTime [clock format $iClock -format [my -format]]
131}
132
133# name: _turn
134# args: sWhat: M for minute, H for hour pointer
135#       iPx, iPy: mouse pointer coords when clicked
136# drags a pointer, detects roll-overs over the "12" to toggle between AM
137# and PM, and redraws the pointers.
138metawidget proc Aclock _turn { sWhat iPx iPy } {
139  # mouse position relative to clock center
140  set iX [expr $iPx-[winfo rootx $this.time]-[my iX0]]
141  set iY [expr $iPy-[winfo rooty $this.time]-[my iY0]]
142
143  if { $sWhat == "M" } {
144    # transform rectangular coords into polar ones
145    if { $iX > 0 } {
146      set iM [expr (round(60*atan(1.*$iY/$iX)/2/[our fPi])+15)%60]
147    } elseif { $iX < 0 } {
148      set iM [expr (round(60*atan(1.*$iY/$iX)/2/[our fPi])+45)%60]
149    } elseif { $iY > 0 } {
150      set iM 30
151    } else {
152      set iM 0
153    }
154
155    # detect roll-over over "12"
156    if { [my iMinute] >= 45 && $iM <= 15 } {
157      my iHour [expr [my iHour]+1]
158    } elseif { [my iMinute] <= 15 && $iM >= 45 } {
159      my iHour [expr [my iHour]-1]
160    }
161
162    # toggle AM/PM if hour pointer rolled over "12" also.
163    if { [my iHour] < 0 || [my iHour] > 11 } {
164      my sAmpm [mkw.decode [my sAmpm] {AM PM PM AM}]
165    }
166
167    my iMinute $iM
168    my iHour   [expr [my iHour]%12]
169  } else {
170    # transform rectangular coords into polar ones
171    if { $iX > 0 } {
172      set iH [expr (round(12*atan(1.*$iY/$iX)/2/[our fPi])+3)%12]
173    } elseif { $iX < 0 } {
174      set iH [expr (round(12*atan(1.*$iY/$iX)/2/[our fPi])+9)%12]
175    } elseif { $iY > 0 } {
176      set iH 6
177    } else {
178      set iH 0
179    }
180
181    # detect roll-over over "12" and toggle AM/PM
182    if { ( [my iHour] >= 9 && $iH <= 3 ) || ( [my iHour] <=3 && $iH >=9 ) } {
183      my sAmpm [mkw.decode [my sAmpm] {AM PM PM AM}]
184    }
185
186    my iHour $iH
187  }
188
189  _setClock
190}
191
192# name: -controls
193# args: sPos: controls position: top or bottom
194# packs the control frame according to the option
195metawidget proc Aclock -controls { sPos } {
196  my -controls [mkw.complete $sPos {top bottom}]
197  pack $this.ctrl -side [my -controls]
198}
199
200# name: -format
201# args: sFormat: format accepted by "clock format"
202# option member. stores a new format.
203metawidget proc Aclock -format { sFormat } {
204  my -format $sFormat
205  _setClock
206}
207
208# name: -font
209# args: sFont: font to set
210# member option. sets the font in the control frame.
211metawidget proc Aclock -font { sFont } {
212  $this.ctrl.cuti config -font $sFont
213}
214
215# name: get
216# args: -
217# returns the date formatted according to -format
218metawidget proc Aclock get {} {
219  return [my sTime]
220}
221
222# name: set
223# args: sTime: time to set
224# sets the clock to a given time.
225metawidget proc Aclock set_ { {sTime {}} } {
226  if { $sTime == {} } {
227    set iClock [clock seconds]
228  } else {
229    set iClock [clock scan $sTime]
230  }
231
232  regsub {^0} [clock format $iClock -format %I] {} iH
233  regsub {^0} [clock format $iClock -format %M] {} iM
234  my sAmpm    [clock format $iClock -format %p]
235  my iHour   $iH
236  my iMinute $iM
237
238  _setClock
239}
240
241# name: scroll
242# args: iStep: minutes
243# sets the clock iStep minutes forward or backward.
244metawidget proc Aclock scroll { iStep } {
245  set iClock [clock scan [my sTime]]
246  incr iClock [expr $iStep*60]
247  set_ [clock format $iClock -format %H:%M]
248}
249
250# name: bind
251# args: args: same as for the bind command
252# applies bindings to the text widget.
253metawidget proc Aclock bind_ { args } {
254  eval bind $this.ctrl.cuti $args
255}
256
257metawidget command Aclock _turn      _turn
258metawidget command Aclock _scroll    _scroll
259metawidget command Aclock _drawClock _drawClock
260
261metawidget command Aclock bind       bind_
262metawidget command Aclock scroll     scroll
263metawidget command Aclock set        set_
264metawidget command Aclock get        get
265
266metawidget option  Aclock -format    -format
267metawidget option  Aclock -control   -control
268metawidget option  Aclock -font      -font
269
270proc test {} {
271  console show
272  pack [aclock .clock] -fill both -expand 1
273}
274
275#test
Note: See TracBrowser for help on using the repository browser.