This method reads and processes one line from the
rgb.txt file. For a description of the format, see
Section 14.7, “
PickList.__readColorsFile(): Process the
# - - - P i c k L i s t . _ _ r e a d C o l o r L i n e def __readColorLine ( self, index, rawLine ): """Process one line from the rgb.txt file. [ (index is a nonnegative integer) and (rawLine is a string) -> if rawLine is a comment -> I else if rawLine is valid -> self.__colorMap +:= an entry mapping the uppercased color name |-> a tuple (index, the color from that line as a Color instance), the name from that line) else -> raise IOError ] """
First we remove any trailing whitespace. This will take care of any newline character.
#-- 1 -- # [ line := rawLine with trailing whitespace removed ] line = rawLine.rstrip()
If the line is a comment, return.
#-- 2 -- if line.startswith('!'): return
.split() method does a nice job
of breaking the line into fields. In this call, there are two
arguments. The first argument is the delimiter; passing
None to this argument has the effect of using any
contiguous string of whitespace characters as a delimiter. The
second argument specifies an upper limit to the number of fields
removed from the front of the string. By passing a value of 3
to this argument, we never get more than four fields; this will
avoid splitting up color names that contain embedded spaces.
#-- 3 -- # [ fieldList := line split on whitespace regions, but never # more than the first four ] fieldList = line.split ( None, 3 )
Now for some validity tests. There should be exactly
four fields. Also, the first three must contain strings
that can be converted to integers. For conversion of the
integer values, see Section 14.9, “
PickList.__convert8(): Convert an 8-bit
#-- 4 -- if len(fieldList) < 4: raise IOError, "rgb.txt lines must have four fields" else: colorName = fieldList[-1] #-- 5 -- # [ if the first three elements of fieldList can be # converted to integers in [0,255] -> # red8 := int(fieldList) # green8 := int(fieldList) # blue8 := int(fieldList) # else -> raise IOError ] red8 = self.__convert8 ( fieldList ) green8 = self.__convert8 ( fieldList ) blue8 = self.__convert8 ( fieldList )
Color class constructor expects values in the
range [0,MAX_PARAM]. One possibility is just to multiply the
values by 256, and that's probably sufficiently accurate. A
rejected possibility was to duplicate the value, e.g.,
0xffff. If anyone ever
convinces me that it makes a difference, I'll change it.
#-- 6 -- # [ color := a new Color instance made from red8, green8, # and blue8, each shifted left 8 bits ] color = Color ( red8<<8, green8<<8, blue8<<8 )
Finally, add a new entry to
#-- 7 -- colorKey = colorName.upper() colorTuple = (index, color, colorName) self.__colorMap [ colorKey ] = colorTuple