Pmw.Counter() - entry field with up and down arrow buttons
A counter contains an entry field and two arrow buttons to increment and decrement the value in the entry field. Standard counting types include numbers, times and dates. A user defined counting function may also be supplied for specialised counting. Counting can be used in combination with the entry field's validation. The components may be laid out horizontally or vertically.
Each time an arrow button is pressed the value displayed in the entry field is incremented or decremented by the value of the increment option. If the new value is invalid (according to the entry field's validate option, perhaps due to exceeding minimum or maximum limits), the old value is restored.
When an arrow button is pressed and the value displayed is not an exact multiple of the increment, it is "truncated" up or down to the nearest increment.
The most general way to specify the datatype option is as a dictionary. The kind of counting is specified by the 'counter' dictionary field, which may be either a function or the name of one of the standard counters described below. If the dictionary does not have a 'counter' field, the field defaults to 'numeric'.
Any other fields in the dictionary are passed on to the counter function as keyword arguments.
If datatype is not a dictionary, then it is equivalent to
specifying it as a dictionary with a single 'counter' field.
For example, datatype = 'real'
is equivalent to
datatype = {'counter' : 'real'}
.
The standard counters are:
string.atol()
.
string.atof()
. This
counter accepts a 'separator' argument, which specifies
the character used to represent the decimal point. The
default 'separator' is '.'.
Pmw.timestringtoseconds()
. This counter accepts a
'separator' argument, which specifies the character used to
separate the time fields. The default separator is ':'.
This counter also accepts a 'time24' argument. If this is
true, the time value is converted to a value between
'00:00:00' and '23:59:59'. The default is false.
Pmw.datestringtojdn()
. This counter accepts a 'separator'
argument, which specifies the character used to separate the
three date fields. The default is '/'. This counter also
accepts a 'format' argument, which is passed to
Pmw.datestringtojdn()
to specify the desired ordering of the
fields. The default is 'ymd'.
This counter also accepts a 'yyyy' argument. If this is
false, the year field will be displayed as the year within the
century, otherwise it will be fully displayed. In both cases
it will be displayed with at least 2 digits, using leading
zeroes. The default is false.
If the 'counter' dictionary field is a function, then it will be called whenever the counter is to be incremented or decremented. The function is called with at least three arguments, the first three being (text, factor, increment), where text is the current contents of the entry field, factor is 1 when incrementing or -1 when decrementing, and increment is the value of the increment megawidget option.
The other arguments are keyword arguments made up of the fields of the datatype dictionary (excluding the 'counter' field).
The counter function should return a string representing the incremented or decremented value. It should raise a ValueError exception if the text is invalid. In this case the bell is rung and the entry text is not changed.
The default for datatype is numeric.
For the number datatypes, the value of increment is a number. For the 'time' datatype, the value is in seconds. For the 'date' datatype, the value is in days. The default is 1.
If None, a label component is not created. The default is None.
class Demo: def __init__(self, parent): # Need to use long ints here because on the Macintosh the maximum size # of an integer is smaller than the value returned by time.time(). now = (long(time.time()) / 300) * 300 # Create the Counters. self._date = Pmw.Counter(parent, labelpos = 'w', label_text = 'Date (4-digit year):', entryfield_value = time.strftime('%d/%m/%Y', time.localtime(now)), entryfield_command = self.execute, entryfield_validate = {'validator' : 'date', 'format' : 'dmy'}, datatype = {'counter' : 'date', 'format' : 'dmy', 'yyyy' : 1}) self._isodate = Pmw.Counter(parent, labelpos = 'w', label_text = 'ISO-Date (4-digit year):', entryfield_value = time.strftime('%Y-%m-%d', time.localtime(now)), entryfield_command = self.execute, entryfield_validate = {'validator' : 'date', 'format' : 'ymd', 'separator' : '-' }, datatype = {'counter' : 'date', 'format' : 'ymd', 'yyyy' : 1, 'separator' : '-' }) self._time = Pmw.Counter(parent, labelpos = 'w', label_text = 'Time:', entryfield_value = time.strftime('%H:%M:%S', time.localtime(now)), entryfield_validate = {'validator' : 'time', 'min' : '00:00:00', 'max' : '23:59:59', 'minstrict' : 0, 'maxstrict' : 0}, datatype = {'counter' : 'time', 'time24' : 1}, increment=5*60) self._real = Pmw.Counter(parent, labelpos = 'w', label_text = 'Real (with comma)\nand extra\nlabel lines:', label_justify = 'left', entryfield_value = '1,5', datatype = {'counter' : 'real', 'separator' : ','}, entryfield_validate = {'validator' : 'real', 'min' : '-2,0', 'max' : '5,0', 'separator' : ','}, increment = 0.1) self._custom = Pmw.Counter(parent, labelpos = 'w', label_text = 'Custom:', entryfield_value = specialword[:4], datatype = _custom_counter, entryfield_validate = _custom_validate) self._int = Pmw.Counter(parent, labelpos = 'w', label_text = 'Vertical integer:', orient = 'vertical', entry_width = 2, entryfield_value = 50, entryfield_validate = {'validator' : 'integer', 'min' : 0, 'max' : 99} ) counters = (self._date, self._isodate, self._time, self._real, self._custom) Pmw.alignlabels(counters) # Pack them all. for counter in counters: counter.pack(fill='both', expand=1, padx=10, pady=5) self._int.pack(padx=10, pady=5) def execute(self): print 'Return pressed, value is', self._date.get() specialword = 'Monti Python ik den Holie Grailen (Bok)' def _custom_validate(text): if string.find(specialword, text) == 0: return 1 else: return -1 def _custom_counter(text, factor, increment): # increment is ignored here. if string.find(specialword, text) == 0: length = len(text) if factor == 1: if length >= len(specialword): raise ValueError, 'maximum length reached' return specialword[:length + 1] else: if length == 0: raise ValueError, 'empty string' return specialword[:length - 1] else: raise ValueError, 'bad string ' + text
Pmw 1.2 -
5 Aug 2003
- Home
Manual page last reviewed: 24 May 1998