mirror of
https://we.phorge.it/source/phorge.git
synced 2024-11-29 10:12:41 +01:00
Provide chart function labels over the wire instead of making them up
Summary: Ref T13279. Makes charts incrementally more useful by allowing the server to provide labels and colors for functions. Test Plan: {F6438872} Reviewers: amckinley Reviewed By: amckinley Subscribers: yelirekim Maniphest Tasks: T13279 Differential Revision: https://secure.phabricator.com/D20501
This commit is contained in:
parent
c6052b41a6
commit
a80426b339
8 changed files with 149 additions and 20 deletions
|
@ -389,8 +389,9 @@ return array(
|
||||||
'rsrc/js/application/diffusion/behavior-pull-lastmodified.js' => 'c715c123',
|
'rsrc/js/application/diffusion/behavior-pull-lastmodified.js' => 'c715c123',
|
||||||
'rsrc/js/application/doorkeeper/behavior-doorkeeper-tag.js' => '6a85bc5a',
|
'rsrc/js/application/doorkeeper/behavior-doorkeeper-tag.js' => '6a85bc5a',
|
||||||
'rsrc/js/application/drydock/drydock-live-operation-status.js' => '47a0728b',
|
'rsrc/js/application/drydock/drydock-live-operation-status.js' => '47a0728b',
|
||||||
'rsrc/js/application/fact/Chart.js' => 'b88a227d',
|
'rsrc/js/application/fact/Chart.js' => 'eec96de0',
|
||||||
'rsrc/js/application/fact/ChartCurtainView.js' => 'd10a3c25',
|
'rsrc/js/application/fact/ChartCurtainView.js' => '86954222',
|
||||||
|
'rsrc/js/application/fact/ChartFunctionLabel.js' => '81de1dab',
|
||||||
'rsrc/js/application/files/behavior-document-engine.js' => '243d6c22',
|
'rsrc/js/application/files/behavior-document-engine.js' => '243d6c22',
|
||||||
'rsrc/js/application/files/behavior-icon-composer.js' => '38a6cedb',
|
'rsrc/js/application/files/behavior-icon-composer.js' => '38a6cedb',
|
||||||
'rsrc/js/application/files/behavior-launch-icon-composer.js' => 'a17b84f1',
|
'rsrc/js/application/files/behavior-launch-icon-composer.js' => 'a17b84f1',
|
||||||
|
@ -697,8 +698,9 @@ return array(
|
||||||
'javelin-behavior-user-menu' => '60cd9241',
|
'javelin-behavior-user-menu' => '60cd9241',
|
||||||
'javelin-behavior-view-placeholder' => 'a9942052',
|
'javelin-behavior-view-placeholder' => 'a9942052',
|
||||||
'javelin-behavior-workflow' => '9623adc1',
|
'javelin-behavior-workflow' => '9623adc1',
|
||||||
'javelin-chart' => 'b88a227d',
|
'javelin-chart' => 'eec96de0',
|
||||||
'javelin-chart-curtain-view' => 'd10a3c25',
|
'javelin-chart-curtain-view' => '86954222',
|
||||||
|
'javelin-chart-function-label' => '81de1dab',
|
||||||
'javelin-color' => '78f811c9',
|
'javelin-color' => '78f811c9',
|
||||||
'javelin-cookie' => '05d290ef',
|
'javelin-cookie' => '05d290ef',
|
||||||
'javelin-diffusion-locate-file-source' => '94243d89',
|
'javelin-diffusion-locate-file-source' => '94243d89',
|
||||||
|
@ -1933,11 +1935,6 @@ return array(
|
||||||
'javelin-dom',
|
'javelin-dom',
|
||||||
'phabricator-draggable-list',
|
'phabricator-draggable-list',
|
||||||
),
|
),
|
||||||
'b88a227d' => array(
|
|
||||||
'phui-chart-css',
|
|
||||||
'd3',
|
|
||||||
'javelin-chart-curtain-view',
|
|
||||||
),
|
|
||||||
'b9109f8f' => array(
|
'b9109f8f' => array(
|
||||||
'javelin-behavior',
|
'javelin-behavior',
|
||||||
'javelin-uri',
|
'javelin-uri',
|
||||||
|
@ -2128,6 +2125,12 @@ return array(
|
||||||
'phabricator-keyboard-shortcut',
|
'phabricator-keyboard-shortcut',
|
||||||
'javelin-stratcom',
|
'javelin-stratcom',
|
||||||
),
|
),
|
||||||
|
'eec96de0' => array(
|
||||||
|
'phui-chart-css',
|
||||||
|
'd3',
|
||||||
|
'javelin-chart-curtain-view',
|
||||||
|
'javelin-chart-function-label',
|
||||||
|
),
|
||||||
'ef836bf2' => array(
|
'ef836bf2' => array(
|
||||||
'javelin-behavior',
|
'javelin-behavior',
|
||||||
'javelin-dom',
|
'javelin-dom',
|
||||||
|
|
|
@ -2668,6 +2668,7 @@ phutil_register_library_map(array(
|
||||||
'PhabricatorChartFunction' => 'applications/fact/chart/PhabricatorChartFunction.php',
|
'PhabricatorChartFunction' => 'applications/fact/chart/PhabricatorChartFunction.php',
|
||||||
'PhabricatorChartFunctionArgument' => 'applications/fact/chart/PhabricatorChartFunctionArgument.php',
|
'PhabricatorChartFunctionArgument' => 'applications/fact/chart/PhabricatorChartFunctionArgument.php',
|
||||||
'PhabricatorChartFunctionArgumentParser' => 'applications/fact/chart/PhabricatorChartFunctionArgumentParser.php',
|
'PhabricatorChartFunctionArgumentParser' => 'applications/fact/chart/PhabricatorChartFunctionArgumentParser.php',
|
||||||
|
'PhabricatorChartFunctionLabel' => 'applications/fact/chart/PhabricatorChartFunctionLabel.php',
|
||||||
'PhabricatorChartRenderingEngine' => 'applications/fact/engine/PhabricatorChartRenderingEngine.php',
|
'PhabricatorChartRenderingEngine' => 'applications/fact/engine/PhabricatorChartRenderingEngine.php',
|
||||||
'PhabricatorChartStackedAreaDataset' => 'applications/fact/chart/PhabricatorChartStackedAreaDataset.php',
|
'PhabricatorChartStackedAreaDataset' => 'applications/fact/chart/PhabricatorChartStackedAreaDataset.php',
|
||||||
'PhabricatorChatLogApplication' => 'applications/chatlog/application/PhabricatorChatLogApplication.php',
|
'PhabricatorChatLogApplication' => 'applications/chatlog/application/PhabricatorChatLogApplication.php',
|
||||||
|
@ -8683,6 +8684,7 @@ phutil_register_library_map(array(
|
||||||
'PhabricatorChartFunction' => 'Phobject',
|
'PhabricatorChartFunction' => 'Phobject',
|
||||||
'PhabricatorChartFunctionArgument' => 'Phobject',
|
'PhabricatorChartFunctionArgument' => 'Phobject',
|
||||||
'PhabricatorChartFunctionArgumentParser' => 'Phobject',
|
'PhabricatorChartFunctionArgumentParser' => 'Phobject',
|
||||||
|
'PhabricatorChartFunctionLabel' => 'Phobject',
|
||||||
'PhabricatorChartRenderingEngine' => 'Phobject',
|
'PhabricatorChartRenderingEngine' => 'Phobject',
|
||||||
'PhabricatorChartStackedAreaDataset' => 'PhabricatorChartDataset',
|
'PhabricatorChartStackedAreaDataset' => 'PhabricatorChartDataset',
|
||||||
'PhabricatorChatLogApplication' => 'PhabricatorApplication',
|
'PhabricatorChatLogApplication' => 'PhabricatorApplication',
|
||||||
|
|
|
@ -4,6 +4,7 @@ abstract class PhabricatorChartFunction
|
||||||
extends Phobject {
|
extends Phobject {
|
||||||
|
|
||||||
private $argumentParser;
|
private $argumentParser;
|
||||||
|
private $functionLabel;
|
||||||
|
|
||||||
final public function getFunctionKey() {
|
final public function getFunctionKey() {
|
||||||
return $this->getPhobjectClassConstant('FUNCTIONKEY', 32);
|
return $this->getPhobjectClassConstant('FUNCTIONKEY', 32);
|
||||||
|
@ -43,6 +44,22 @@ abstract class PhabricatorChartFunction
|
||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function setFunctionLabel(PhabricatorChartFunctionLabel $label) {
|
||||||
|
$this->functionLabel = $label;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getFunctionLabel() {
|
||||||
|
if (!$this->functionLabel) {
|
||||||
|
$this->functionLabel = id(new PhabricatorChartFunctionLabel())
|
||||||
|
->setName(pht('Unlabeled Function'))
|
||||||
|
->setColor('rgba(255, 0, 0, 1)')
|
||||||
|
->setFillColor('rgba(255, 0, 0, 0.15)');
|
||||||
|
}
|
||||||
|
|
||||||
|
return $this->functionLabel;
|
||||||
|
}
|
||||||
|
|
||||||
final public static function newFromDictionary(array $map) {
|
final public static function newFromDictionary(array $map) {
|
||||||
PhutilTypeSpec::checkMap(
|
PhutilTypeSpec::checkMap(
|
||||||
$map,
|
$map,
|
||||||
|
|
|
@ -0,0 +1,56 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
final class PhabricatorChartFunctionLabel
|
||||||
|
extends Phobject {
|
||||||
|
|
||||||
|
private $name;
|
||||||
|
private $color;
|
||||||
|
private $icon;
|
||||||
|
private $fillColor;
|
||||||
|
|
||||||
|
public function setName($name) {
|
||||||
|
$this->name = $name;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getName() {
|
||||||
|
return $this->name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setColor($color) {
|
||||||
|
$this->color = $color;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getColor() {
|
||||||
|
return $this->color;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setIcon($icon) {
|
||||||
|
$this->icon = $icon;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getIcon() {
|
||||||
|
return $this->icon;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setFillColor($fill_color) {
|
||||||
|
$this->fillColor = $fill_color;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getFillColor() {
|
||||||
|
return $this->fillColor;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function toWireFormat() {
|
||||||
|
return array(
|
||||||
|
'name' => $this->getName(),
|
||||||
|
'color' => $this->getColor(),
|
||||||
|
'icon' => $this->getIcon(),
|
||||||
|
'fillColor' => $this->getFillColor(),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -131,15 +131,20 @@ final class PhabricatorChartStackedAreaDataset
|
||||||
$events[] = $event_list;
|
$events[] = $event_list;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$wire_labels = array();
|
||||||
|
foreach ($functions as $function_key => $function) {
|
||||||
|
$label = $function->getFunctionLabel();
|
||||||
|
|
||||||
|
$label->setName(pht('Important Data %s', $function_key));
|
||||||
|
|
||||||
|
$wire_labels[] = $label->toWireFormat();
|
||||||
|
}
|
||||||
|
|
||||||
$result = array(
|
$result = array(
|
||||||
'type' => $this->getDatasetTypeKey(),
|
'type' => $this->getDatasetTypeKey(),
|
||||||
'data' => $series,
|
'data' => $series,
|
||||||
'events' => $events,
|
'events' => $events,
|
||||||
'color' => array(
|
'labels' => $wire_labels,
|
||||||
'blue',
|
|
||||||
'cyan',
|
|
||||||
'green',
|
|
||||||
),
|
|
||||||
);
|
);
|
||||||
|
|
||||||
return $result;
|
return $result;
|
||||||
|
|
13
webroot/rsrc/js/application/fact/Chart.js
vendored
13
webroot/rsrc/js/application/fact/Chart.js
vendored
|
@ -3,6 +3,7 @@
|
||||||
* @requires phui-chart-css
|
* @requires phui-chart-css
|
||||||
* d3
|
* d3
|
||||||
* javelin-chart-curtain-view
|
* javelin-chart-curtain-view
|
||||||
|
* javelin-chart-function-label
|
||||||
*/
|
*/
|
||||||
JX.install('Chart', {
|
JX.install('Chart', {
|
||||||
|
|
||||||
|
@ -144,13 +145,19 @@ JX.install('Chart', {
|
||||||
.y(function(d) { return y(d.y1); });
|
.y(function(d) { return y(d.y1); });
|
||||||
|
|
||||||
for (var ii = 0; ii < dataset.data.length; ii++) {
|
for (var ii = 0; ii < dataset.data.length; ii++) {
|
||||||
|
var label = new JX.ChartFunctionLabel(dataset.labels[ii]);
|
||||||
|
|
||||||
|
var fill_color = label.getFillColor() || label.getColor();
|
||||||
|
|
||||||
g.append('path')
|
g.append('path')
|
||||||
.style('fill', dataset.color[ii % dataset.color.length])
|
.style('fill', fill_color)
|
||||||
.style('opacity', '0.15')
|
|
||||||
.attr('d', area(dataset.data[ii]));
|
.attr('d', area(dataset.data[ii]));
|
||||||
|
|
||||||
|
var stroke_color = label.getColor();
|
||||||
|
|
||||||
g.append('path')
|
g.append('path')
|
||||||
.attr('class', 'line')
|
.attr('class', 'line')
|
||||||
|
.style('stroke', stroke_color)
|
||||||
.attr('d', line(dataset.data[ii]));
|
.attr('d', line(dataset.data[ii]));
|
||||||
|
|
||||||
g.selectAll('dot')
|
g.selectAll('dot')
|
||||||
|
@ -181,7 +188,7 @@ JX.install('Chart', {
|
||||||
div.style('opacity', 0);
|
div.style('opacity', 0);
|
||||||
});
|
});
|
||||||
|
|
||||||
curtain.addFunctionLabel('Important Data');
|
curtain.addFunctionLabel(label);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
|
|
@ -64,17 +64,21 @@ JX.install('ChartCurtainView', {
|
||||||
return this._labelsNode;
|
return this._labelsNode;
|
||||||
},
|
},
|
||||||
|
|
||||||
_newFunctionLabelItem: function(item) {
|
_newFunctionLabelItem: function(label) {
|
||||||
var item_attrs = {
|
var item_attrs = {
|
||||||
className: 'chart-function-label-list-item'
|
className: 'chart-function-label-list-item'
|
||||||
};
|
};
|
||||||
|
|
||||||
var icon = new JX.PHUIXIconView()
|
var icon = new JX.PHUIXIconView()
|
||||||
.setIcon('fa-circle');
|
.setIcon(label.getIcon());
|
||||||
|
|
||||||
|
// Charts may use custom colors, so we can't rely on the CSS classes
|
||||||
|
// which only provide standard colors like "red" and "blue".
|
||||||
|
icon.getNode().style.color = label.getColor();
|
||||||
|
|
||||||
var content = [
|
var content = [
|
||||||
icon.getNode(),
|
icon.getNode(),
|
||||||
item
|
label.getName()
|
||||||
];
|
];
|
||||||
|
|
||||||
return JX.$N('li', item_attrs, content);
|
return JX.$N('li', item_attrs, content);
|
||||||
|
|
35
webroot/rsrc/js/application/fact/ChartFunctionLabel.js
Normal file
35
webroot/rsrc/js/application/fact/ChartFunctionLabel.js
Normal file
|
@ -0,0 +1,35 @@
|
||||||
|
/**
|
||||||
|
* @provides javelin-chart-function-label
|
||||||
|
*/
|
||||||
|
JX.install('ChartFunctionLabel', {
|
||||||
|
|
||||||
|
construct: function(spec) {
|
||||||
|
this._name = spec.name;
|
||||||
|
this._color = spec.color;
|
||||||
|
this._icon = spec.icon;
|
||||||
|
this._fillColor = spec.fillColor;
|
||||||
|
},
|
||||||
|
|
||||||
|
members: {
|
||||||
|
_name: null,
|
||||||
|
_color: null,
|
||||||
|
_icon: null,
|
||||||
|
_fillColor: null,
|
||||||
|
|
||||||
|
getColor: function() {
|
||||||
|
return this._color;
|
||||||
|
},
|
||||||
|
|
||||||
|
getName: function() {
|
||||||
|
return this._name;
|
||||||
|
},
|
||||||
|
|
||||||
|
getIcon: function() {
|
||||||
|
return this._icon || 'fa-circle';
|
||||||
|
},
|
||||||
|
|
||||||
|
getFillColor: function() {
|
||||||
|
return this._fillColor;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
Loading…
Reference in a new issue