Source for file CustomBar.php
Documentation is available at CustomBar.php
* Description: Custom Bar Series
* @copyright Copyright (c) 1995-2008 by Steema Software SL. All Rights Reserved. <info@steema.com>
* @link http://www.steema.com
//private boolean autoBarSize;
private $autoMarkPosition = true;
private $gradientRelative;
private $depthPercent = 100;
private $sideMargins = true;
function __get( $property ) {
$method = "get{$property}";
function __set ( $property,$value ) {
$method = "set{$property}";
return $this->$method($value);
$this->barStyle = BarStyle::$RECTANGLE;
$this->groups = array(); // TODO review before int[100];
$this->getMarks()->setDefaultVisible(true);
$this->getMarks()->getCallout()->setDefaultLength(20);
$this->styleResolver = $resolver;
$this->styleResolver = null;
* Defines the color Gradient used to fill the Bars.<br>
* These can be filled with these three colors: StartColor, MidColor,
* EndColor. You can control the drawing output by setting the Direction
* method.<br> Use the Visible property to show / hide filling. <br>
* <pre><font face="Courier" size="4">
* $barSeries = new Bar(myChart->getChart());
* $barSeries->getMarks()->setVisible(true);
* $barSeries->fillSampleValues(6);
* $barSeries->setColor(new Color(255,0,0));
* $barSeries->setBarStyle(BarStyle::$RECTGRADIENT);
* $barSeries->getGradient()->setDirection(GradientDirection::$VERTICAL);
* $barSeries->getGradient()->setStartColor(Color.GREEN);
* $barSeries->getGradient()->setUseMiddle(false);
* $barSeries->getGradient()->setMiddleColor(Color.YELLOW);
return $this->getBrush()->getGradient();
* Calculates Colors based on highest bar when Gradient is Visible.<br>
return $this->gradientRelative;
* Calculates Colors based on highest bar when Gradient is Visible.<br>
* Allows stacking independent Series within the same Chart, in
return $this->stackGroup;
* Allows stacking independent Series within the same Chart, in
* <pre><font face="Courier" size="4">
* bar1Series.setStackGroup(0);
* bar2Series.setStackGroup(1);
if ($this->depthPercent != 0) {
* Determines the percent amount of bar size in "z" depth direction.
return $this->depthPercent;
* Determines the percent amount of bar size in "z" depth direction.
* <pre><font face="Courier" size="4">
* series.setDepthPercent(50) ; // % of 3D depth
* Darkens sides of bars to enhance 3D effect.<br>
* This has effect only when Chart.Aspect.View3D is true.
* High color video modes (greater than 256 colors) will show dark colors
* much better than 256 or 16 color modes. <br>
* Darkens sides of bars to enhance 3D effect.<br>
private function setOtherBars($setOthers) {
if ($this->chart != null) {
for ( $t = 0; $t < $this->chart->getSeriesCount(); $t++ ) {
$s = $this->chart->getSeries($t);
$tmpBar->sideMargins = $this->sideMargins;
$this->sideMargins = $tmpBar->sideMargins;
* Margin between Chart rectangle and Bars.<br>
return $this->sideMargins;
* Sets a margin between Chart rectangle and Bars.<br>
$this->setOtherBars(true);
* Obsolete. Please use CustomBar.<!-- -->Origin instead.
* Obsolete. Please use CustomBar.<!-- -->Origin instead.
* Bars to be bottom aligned at the Origin method value. <br>
* When false, the minimum of all Bar values is used as the Bar origins
* When true, the Origin property is used as the start point for Bars. <br>
* Allows Bars to be bottom aligned at the Origin method value. <br>
* The common bottom value used for all Bar points.<br>
* UseOrigin must be true (the default) to use the Origin property. <br>
* Bars with a value bigger than Origin are drawn in one direction and
* Bars with a lower value are drawn in the opposite direction.
* This applies both to Bar series and HorizBar series classes.<br>
* Sets the common bottom value used for all Bar points.<br>
* Repositions Marks on BarSeries to prevent overlapping.<br>
* Marks are displaced to the top of the Bars to minimize the overlapping
* effect of Marks with long text or big font sizes.<br>
* When false, no checking is performed and all Marks are drawn at their
* Mark.ArrowLength distance to the top of the Bar.<br>
return $this->autoMarkPosition;
* Repositions Marks on BarSeries to prevent overlapping.<br>
* The apex size as percentage of the base.<br>
* Sets the apex size as a percentage of the base.<br>
* The Bar displacement as percentage of Bar size.<br>
* Displacement is horizontal for Bar series and vertical for HorizBar
* series. It can be used to create "overlayed" Bar charts.
* You can specify positive or negative values. <br>
return $this->offsetPercent;
* Sets the Bar displacement as percentage of Bar size.<br>
* Defines the Bar shape used to draw Bars.<br>
* Default value: BarStyle.Rectangle
* Defines the Bar shape used to draw Bars.<br>
* Default value: BarStyle.Rectangle
if ($this->barStyle != $value) {
$this->barStyle = $value;
/* TODO if ($this->barStyle == BarStyle::$RECTGRADIENT) {
$this->getGradient()->setVisible(true);
$this->getGradient()->setVisible(false);
* Defines the Brush used to fill Bars.<br>
* When BarBrush.Style is different than bsSolid, the Series.Color color
* is the background bar color.
if ($this->pPen != null) {
$this->setOtherBars(false);
* Determines how multiple BarSeries will be displayed in the same
* If you have more than one Bar series in the same Chart, then you can
* choose if they will be drawn side-by-side, back-to-front or Stacked.<br>
* Side-by-side means the Bar width will be divided by the number of Bar
* Default value: MultiBars.Side
* Determines how multiple BarSeries will be displayed in the same
* Default value: MultiBars.Side
$this->setOtherBars(true);
* Pen used to draw the Bar rectangles.<br>
* You can set BarPen.Visible = false to hide these lines.
if ($this->pPen == null) {
$tmpColor = new Color(0,0,0);
* Coordinates of current Bar point being displayed.<br>
* Run-time and read-only. <br>
* This function returns an internal variable, that is calculated only
* when the Bar Series DrawValue method is called.<br>
* You should only use BarBounds in custom-derived series, after
* calling the "inherited DrawValue" method.
private function calcGradientColor($valueIndex) {
if ($this->gradientRelative) {
$tmpRatio = ($this->mandatory->value[$valueIndex] - $tmp) /
$t0 = $g->getStartColor()->getRed();
$t1 = $g->getStartColor()->getGreen();
$t2 = $g->getStartColor()->getBlue();
/* TODO $g->setEndColor($this->Color->fromArgb(
$g->getStartColor()->getAlpha(),
MathUtils::round($tmpRatio * ($this->normalBarColor->getRed() - $t0))),
MathUtils::round($tmpRatio *
($this->normalBarColor->getGreen() - $t1))),
MathUtils::round($tmpRatio * ($this->normalBarColor->getBlue() - $t2))))
$style = $this->barStyle;
if ($this->styleResolver != null) {
$style = $this->styleResolver->getStyle($this, $valueIndex, $style);
private function internalPointOrigin($valueIndex, $sumAll) {
$tmpValue = $this->mandatory->value[$valueIndex];
if ($this->chart != null) {
for ( $t = 0; $t < $this->chart->getSeriesCount(); $t++ ) {
$s = $this->chart->getSeries($t);
if ((!$sumAll) && ($s === $this)) {
if ($s->getActive() && $this->sameClass($s) && ($s->getCount() > $valueIndex)
&& ($s->stackGroup == $this->stackGroup)) {
$tmp = $s->getOriginValue($valueIndex);
$result += $tmp; /* 5.01 */
if ($this->pPen->getVisible()) {
$this->calcGradientColor($valueIndex);
$this->getGradient()->draw($this->chart->getGraphics3D(), $p0->x, $p0->y, $p1->x, $p1->y);
* Displays a Bar or HorizBar point using the parameter coordinates and
* the BarColor parameter. <br>
* It is internally called for each point in the Series. <br>
* The BarStyle property determines the type of graphical representation
* of every point (ie: Rectangle, Ellipse, Pyramid, etc).
$this->_barRectangle($barColor, $r->x, $r->y, $r->getRight(), $r->getBottom());
* Displays a Bar or HorizBar point using the parameter coordinates and
* the BarColor parameter. <br>
* It is internally called for each point in the Series. <br>
* The BarStyle property determines the type of graphical representation
* of every point (ie: Rectangle, Ellipse, Pyramid, etc).
public function _barRectangle($barColor, $aLeft, $aTop, $aRight, $aBottom) {
$g = $this->chart->getGraphics3D();
if ($this->bBrush->getSolid()) {
if (($aRight == $aLeft) || ($aTop == $aBottom)) {
$g->getPen()->setColor($g->getBrush()->getColor());
$g->getPen()->setVisible(true);
$g->line($aLeft, $aTop, $aRight, $aBottom);
if ((abs($aRight - $aLeft) < $g->getPen()->getWidth()) ||
(abs($aBottom - $aTop) < $g->getPen()->getWidth())) {
$g->getPen()->setColor($g->getBrush()->getColor());
$g->getPen()->setVisible(true);
$g->getBrush()->setVisible(false);
$tmpR->setRight($aRight);
$tmpR->setBottom($aBottom);
$this->calcGradientColor($valueIndex);
if ($this->pPen->getVisible()) {
$this->chart->getGraphics3D()->getBrush()->setVisible(false);
$this->chart->invalidate();
private function doCalcBarWidth() {
if ($this->iMaxBarPoints > 0) {
// tmp=MathUtils.round(tmpAxis.IAxisSize/(2.0+tmpAxis.Maximum-tmpAxis.Minimum));
if ($this->sideMargins) {
$tmp = $tmpAxis->iAxisSize / $this->iMaxBarPoints;
* Returns side margin amount in pixels.
if (!$this->sideMargins) {
$result = ($tmp != 0) ? $this->calcPosValue($tmpValue * 100.0 / $tmp) : 0;
for ( $t = 0; $t < $this->getCount(); $t++ ) {
* The PointOrigin function returns the summed values of more than one
* It's only used by Series types with Stacked or Stacked 100% styles such
* as BarSeries, HorizBar series and Area series.
return $this->internalPointOrigin($valueIndex, $sumAll);
for ( $t = 0; $t < $valueIndex; $t++ ) {
for ( $t = 0; $t < $this->getCount(); $t++ ) {
for ( $t = 0; $t < $this->chart->getSeriesCount(); $t++ ) {
$s = $this->chart->getSeries($t);
$tmpZOrder = $s->getZOrder();
private function newGroup($aGroup) {
for ( $t = 0; $t < $this->numGroups; $t++ ) {
if ($this->groups[$t] == $aGroup) {
$this->groups[$this->numGroups] = $aGroup;
// if more than one bar series exists in chart,
// which position are we? the first, the second, the third?
$this->iMaxBarPoints = - 1;
for ( $t = 0; $t < $this->chart->getSeriesCount(); $t++ ) {
$s = $this->chart->getSeries($t);
if ($s->getActive() && $this->sameClass($s)) {
if (($this->iMaxBarPoints == - 1) || ($tmp > $this->iMaxBarPoints)) {
$this->iMaxBarPoints = $tmp;
if ($this->newGroup($s->stackGroup)) {
for ( $tt = 0; $tt < $this->numGroups; $tt++ ) {
if ($this->groups[$tt] == $this->stackGroup) {
// this should be done after calculating INumBars
if ($this->chart->getPage()->getMaxPointsPerPage() > 0) {
$this->iMaxBarPoints = $this->chart->getPage()->getMaxPointsPerPage();
if ($this->getBrush()->getImage() != null) {
$g->getBrush()->setImage($this->bBrush->getImage());
if ($this->offsetPercent != 0) {
$this->chart->getGraphics3D()->setFont($this->getMarks()->getFont());
$result = $this->getMarks()->getArrowLength() +
if ($this->getMarks()->getPen()->getVisible()) {
* Returns the ValueIndex of the "clicked" point in the Series.<br>
* Clicked means the X and Y coordinates are in the point screen region
* bounds. If no point is "touched", Clicked returns -1
if ($this->chart != null) {
$p = $this->chart->getGraphics3D()->calculate2DPosition($x, $y,
if (($this->chart != null) && ($this->chart->getSeriesCount() > 1)) {
for ( $t = 0; $t < $this->chart->getSeriesCount(); $t++ ) {
$s = $this->chart->getSeries($t);
if (($s != $this) && ($s instanceof CustomBar) &&
$this->chart->getGraphics3D()->setPen($this->pPen);
/* todo change the isnull if ($barColor->isNull()) {
$this->chart->getGraphics3D()->getPen()->setColor($barColor);
if ($this->getBrush()->getColor()->isEmpty()) {
/* TODO public function createSubGallery(
super.createSubGallery(addSubChart);
addSubChart.createSubChart(Language.getString("Colors"));
addSubChart.createSubChart(Language.getString("Pyramid"));
addSubChart.createSubChart(Language.getString("Ellipse"));
addSubChart.createSubChart(Language.getString("InvPyramid"));
addSubChart.createSubChart(Language.getString("Gradient"));
addSubChart.createSubChart(Language.getString("Stack"));
addSubChart.createSubChart(Language.getString("Stack"));
addSubChart.createSubChart(Language.getString("SelfStack"));
addSubChart.createSubChart(Language.getString("Sides"));
addSubChart.createSubChart(Language.getString("SideAll"));
/* public function setSubGallery($index) {
$this->setColorEach(true);
$this->setBarStyle(BarStyle::$PYRAMID);
$this->setBarStyle(BarStyle::$ELLIPSE);
$this->setBarStyle(BarStyle::$INVPYRAMID);
$this->setBarStyle(BarStyle::$RECTGRADIENT);
if (($this->chart != null) &&
($this->chart->getSeriesCount() == 1)) {
$this->fillSampleValues(2);
$tmp = ($this->Series) $this->getClass()->newInstance();
$this->getChart()->addSeries($tmp);
$tmp->setTitle(""); // <-- $and $this->others
$tmp->fillSampleValues(2);
$tmp->getMarks()->setVisible(false);
(($this->CustomBar) ($tmp))->barSizePercent = $this->barSizePercent;
$this->getMarks()->setVisible(false);
$tmp->setSubGallery($index);
if (!$subGalleryStack()) {
$this->setMultiBar(MultiBars::$STACKED);
$this->setMultiBar(MultiBars::$STACKED100);
$this->setMultiBar(MultiBars::$SELFSTACK);
$this->setMultiBar(MultiBars::$SIDE);
$this->setMultiBar(MultiBars::$SIDEALL);
parent::setSubGallery($index);
/* tODO public $BarStyleResolver ${
public function getStyle($series, $valueIndex, $style);
|