Changeset 70
- Timestamp:
- 11/21/07 01:52:55 (4 years ago)
- Files:
-
- 1 modified
-
trunk/src/chart.py (modified) (26 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/chart.py
r61 r70 42 42 self.xrange = None 43 43 self.yrange = None 44 44 45 45 self.xticks = [] 46 46 self.yticks = [] … … 81 81 def render(self, surface=None, options={}): 82 82 """Renders the chart with the specified options. 83 83 84 84 The optional parameters can be used to render a chart in a different 85 85 surface with new options. … … 88 88 if surface: 89 89 self._initSurface(surface) 90 90 91 91 cx = cairo.Context(self.surface) 92 92 self._renderBackground(cx) … … 123 123 self.resetFlag = False 124 124 self.clean() 125 125 126 126 127 127 # update methods … … 154 154 xdata = [pair[0] for pair in reduce(lambda a,b: a+b, stores)] 155 155 if self.options.xOriginIsZero: 156 self.minxval = 0.0 156 self.minxval = 0.0 157 157 else: 158 158 self.minxval = float(min(xdata)) 159 159 self.maxxval = float(max(xdata)) 160 160 161 self.xrange = self.maxxval - self.minxval 161 self.xrange = self.maxxval - self.minxval 162 162 if self.xrange == 0: 163 self.xscale = 1.0 163 self.xscale = 1.0 164 164 else: 165 165 self.xscale = 1 / self.xrange … … 172 172 ydata = [pair[1] for pair in reduce(lambda a,b: a+b, stores)] 173 173 if self.options.yOriginIsZero: 174 self.minyval = 0.0 174 self.minyval = 0.0 175 175 else: 176 176 self.minyval = float(min(ydata)) … … 179 179 self.yrange = self.maxyval - self.minyval 180 180 if self.yrange == 0: 181 self.yscale = 1.0 181 self.yscale = 1.0 182 182 else: 183 183 self.yscale = 1 / self.yrange … … 188 188 def _updateTicks(self): 189 189 """Evaluates ticks for x and y axis. 190 190 191 191 You should call _updateXY before because that method computes the 192 192 values of xscale, minxval, yscale, and other attributes needed for … … 203 203 if tick.label is None: 204 204 label = str(tick.v) 205 else: 205 else: 206 206 label = tick.label 207 207 pos = self.xscale * (tick.v - self.minxval) … … 225 225 self.yticks = [] 226 226 if self.options.axis.y.ticks: 227 for tick in self.options. y.ticks:227 for tick in self.options.axis.y.ticks: 228 228 if not isinstance(tick, Option): 229 229 tick = Option(tick) 230 230 if tick.label is None: 231 label = str(tick.v) 231 label = str(tick.v) 232 232 else: 233 233 label = tick.label … … 243 243 else: 244 244 roughSeparation = round(num, prec) 245 245 246 246 for i in range(self.options.axis.y.tickCount + 1): 247 247 yval = self.minyval + (i * roughSeparation) … … 249 249 if 0.0 <= pos <= 1.0: 250 250 self.yticks.append((pos, round(yval, prec))) 251 251 252 252 # render methods 253 253 def _renderBackground(self, cx): … … 255 255 if self.options.background.hide: 256 256 return 257 257 258 258 cx.save() 259 259 cx.set_source_rgb(*hex2rgb(self.options.background.color)) … … 262 262 cx.set_source_rgb(*hex2rgb(self.options.background.lineColor)) 263 263 cx.set_line_width(self.options.axis.lineWidth) 264 264 265 265 self._renderLines(cx) 266 266 267 267 cx.restore() 268 268 … … 272 272 for tick in ticks: 273 273 self._renderLine(cx, tick, False) 274 274 275 275 def _renderLine(self, cx, tick, horiz): 276 """Aux function for _renderLines""" 276 """Aux function for _renderLines""" 277 277 x1, x2, y1, y2 = (0, 0, 0, 0) 278 278 if horiz: … … 298 298 if self.options.axis.x.hide and self.options.axis.y.hide: 299 299 return 300 300 301 301 cx.save() 302 302 cx.set_source_rgb(*hex2rgb(self.options.axis.lineColor)) 303 303 cx.set_line_width(self.options.axis.lineWidth) 304 304 305 305 if not self.options.axis.y.hide: 306 306 if self.yticks: … … 308 308 if callable(tick): 309 309 return 310 310 311 311 x = self.area.x 312 312 y = self.area.y + tick[0] * self.area.h 313 313 314 314 cx.new_path() 315 315 cx.move_to(x, y) … … 317 317 cx.close_path() 318 318 cx.stroke() 319 319 320 320 label = unicode(tick[1]) 321 321 extents = cx.text_extents(label) … … 325 325 y + labelHeight / 2.0) 326 326 cx.show_text(label) 327 327 328 328 return label 329 329 for tick in self.yticks: 330 330 drawYLabel(tick) 331 331 332 332 cx.new_path() 333 333 cx.move_to(self.area.x, self.area.y) … … 341 341 if callable(tick): 342 342 return 343 343 344 344 x = self.area.x + tick[0] * self.area.w 345 345 y = self.area.y + self.area.h 346 346 347 347 cx.new_path() 348 348 cx.move_to(x, y) … … 350 350 cx.close_path() 351 351 cx.stroke() 352 352 353 353 label = unicode(tick[1]) 354 354 extents = cx.text_extents(label) … … 361 361 for tick in self.xticks: 362 362 drawXLabel(tick) 363 363 364 364 cx.new_path() 365 365 cx.move_to(self.area.x, self.area.y + self.area.h) … … 374 374 if self.options.legend.hide: 375 375 return 376 376 377 377 padding = 4 378 378 bullet = 15 … … 395 395 cx.set_source_rgb(*hex2rgb(self.options.legend.borderColor)) 396 396 cx.stroke() 397 397 398 398 def drawKey(key, x, y, text_height): 399 399 cx.rectangle(x, y, bullet, bullet) … … 405 405 y + bullet / 2.0 + text_height / 2.0) 406 406 cx.show_text(key) 407 407 408 408 cx.set_line_width(1) 409 409 x = self.options.legend.position.left + padding … … 419 419 """Return a list with the indexes of the biggest element of arr""" 420 420 return range(max([len(a) for a in arr])) 421 421 422 422 class Area(object): 423 423 """Simple rectangle to hold an area coordinates and dimensions"""
