/[thuban]/branches/WIP-pyshapelib-bramz/Thuban/Model/classgen.py
ViewVC logotype

Diff of /branches/WIP-pyshapelib-bramz/Thuban/Model/classgen.py

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1157 by jonathan, Thu Jun 12 12:39:54 2003 UTC revision 1359 by jonathan, Wed Jul 2 10:51:49 2003 UTC
# Line 15  __version__ = "$Revision$" Line 15  __version__ = "$Revision$"
15    
16  import operator  import operator
17    
18  from color import Color  from color import Color, Transparent
19  from range import Range  from range import Range
20  from classification import Classification, ClassGroupSingleton, \  from classification import Classification, ClassGroupSingleton, \
21      ClassGroupRange, ClassGroupProperties      ClassGroupRange, ClassGroupProperties
22    
23  def generate_singletons(_list, numGroups, ramp):  def generate_singletons(_list, ramp):
24      """Generate a new classification consisting solely of singletons.      """Generate a new classification consisting solely of singletons.
25    
26      The resulting classification will consist of at most 'numGroups'      The resulting classification will consist of one group for each
27      groups whose group properties ramp between 'prop1' and 'prop2'. There      item in _list whose properties ramp between 'prop1' and 'prop2'.
     could be fewer groups if '_list' contains fewer that 'numGroups' items.  
28    
29      _list -- any object that implements the iterator interface      _list -- any object that implements the iterator interface
30    
     numGroups -- how many groups to generate. This can not be  
                  determined while the classification is being  
                  generated because the stepping values must  
                  be precalculated to ramp between prop1 and prop2.  
   
31      ramp -- an object which implements the CustomRamp interface      ramp -- an object which implements the CustomRamp interface
32      """      """
33    
34      clazz = Classification()      clazz = Classification()
     if numGroups == 0: return clazz  
   
     ramp.SetNumGroups(numGroups)  
35    
36      for value, prop in zip(_list, ramp):      i = 0
37        maxValue = float(len(_list) - 1)
38        for value in _list:
39            prop = ramp.GetProperties(i / maxValue)
40          clazz.AppendGroup(ClassGroupSingleton(value, prop))          clazz.AppendGroup(ClassGroupSingleton(value, prop))
41            i += 1
42    
43      return clazz      return clazz
44    
# Line 58  def generate_uniform_distribution(min, m Line 53  def generate_uniform_distribution(min, m
53      """      """
54    
55      clazz = Classification()      clazz = Classification()
     if numGroups == 0: return clazz  
   
     ramp.SetNumGroups(numGroups)  
56    
57      cur_min = min      cur_min = min
58    
     i = 1  
59      end = "["      end = "["
60      for prop in ramp:      maxValue = float(numGroups - 1)
61        for i in range(1, numGroups + 1):
62    
63            prop = ramp.GetProperties(float(i-1) / maxValue)
64    
65          if intStep:          if intStep:
66              cur_max = min + int(round((i * (max - min + 1)) / float(numGroups)))              cur_max = min + int(round((i * (max - min + 1)) / maxValue))
67          else:          else:
68              cur_max = min + (i * (max - min)) / float(numGroups)              cur_max = min + (i * (max - min)) / maxValue
69    
70          if i == numGroups:          if i == numGroups:
71              cur_max = max              cur_max = max
72              end = "]"              end = "]"
73    
74          if cur_min == cur_max:          if cur_min == cur_max:
75              range = Range(("[", cur_min, cur_max, "]"))              _range = Range(("[", cur_min, cur_max, "]"))
76          else:          else:
77              range = Range(("[", cur_min, cur_max, end))              _range = Range(("[", cur_min, cur_max, end))
78    
79          clazz.AppendGroup(ClassGroupRange(range, None, prop))          clazz.AppendGroup(ClassGroupRange(_range, prop))
80    
81          cur_min = cur_max          cur_min = cur_max
         i += 1  
82    
83      return clazz      return clazz
84    
   
85  def generate_quantiles(_list, percents, ramp, _range):  def generate_quantiles(_list, percents, ramp, _range):
86      """Generates a Classification which has groups of ranges that      """Generates a Classification which has groups of ranges that
87      represent quantiles of _list at the percentages given in percents.      represent quantiles of _list at the percentages given in percents.
# Line 126  def generate_quantiles(_list, percents, Line 118  def generate_quantiles(_list, percents,
118    
119              adjusted = quantiles[0]              adjusted = quantiles[0]
120    
             ramp.SetNumGroups(numGroups)  
   
121              start, min, endMax, right = _range.GetRange()              start, min, endMax, right = _range.GetRange()
122    
123              oldp = 0              oldp = 0
124              i = 1              i = 1
125              end = "]"              end = "]"
126    
127              for (q, p), prop in zip(quantiles[3], ramp):              maxValue = float(numGroups - 1)
128                for (q, p) in quantiles[3]:
129    
130                    prop = ramp.GetProperties(float(i-1) / maxValue)
131    
132                  if i == numGroups:                  if i == numGroups:
133                      max = endMax                      max = endMax
134                      end = right                      end = right
135                  else:                  else:
136                      max = _list[q]                      max = _list[q]
137    
138                  group = ClassGroupRange(Range((start, min, max, end)),                  group = ClassGroupRange(Range((start, min, max, end)), prop)
                                         None, prop)  
139            
140                  group.SetLabel("%s%% - %s%%" % (round(oldp*100, 2),                  group.SetLabel("%s%% - %s%%" % (round(oldp*100, 2),
141                                                  round(p*100, 2)))                                                  round(p*100, 2)))
# Line 187  def GenQuantiles0(_list, percents, ramp, Line 180  def GenQuantiles0(_list, percents, ramp,
180          if numGroups > 0:          if numGroups > 0:
181              adjusted = quantiles[0]              adjusted = quantiles[0]
182    
             ramp.SetNumGroups(numGroups)  
   
183              start, min, endMax, right = _range.GetRange()              start, min, endMax, right = _range.GetRange()
184    
185              class0 = quantiles[3][0]              class0 = quantiles[3][0]
# Line 197  def GenQuantiles0(_list, percents, ramp, Line 188  def GenQuantiles0(_list, percents, ramp,
188              i = 1              i = 1
189              end = "]"              end = "]"
190    
191              for (q, p), prop in zip(quantiles[3][1:], ramp):              maxValue = float(numGroups - 1)
192                for (q, p) in quantiles[3][1:]:
193                    prop = ramp.GetProperties(float(i-1) / maxValue)
194    
195                  if i == numGroups:                  if i == numGroups:
196                      max = endMax                      max = endMax
197                      end = right                      end = right
198                  else:                  else:
199                      max = _list[q]                      max = _list[q]
200    
201                  group = ClassGroupRange(Range((start, min, max, end)),                  group = ClassGroupRange(Range((start, min, max, end)), prop)
                                         None, prop)  
202            
203                  group.SetLabel("%s%% - %s%%" % (round(oldp*100, 2),                  group.SetLabel("%s%% - %s%%" % (round(oldp*100, 2),
204                                                  round(p*100, 2)))                                                  round(p*100, 2)))
# Line 256  def calculate_quantiles(_list, percents, Line 249  def calculate_quantiles(_list, percents,
249      if len(percents) <= 1:      if len(percents) <= 1:
250          raise ValueError("percents parameter must have more than one item")          raise ValueError("percents parameter must have more than one item")
251    
252      if percents[len(percents) - 1] != 1.0:      if percents[-1] != 1.0:
253          raise ValueError("percents does not cover the entire range")          raise ValueError("percents does not cover the entire range")
254    
255      #      #
# Line 375  def calculate_quantiles(_list, percents, Line 368  def calculate_quantiles(_list, percents,
368                  [(q, (q - minIndex+1) / float(numValues)) \                  [(q, (q - minIndex+1) / float(numValues)) \
369                   for q in quantiles])                   for q in quantiles])
370    
 CLR  = 0  
 STEP = 1  
371  class CustomRamp:  class CustomRamp:
372    
373      def __init__(self, prop1, prop2):      def __init__(self, prop1, prop2):
374          self.prop1 = prop1          self.prop1 = prop1
375          self.prop2 = prop2          self.prop2 = prop2
376    
         self.count = 0  
   
     def __iter__(self):  
         return self  
   
377      def GetRamp(self):      def GetRamp(self):
378          return self          return self
379    
380      def SetNumGroups(self, num):      def GetProperties(self, index):
381            """Return a ClassGroupProperties object whose properties
382          if num <= 0:          represent a point at 'index' between prop1 and prop2 in
383              return False          the constructor.
384    
385          self.count = int(num)          index -- a value such that 0 <= index <= 1
386          num = float(num)          """
387    
388          prop1 = self.prop1          if not (0 <= index <= 1):
389          prop2 = self.prop2              raise ValueError(_("invalid index"))
390    
391          clr = prop1.GetLineColor()          newProps = ClassGroupProperties()
392          lineColor2 = prop2.GetLineColor()  
393                    color1 = self.prop1.GetLineColor()
394          self.noLine = clr is not Color.Transparent \          color2 = self.prop2.GetLineColor()
395                          and lineColor2 is not Color.Transparent  
396            self.__SetProperty(color1, color2, index, newProps.SetLineColor)
397            self.__SetProperty(color1, color2, index, newProps.SetFill)
398          self.lineInfo = self.__GetColorInfo(prop1.GetLineColor(),  
399                                              prop2.GetLineColor(),          w = (self.prop2.GetLineWidth() - self.prop1.GetLineWidth()) \
400                                              num)              * index \
401                + self.prop1.GetLineWidth()
402          self.fillInfo = self.__GetColorInfo(prop1.GetFill(),  
403                                              prop2.GetFill(),          newProps.SetLineWidth(int(round(w)))
404                                              num)  
405            return newProps
406          self.lineWidth = prop1.GetLineWidth()  
407          self.lineWidthStep = (prop2.GetLineWidth() - self.lineWidth) / num      def __SetProperty(self, color1, color2, index, setf):
408    
409          return True          if color1 is Transparent and color2 is Transparent:
410                setf(Transparent)
411      def next(self):          elif color1 is Transparent:
412          if self.count == 0:              setf(Color(
413              raise StopIteration                   color2.red   * index,
414                     color2.green * index,
415          prop = ClassGroupProperties()                   color2.blue  * index))
416            elif color2 is Transparent:
417          if self.lineInfo is None:              setf(Color(
418              prop.SetLineColor(Color.Transparent)                   color1.red   * index,
419          else:                   color1.green * index,
420              prop.SetLineColor(Color(self.lineInfo[CLR][0] / 255,                   color1.blue  * index))
                                     self.lineInfo[CLR][1] / 255,  
                                     self.lineInfo[CLR][2] / 255))  
   
             self.lineInfo[CLR][0] += self.lineInfo[STEP][0]  
             self.lineInfo[CLR][1] += self.lineInfo[STEP][1]  
             self.lineInfo[CLR][2] += self.lineInfo[STEP][2]  
   
         if self.fillInfo is None:  
             prop.SetFill(Color.Transparent)  
421          else:          else:
422              prop.SetFill(Color(self.fillInfo[CLR][0] / 255,              setf(Color(
423                              self.fillInfo[CLR][1] / 255,                  (color2.red   - color1.red)   * index + color1.red,
424                              self.fillInfo[CLR][2] / 255))                  (color2.green - color1.green) * index + color1.green,
425                    (color2.blue  - color1.blue)  * index + color1.blue))
             self.fillInfo[CLR][0] += self.fillInfo[STEP][0]  
             self.fillInfo[CLR][1] += self.fillInfo[STEP][1]  
             self.fillInfo[CLR][2] += self.fillInfo[STEP][2]  
   
   
         prop.SetLineWidth(int(self.lineWidth))  
         self.lineWidth        += self.lineWidthStep  
   
         self.count -= 1  
   
         return prop  
   
     def __GetColorInfo(self, color1, color2, numGroups):  
   
         if color1 is Color.Transparent and color2 is Color.Transparent:  
             #  
             # returning early  
             #  
             return None  
         elif color1 is not Color.Transparent and color2 is Color.Transparent:  
             color = [color1.red   * 255,  
                      color1.green * 255,  
                      color1.blue  * 255]  
             step = (0, 0, 0)  
         elif color1 is Color.Transparent and color2 is not Color.Transparent:  
             color = [color2.red   * 255,  
                      color2.green * 255,  
                      color2.blue  * 255]  
             step = (0, 0, 0)  
         else:  
             color = [color1.red   * 255,  
                      color1.green * 255,  
                      color1.blue  * 255]  
             step = ((color2.red   * 255 - color1.red   * 255) / numGroups,  
                     (color2.green * 255 - color1.green * 255) / numGroups,  
                     (color2.blue  * 255 - color1.blue  * 255) / numGroups)  
   
   
         return (color, step)  
426    
427  class MonochromaticRamp(CustomRamp):  class MonochromaticRamp(CustomRamp):
428      def __init__(self, start, end):      def __init__(self, start, end):
# Line 498  class MonochromaticRamp(CustomRamp): Line 436  class MonochromaticRamp(CustomRamp):
436    
437          CustomRamp.__init__(self, sp, ep)          CustomRamp.__init__(self, sp, ep)
438    
439  class GreyRamp(MonochromaticRamp):  GreyRamp       = MonochromaticRamp(Color(1, 1, 1),  Color(0, 0, 0))
440      def __init__(self):  RedRamp        = MonochromaticRamp(Color(1, 1, 1),  Color(.8, 0, 0))
441          MonochromaticRamp.__init__(self, Color(1, 1, 1), Color(0, 0, 0))  GreenRamp      = MonochromaticRamp(Color(1, 1, 1),  Color(0, .8, 0))
442    BlueRamp       = MonochromaticRamp(Color(1, 1, 1),  Color(0, 0, .8))
443  class RedRamp(MonochromaticRamp):  GreenToRedRamp = MonochromaticRamp(Color(1, .8, 1), Color(1, 0, 0))
     def __init__(self):  
         MonochromaticRamp.__init__(self, Color(1, 1, 1), Color(.8, 0, 0))  
   
 class GreenRamp(MonochromaticRamp):  
     def __init__(self):  
         MonochromaticRamp.__init__(self, Color(1, 1, 1), Color(0, .8, 0))  
   
 class BlueRamp(MonochromaticRamp):  
     def __init__(self):  
         MonochromaticRamp.__init__(self, Color(1, 1, 1), Color(0, 0, .8))  
   
 class GreenToRedRamp(MonochromaticRamp):  
     def __init__(self):  
         MonochromaticRamp.__init__(self, Color(0, .8, 0), Color(1, 0, 0))  
444    
445  class HotToColdRamp:  class HotToColdRamp:
446    
     def __iter__(self):  
         return self  
           
447      def GetRamp(self):      def GetRamp(self):
448          return self          return self
449    
450      def SetNumGroups(self, num):      def GetProperties(self, index):
451          if num < 0:          """Return a ClassGroupProperties object whose properties
452              return False          represent a point at 'index' between "hot" and "cold".
453    
454          self.num = float(num)          index -- a value such that 0 <= index <= 1
455          self.index = 0          """
   
         return True  
   
     def next(self):  
         if self.index == self.num:  
             raise StopIteration  
456    
457          clr = [1.0, 1.0, 1.0]          clr = [1.0, 1.0, 1.0]
458    
459          if self.index < (.25 * self.num):          if index < .25:
460              clr[0] = 0              clr[0] = 0
461              clr[1] = 4 * self.index / self.num              clr[1] = 4 * index
462          elif self.index < (.5 * self.num):          elif index < .5:
463              clr[0] = 0              clr[0] = 0
464              clr[2] = 1 + 4 * (.25 * self.num - self.index) / self.num              clr[2] = 1 + 4 * (.25 - index)
465          elif self.index < (.75 * self.num):          elif index < .75:
466              clr[0] = 4 * (self.index - .5 * self.num) / self.num              clr[0] = 4 * (index - .5)
467              clr[2] = 0              clr[2] = 0
468          else:          else:
469              clr[1] = 1 + 4 * (.75 * self.num - self.index) / self.num              clr[1] = 1 + 4 * (.75 - index)
470              clr[2] = 0              clr[2] = 0
471    
         self.index += 1  
   
472          prop = ClassGroupProperties()          prop = ClassGroupProperties()
473          prop.SetLineColor(Color(clr[0], clr[1], clr[2]))          prop.SetLineColor(Color(clr[0], clr[1], clr[2]))
474          prop.SetFill(Color(clr[0], clr[1], clr[2]))          prop.SetFill(Color(clr[0], clr[1], clr[2]))
475    
476          return prop          return prop
477    

Legend:
Removed from v.1157  
changed lines
  Added in v.1359

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26