source: trunk/SRC/ToBeReviewed/WIDGET/COMPOUND_WIDGET/cw_bgroup.pro

Last change on this file was 495, checked in by pinsard, 10 years ago

fix thanks to coding rules; typo; dupe empty lines; trailing blanks

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 12.9 KB
Line 
1;+
2;
3; @file_comments
4;
5; @categories
6; Compound widget
7;
8; @param ID
9;
10; @param VALUE
11; It is the default tick mark value (a floating-point number).
12;
13; @returns
14;
15; @uses
16;
17; @restrictions
18;
19; @examples
20;
21; @history
22;
23; @version
24; $Id$
25;
26;-
27PRO cw_bgroup_setv, id, value
28;
29  compile_opt hidden, idl2, strictarrsubs
30;
31  ON_ERROR, 2                       ;return to caller
32
33  stash = WIDGET_INFO(id, /CHILD)
34  WIDGET_CONTROL, stash, GET_UVALUE=state, /NO_COPY
35
36  case state.type of
37    0: message,'unable to set plain button group value'
38    1: begin
39      WIDGET_CONTROL, SET_BUTTON=0, state.ids[state.excl_pos]
40      state.excl_pos = value
41      WIDGET_CONTROL, /SET_BUTTON, state.ids[value]
42    end
43    2: begin
44      n = n_elements(value)-1
45      for i = 0, n do begin
46        state.nonexcl_curpos[i] = value[i]
47        WIDGET_CONTROL, state.ids[i], SET_BUTTON=value[i]
48      endfor
49    end
50  endcase
51
52  WIDGET_CONTROL, stash, SET_UVALUE=state, /NO_COPY
53end
54
55;+
56; @file_comments
57; Compound widget
58;
59; @categories
60;
61; @param ID
62;
63; @param VALUE
64; It is the default tick mark value (a floating-point number).
65;
66; @returns
67;
68; @uses
69;
70; @restrictions
71;
72; @examples
73;
74; @history
75;
76; @version
77; $Id$
78;
79;-
80FUNCTION cw_bgroup_getv, id, value
81;
82  compile_opt hidden, idl2, strictarrsubs
83;
84  ON_ERROR, 2                       ;return to caller
85
86  stash = WIDGET_INFO(id, /CHILD)
87  WIDGET_CONTROL, stash, GET_UVALUE=state, /NO_COPY
88
89  case state.type of
90    0: message, 'unable to get plain button group value'
91;    1: ret = state.excl_pos
92    1: ret = state.ret_arr[state.excl_pos]
93;    2: ret = state.nonexcl_curpos
94    2: BEGIN
95      index = where(state.nonexcl_curpos NE 0)
96      if index[0] EQ -1 then begin
97        if size(state.ret_arr, /type) EQ 7 then ret = '' ELSE ret = -1
98      ENDIF ELSE ret = state.ret_arr[index]
99    END
100  endcase
101
102  WIDGET_CONTROL, stash, SET_UVALUE=state, /NO_COPY
103
104  return, ret
105
106end
107;
108;+
109;
110; @file_comments
111; Compound widget
112;
113; @categories
114;
115; @param EV
116;
117; @returns
118;
119; @uses
120;
121; @restrictions
122;
123; @examples
124;
125; @history
126;
127; @version
128; $Id$
129;
130;-
131FUNCTION cw_bgroup_event, ev
132;
133  compile_opt hidden, idl2, strictarrsubs
134;
135  WIDGET_CONTROL, ev.handler, GET_UVALUE=stash
136  WIDGET_CONTROL, stash, GET_UVALUE=state, /NO_COPY
137  WIDGET_CONTROL, ev.id, get_uvalue=uvalue
138
139  ret = 1           ;Assume we return a struct
140  case state.type of
141    0:
142    1: if (ev.select eq 1) then begin
143      state.excl_pos = uvalue
144    ENDIF else begin
145      if (state.no_release ne 0) then ret = 0
146    ENDELSE
147    2: begin
148      ; Keep track of the current state
149      state.nonexcl_curpos[uvalue] = ev.select
150          if (state.no_release ne 0) and (ev.select eq 0) then ret = 0
151    end
152  endcase
153
154  if ret then begin     ;Return a struct?
155      ret = { ID:state.base, TOP:ev.top, HANDLER:0L, SELECT:ev.select, $
156           VALUE:state.ret_arr[uvalue] }
157      efun = state.efun
158      WIDGET_CONTROL, stash, SET_UVALUE=state, /NO_COPY
159      if efun ne '' then return, CALL_FUNCTION(efun, ret) $
160      else return, ret
161  endif else begin      ;Trash the event
162      WIDGET_CONTROL, stash, SET_UVALUE=state, /NO_COPY
163      return, 0
164  endelse
165end
166;
167;+
168; @file_comments
169; CW_BGROUP is a compound widget that simplifies creating
170; a base of buttons. It handles the details of creating the
171; proper base (standard, exclusive, or non-exclusive) and filling
172; in the desired buttons. Events for the individual buttons are
173; handled transparently, and a CW_BGROUP event returned. This
174; event can return any one of the following:
175;      - The Index of the button within the base.
176;      - The widget ID of the button.
177;      - The name of the button.
178;      - An arbitrary value taken from an array of User values.
179;
180; @categories
181; Compound widget
182;
183; @param PARENT {in}{required}
184; The ID of the parent widget.
185;
186; @param NAMES {type=string array}
187; A string array, containing one string per button,
188; giving the name of each button.
189;
190; @keyword BUTTON_UVALUE {type=array}
191; An array of user values to be associated with
192; each button and returned in the event structure.
193;
194; @keyword COLUMN
195; Buttons will be arranged in the number of columns
196; specified by this keyword.
197;
198; @keyword EVENT_FUNCT
199; The name of an optional user-supplied event function
200; for buttons. This function is called with the return
201; value structure whenever a button is pressed, and
202; follows the conventions for user-written event functions.
203;
204; @keyword EXCLUSIVE
205; Buttons will be placed in an exclusive base, with
206; only one button allowed to be selected at a time.
207;
208; @keyword FONT
209; The name of the font to be used for the button
210; titles. If this keyword is not specified, the default
211; font is used.
212;
213; @keyword FRAME
214; Specifies the width of the frame to be drawn around the base.
215;
216; @keyword IDS
217; A named variable into which the button IDs will be
218; stored, as a longword vector.
219;
220; @keyword LABEL_LEFT
221; Creates a text label to the left of the buttons.
222;
223; @keyword LABEL_TOP
224; Creates a text label above the buttons.
225;
226; @keyword MAP
227; If set, the base will be mapped when the widget
228; is realized (the default).
229;
230; @keyword NONEXCLUSIVE
231; Buttons will be placed in an non-exclusive base.
232; The buttons will be independent.
233;
234; @keyword NO_RELEASE
235; If set, button release events will not be returned.
236;
237; @keyword RETURN_ID
238; If set, the VALUE field of returned events will be
239; the widget ID of the button.
240;
241; @keyword RETURN_INDEX
242; If set, the VALUE field of returned events will be
243; the zero-based index of the button within the base.
244; THIS IS THE DEFAULT.
245;
246; @keyword RETURN_NAME
247; If set, the VALUE field of returned events will be
248; the name of the button within the base.
249;
250; @keyword ROW
251; Buttons will be arranged in the number of rows
252; specified by this keyword.
253;
254; @keyword SCROLL
255; If set, the base will include scroll bars to allow
256; viewing a large base through a smaller viewport.
257;
258; @keyword SET_VALUE
259; The initial value of the buttons. This is equivalent
260; to the later statement:
261;
262; WIDGET_CONTROL, widget, set_value=value
263;
264; @keyword SPACE
265; The space, in pixels, to be left around the edges
266; of a row or column major base. This keyword is
267; ignored if EXCLUSIVE or NONEXCLUSIVE are specified.
268;
269; @keyword UVALUE
270; The user value to be associated with the widget.
271;
272; @keyword UNAME
273; The user name to be associated with the widget.
274;
275; @keyword XOFFSET
276; The X offset of the widget relative to its parent.
277;
278; @keyword XPAD
279; The horizontal space, in pixels, between children
280; of a row or column major base. Ignored if EXCLUSIVE
281; or NONEXCLUSIVE are specified.
282;
283; @keyword XSIZE
284; The width of the base.
285; @keyword X_SCROLL_SIZE
286; The width of the viewport if SCROLL is specified.
287;
288; @keyword YOFFSET
289; The Y offset of the widget relative to its parent.
290;
291; @keyword YPAD
292; The vertical space, in pixels, between children of
293; a row or column major base. Ignored if EXCLUSIVE
294; or NONEXCLUSIVE are specified.
295;
296; @keyword YSIZE
297; The height of the base.
298;
299; @keyword Y_SCROLL_SIZE
300; The height of the viewport if SCROLL is specified.
301;
302; @returns
303; The ID of the created widget is returned.
304;
305; @restrictions
306; This widget generates event structures with the following definition:
307;
308;       event = { ID:0L, TOP:0L, HANDLER:0L, SELECT:0, VALUE:0 }
309;
310; The SELECT field is passed through from the button event. VALUE is
311; either the INDEX, ID, NAME, or BUTTON_UVALUE of the button,
312; depending on how the widget was created.
313;
314; @restrictions
315; Only buttons with textual names are handled by this widget.
316; Bitmaps are not understood.
317;
318; @history
319; 15 June 1992, AB
320; 7 April 1993, AB, Removed state caching.
321; 6 Oct. 1994, KDB, Font keyword is not applied to the label.
322; 10 FEB 1995, DJC  fixed bad bug in event procedure, getting
323;                         id of stash widget.
324; 11 April 1995, AB Removed Motif special cases.
325;
326; Copyright (c) 1992-2005, Research Systems, Inc.  All rights reserved.
327;   Unauthorized reproduction prohibited.
328;
329; @version
330; $Id$
331;
332;-
333FUNCTION cw_bgroup, parent, names, $
334    BUTTON_UVALUE=button_uvalue, COLUMN=column, EVENT_FUNCT=efun, $
335    EXCLUSIVE=excl, FONT=font, FRAME=frame, IDS=ids, LABEL_TOP=label_top, $
336    LABEL_LEFT=label_left, MAP=map, $
337    NONEXCLUSIVE=nonexcl, NO_RELEASE=no_release, RETURN_ID=return_id, $
338    RETURN_INDEX=return_index, RETURN_NAME=return_name, $
339    ROW=row, SCROLL=scroll, SET_VALUE=sval, SPACE=space, $
340    TAB_MODE=tab_mode, UVALUE=uvalue, $
341    XOFFSET=xoffset, XPAD=xpad, XSIZE=xsize, X_SCROLL_SIZE=x_scroll_size,$
342    YOFFSET=yoffset, YPAD=ypad, YSIZE=ysize, Y_SCROLL_SIZE=y_scroll_size, $
343    UNAME=uname
344;
345  compile_opt hidden, idl2, strictarrsubs
346;
347  IF (N_PARAMS() ne 2) THEN ras = report('Incorrect number of arguments')
348
349  ON_ERROR, 2                       ;return to caller
350
351  ; Set default values for the keywords
352  version = WIDGET_INFO(/version)
353  if (version.toolkit eq 'OLIT') then def_space_pad = 4 else def_space_pad = 3
354  IF (N_ELEMENTS(column) eq 0)      then column = 0
355  IF (N_ELEMENTS(excl) eq 0)        then excl = 0
356  IF (N_ELEMENTS(frame) eq 0)       then frame = 0
357  IF (N_ELEMENTS(map) eq 0)     then map=1
358  IF (N_ELEMENTS(nonexcl) eq 0)     then nonexcl = 0
359  IF (N_ELEMENTS(no_release) eq 0)  then no_release = 0
360  IF (N_ELEMENTS(row) eq 0)     then row = 0
361  IF (N_ELEMENTS(scroll) eq 0)      then scroll = 0
362  IF (N_ELEMENTS(space) eq 0)       then space = def_space_pad
363  IF (N_ELEMENTS(uname) eq 0)      then uname = 'CW_BGROUP_UNAME'
364  IF (N_ELEMENTS(uvalue) eq 0)      then uvalue = 0
365  IF (N_ELEMENTS(xoffset) eq 0)     then xoffset=0
366  IF (N_ELEMENTS(xpad) eq 0)        then xpad = def_space_pad
367  IF (N_ELEMENTS(xsize) eq 0)       then xsize = 0
368  IF (N_ELEMENTS(x_scroll_size) eq 0)   then x_scroll_size = 0
369  IF (N_ELEMENTS(yoffset) eq 0)     then yoffset=0
370  IF (N_ELEMENTS(ypad) eq 0)        then ypad = def_space_pad
371  IF (N_ELEMENTS(ysize) eq 0)       then ysize = 0
372  IF (N_ELEMENTS(y_scroll_size) eq 0)   then y_scroll_size = 0
373
374  top_base = 0L
375  if (n_elements(label_top) ne 0) then begin
376    next_base = WIDGET_BASE(parent, XOFFSET=xoffset, YOFFSET=yoffset, /COLUMN)
377    if(keyword_set(font))then $
378       junk = WIDGET_LABEL(next_base, value=label_top,font=font) $
379    else    junk = WIDGET_LABEL(next_base, value=label_top)
380    top_base = next_base
381  endif else next_base = parent
382
383  if (n_elements(label_left) ne 0) then begin
384    next_base = WIDGET_BASE(next_base, XOFFSET=xoffset, YOFFSET=yoffset, /ROW)
385    if(keyword_set(font))then $
386       junk = WIDGET_LABEL(next_base, value=label_left, font=font) $
387    else junk = WIDGET_LABEL(next_base, value=label_left)
388    if (top_base eq 0L) then top_base = next_base
389  endif
390  ; We need some kind of outer base to hold the users UVALUE
391  if (top_base eq 0L) then begin
392    top_base = WIDGET_BASE(parent, XOFFSET=xoffset, YOFFSET=yoffset)
393    next_base = top_base
394  endif
395  If (top_base EQ next_base) THEN $
396     next_base = WIDGET_BASE(top_base, Xpad=1, Ypad=1, Space=1)
397
398  ; Set top level base attributes
399  WIDGET_CONTROL, top_base, MAP=map, $
400    FUNC_GET_VALUE='CW_BGROUP_GETV', PRO_SET_VALUE='CW_BGROUP_SETV', $
401    SET_UVALUE=uvalue, SET_UNAME=uname
402
403  ; Tabbing
404  if (n_elements(tab_mode) ne 0) then begin
405    WIDGET_CONTROL, top_base, TAB_MODE=tab_mode
406    WIDGET_CONTROL, next_base, TAB_MODE=tab_mode
407  end
408
409  ; The actual button holding base
410  base = WIDGET_BASE(next_base, COLUMN=column, EXCLUSIVE=excl, FRAME=frame, $
411    NONEXCLUSIVE=nonexcl, ROW=row, SCROLL=scroll, SPACE=space, $
412    XPAD=xpad, XSIZE=xsize, X_SCROLL_SIZE=x_scroll_size, $
413    YPAD=ypad, YSIZE=ysize, Y_SCROLL_SIZE=y_scroll_size, $
414    EVENT_FUNC='CW_BGROUP_EVENT', $
415    UVALUE=WIDGET_INFO(top_base, /child))
416
417  n = n_elements(names)
418  ids = lonarr(n)
419  for i = 0, n-1 do begin
420    if (n_elements(font) eq 0) then begin
421      ids[i] = WIDGET_BUTTON(base, value=names[i], UVALUE=i, $
422      UNAME=uname+'_BUTTON'+STRTRIM(i,2))
423    endif else begin
424      ids[i] = WIDGET_BUTTON(base, value=names[i], FONT=font, $
425      UVALUE=i, UNAME=uname+'_BUTTON'+STRTRIM(i,2))
426    endelse
427  endfor
428
429  ; Keep the state info in the real (inner) base UVALUE.
430  ; Pick an event value type:
431  ; 0 - Return ID
432  ; 1 - Return INDEX
433  ; 2 - Return NAME
434  ret_type = 1
435  if KEYWORD_SET(RETURN_ID) then ret_type = 0
436  if KEYWORD_SET(RETURN_NAME) then ret_type = 2
437  if KEYWORD_SET(BUTTON_UVALUE) then ret_type = 3
438    case ret_type of
439      0: ret_arr = ids
440      1: ret_arr = indgen(n)
441      2: ret_arr = names
442      3: ret_arr = button_uvalue
443    endcase
444  type = 0
445  if (excl ne 0) then type = 1
446
447  if (nonexcl ne 0) then type = 2
448  if n_elements(efun) le 0 then efun = ''
449  state = { type:type, $    ; 0-Standard, 1-Exclusive, 2-Non-exclusive
450        base: top_base, $   ; cw_bgroup base...
451        ret_arr:ret_arr, $  ; Vector of event values
452        efun : efun, $  ; Name of event fcn
453        nonexcl_curpos:intarr(n), $ ; If non-exclus, tracks state
454        excl_pos:0, $           ; If exclusive, current button
455        ids:ids, $          ; Ids of buttons
456        no_release:no_release }
457  WIDGET_CONTROL, WIDGET_INFO(top_base, /CHILD), SET_UVALUE=state, /NO_COPY
458
459  if (n_elements(sval) ne 0) then CW_BGROUP_SETV, top_base, sval
460
461  return, top_base
462END
Note: See TracBrowser for help on using the repository browser.