1<?php 2/* 3 * This work is hereby released into the Public Domain. 4 * To view a copy of the public domain dedication, 5 * visit http://creativecommons.org/licenses/publicdomain/ or send a letter to 6 * Creative Commons, 559 Nathan Abbott Way, Stanford, California 94305, USA. 7 * 8 */ 9 10 11/* <php4> */ 12 13define("LABEL_LEFT", 1); 14define("LABEL_RIGHT", 2); 15define("LABEL_CENTER", 3); 16define("LABEL_TOP", 4); 17define("LABEL_BOTTOM", 5); 18define("LABEL_MIDDLE", 6); 19 20/* </php4> */ 21 22/** 23 * Draw labels 24 * 25 * @package Artichow 26 */ 27class awLabel implements awPositionable { 28 29 /** 30 * Label border 31 * 32 * @var int 33 */ 34 public $border; 35 36 /** 37 * Label texts 38 * 39 * @var array 40 */ 41 protected $texts; 42 43 /** 44 * Text font 45 * 46 * @var int 47 */ 48 protected $font; 49 50 /** 51 * Text angle 52 * 53 * @var int 54 */ 55 protected $angle = 0; 56 57 /** 58 * Text color 59 * 60 * @var Color 61 */ 62 protected $color; 63 64 /** 65 * Text background 66 * 67 * @var Color, Gradient 68 */ 69 private $background; 70 71 /** 72 * Callback function 73 * 74 * @var string 75 */ 76 private $function; 77 78 /** 79 * Callback function to format output 80 * 81 * @var string 82 */ 83 private $formatFunction; 84 85 /** 86 * Padding 87 * 88 * @var int 89 */ 90 private $padding; 91 92 /** 93 * Move position from this vector 94 * 95 * @var Point 96 */ 97 protected $move; 98 99 /** 100 * Label interval 101 * 102 * @var int 103 */ 104 protected $interval = 1; 105 106 /** 107 * Horizontal align 108 * 109 * @var int 110 */ 111 protected $hAlign = awLabel::CENTER; 112 113 /** 114 * Vertical align 115 * 116 * @var int 117 */ 118 protected $vAlign = awLabel::MIDDLE; 119 120 /** 121 * Hide all labels ? 122 * 123 * @var bool 124 */ 125 protected $hide = FALSE; 126 127 /** 128 * Keys to hide 129 * 130 * @var array 131 */ 132 protected $hideKey = array(); 133 134 /** 135 * Values to hide 136 * 137 * @var array 138 */ 139 protected $hideValue = array(); 140 141 /** 142 * Hide first label 143 * 144 * @var bool 145 */ 146 protected $hideFirst = FALSE; 147 148 /** 149 * Hide last label 150 * 151 * @var bool 152 */ 153 protected $hideLast = FALSE; 154 155 /** 156 * Build the label 157 * 158 * @param string $label First label 159 */ 160 public function __construct($label = NULL, $font = NULL, $color = NULL, $angle = 0) { 161 162 if(is_array($label)) { 163 $this->set($label); 164 } else if(is_string($label)) { 165 $this->set(array($label)); 166 } 167 168 if($font === NULL) { 169 $font = new awFont2; 170 } 171 172 $this->setFont($font); 173 $this->setAngle($angle); 174 175 if($color instanceof awColor) { 176 $this->setColor($color); 177 } else { 178 $this->setColor(new awColor(0, 0, 0)); 179 } 180 181 $this->move = new awPoint(0, 0); 182 183 $this->border = new awBorder; 184 $this->border->hide(); 185 186 } 187 188 /** 189 * Get an element of the label from its key 190 * 191 * @param int $key Element key 192 * @return string A value 193 */ 194 public function get($key) { 195 return array_key_exists($key, $this->texts) ? $this->texts[$key] : NULL; 196 } 197 198 /** 199 * Get all labels 200 * 201 * @return array 202 */ 203 public function all() { 204 return $this->texts; 205 } 206 207 /** 208 * Set one or several labels 209 * 210 * @param array $labels Array of string or a string 211 */ 212 public function set($labels) { 213 214 if(is_string($labels)) { 215 $this->texts = array($labels); 216 } else if(is_array($labels)) { 217 $this->texts = $labels; 218 } 219 220 } 221 222 /** 223 * Count number of texts in the label 224 * 225 * @return int 226 */ 227 public function count() { 228 return is_array($this->texts) ? count($this->texts) : 0; 229 } 230 231 /** 232 * Set a callback function for labels 233 * 234 * @param string $function 235 */ 236 public function setCallbackFunction($function) { 237 $this->function = is_null($function) ? $function : (string)$function; 238 } 239 240 /** 241 * Return the callback function for labels 242 * 243 * @return string 244 */ 245 public function getCallbackFunction() { 246 return $this->function; 247 } 248 249 /** 250 * Set a callback function to format the labels 251 * 252 * @param string $function 253 */ 254 public function setCallbackFormatFunction($function) { 255 $this->formatFunction =& $function; 256 } 257 258 /** 259 * Change labels format 260 * 261 * @param string $format New format (printf style: %.2f for example) 262 */ 263 public function setFormat($format) { 264 $function = 'label'.time().'_'.(microtime() * 1000000); 265 eval('function '.$function.'($value) { 266 return sprintf("'.addcslashes($format, '"').'", $value); 267 }'); 268 $this->setCallbackFunction($function); 269 } 270 271 /** 272 * Change font for label 273 * 274 * @param awFont $font New font 275 * @param awColor $color Font color (can be NULL) 276 */ 277 public function setFont(awFont $font, $color = NULL) { 278 $this->font = $font; 279 if($color instanceof awColor) { 280 $this->setColor($color); 281 } 282 } 283 284 /** 285 * Change font angle 286 * 287 * @param int $angle New angle 288 */ 289 public function setAngle($angle) { 290 $this->angle = (int)$angle; 291 } 292 293 /** 294 * Change font color 295 * 296 * @param awColor $color 297 */ 298 public function setColor($color) { 299 $this->color = $color; 300 } 301 302 /** 303 * Change text background 304 * 305 * @param mixed $background 306 */ 307 public function setBackground($background) { 308 $this->background = $background; 309 } 310 311 /** 312 * Change text background color 313 * 314 * @param Color 315 */ 316 public function setBackgroundColor(awColor $color) { 317 $this->background = $color; 318 } 319 320 /** 321 * Change text background gradient 322 * 323 * @param Gradient 324 */ 325 public function setBackgroundGradient(awGradient $gradient) { 326 $this->background = $gradient; 327 } 328 329 /** 330 * Change padding 331 * 332 * @param int $left Left padding 333 * @param int $right Right padding 334 * @param int $top Top padding 335 * @param int $bottom Bottom padding 336 */ 337 public function setPadding($left, $right, $top, $bottom) { 338 $this->padding = array((int)$left, (int)$right, (int)$top, (int)$bottom); 339 } 340 341 /** 342 * Hide all labels ? 343 * 344 * @param bool $hide 345 */ 346 public function hide($hide = TRUE) { 347 $this->hide = (bool)$hide; 348 } 349 350 /** 351 * Show all labels ? 352 * 353 * @param bool $show 354 */ 355 public function show($show = TRUE) { 356 $this->hide = (bool)!$show; 357 } 358 359 /** 360 * Hide a key 361 * 362 * @param int $key The key to hide 363 */ 364 public function hideKey($key) { 365 $this->hideKey[$key] = TRUE; 366 } 367 368 /** 369 * Hide a value 370 * 371 * @param int $value The value to hide 372 */ 373 public function hideValue($value) { 374 $this->hideValue[] = $value; 375 } 376 377 /** 378 * Hide first label 379 * 380 * @param bool $hide 381 */ 382 public function hideFirst($hide) { 383 $this->hideFirst = (bool)$hide; 384 } 385 386 /** 387 * Hide last label 388 * 389 * @param bool $hide 390 */ 391 public function hideLast($hide) { 392 $this->hideLast = (bool)$hide; 393 } 394 395 /** 396 * Set label interval 397 * 398 * @param int 399 */ 400 public function setInterval($interval) { 401 402 $this->interval = (int)$interval; 403 404 } 405 406 /** 407 * Change label position 408 * 409 * @param int $x Add this interval to X coord 410 * @param int $y Add this interval to Y coord 411 */ 412 public function move($x, $y) { 413 414 $this->move = $this->move->move($x, $y); 415 416 } 417 418 /** 419 * Change alignment 420 * 421 * @param int $h Horizontal alignment 422 * @param int $v Vertical alignment 423 */ 424 public function setAlign($h = NULL, $v = NULL) { 425 if($h !== NULL) { 426 $this->hAlign = (int)$h; 427 } 428 if($v !== NULL) { 429 $this->vAlign = (int)$v; 430 } 431 } 432 433 /** 434 * Get a text from the labele 435 * 436 * @param mixed $key Key in the array text 437 * @return Text 438 */ 439 public function getText($key) { 440 441 if(is_array($this->texts) and array_key_exists($key, $this->texts)) { 442 443 $value = $this->texts[$key]; 444 445 if(is_string($this->function)) { 446 $value = call_user_func($this->function, $value); 447 } 448 if(!is_null($this->formatFunction)) { 449 $value = call_user_func($this->formatFunction, $value); 450 } 451 452 $text = new awText($value); 453 $text->setFont($this->font); 454 $text->setAngle($this->angle); 455 $text->setColor($this->color); 456 457 if($this->background instanceof awColor) { 458 $text->setBackgroundColor($this->background); 459 } else if($this->background instanceof awGradient) { 460 $text->setBackgroundGradient($this->background); 461 } 462 463 $text->border = $this->border; 464 465 if($this->padding !== NULL) { 466 call_user_func_array(array(&$text, 'setPadding'), $this->padding); 467 } 468 469 return $text; 470 471 } else { 472 return NULL; 473 } 474 475 } 476 477 /** 478 * Get max width of all texts 479 * 480 * @param awDrawer $drawer A drawer 481 * @return int 482 */ 483 public function getMaxWidth(awDrawer $drawer) { 484 485 return $this->getMax($drawer, 'getTextWidth'); 486 487 } 488 489 /** 490 * Get max height of all texts 491 * 492 * @param awDrawer $drawer A drawer 493 * @return int 494 */ 495 public function getMaxHeight(awDrawer $drawer) { 496 497 return $this->getMax($drawer, 'getTextHeight'); 498 499 } 500 501 /** 502 * Draw the label 503 * 504 * @param awDrawer $drawer 505 * @param awPoint $p Label center 506 * @param int $key Text position in the array of texts (default to zero) 507 */ 508 public function draw(awDrawer $drawer, awPoint $p, $key = 0) { 509 510 if(($key % $this->interval) !== 0) { 511 return; 512 } 513 514 // Hide all labels 515 if($this->hide) { 516 return; 517 } 518 519 // Key is hidden 520 if(array_key_exists($key, $this->hideKey)) { 521 return; 522 } 523 524 // Hide first label 525 if($key === 0 and $this->hideFirst) { 526 return; 527 } 528 529 // Hide last label 530 if($key === count($this->texts) - 1 and $this->hideLast) { 531 return; 532 } 533 534 $text = $this->getText($key); 535 536 if($text !== NULL) { 537 538 // Value must be hidden 539 if(in_array($text->getText(), $this->hideValue)) { 540 return; 541 } 542 543 $x = $p->x; 544 $y = $p->y; 545 546 // Get padding 547 list($left, $right, $top, $bottom) = $text->getPadding(); 548 549 $font = $text->getFont(); 550 $width = $font->getTextWidth($text); 551 $height = $font->getTextHeight($text); 552 553 switch($this->hAlign) { 554 555 case awLabel::RIGHT : 556 $x -= ($width + $right); 557 break; 558 559 case awLabel::CENTER : 560 $x -= ($width - $left + $right) / 2; 561 break; 562 563 case awLabel::LEFT : 564 $x += $left; 565 break; 566 567 } 568 569 switch($this->vAlign) { 570 571 case awLabel::TOP : 572 $y -= ($height + $bottom); 573 break; 574 575 case awLabel::MIDDLE : 576 $y -= ($height - $top + $bottom) / 2; 577 break; 578 579 case awLabel::BOTTOM : 580 $y += $top; 581 break; 582 583 } 584 585 $drawer->string($text, $this->move->move($x, $y)); 586 587 } 588 589 } 590 591 protected function getMax(awDrawer $drawer, $function) { 592 593 $max = NULL; 594 595 foreach($this->texts as $key => $text) { 596 597 $text = $this->getText($key); 598 $font = $text->getFont(); 599 600 if(is_null($max)) { 601 $max = $font->{$function}($text); 602 } else { 603 $max = max($max, $font->{$function}($text)); 604 } 605 606 } 607 608 return $max; 609 610 } 611 612} 613 614registerClass('Label'); 615?>