diff options
author | Moriel Schottlender <moriel@gmail.com> | 2018-07-26 16:14:41 -0700 |
---|---|---|
committer | Bartosz DziewoĆski <matma.rex@gmail.com> | 2018-08-22 21:31:27 +0200 |
commit | 5a430cdc1c0224b8e95509b58ad4be7abda2674c (patch) | |
tree | d62072d4fc96a1ae62a4591090d3381391e02af3 /includes/widget/CheckMatrixWidget.php | |
parent | 82acdac2c4f7553fefc7d3b1188cca1546b471d2 (diff) | |
download | mediawikicore-5a430cdc1c0224b8e95509b58ad4be7abda2674c.tar.gz mediawikicore-5a430cdc1c0224b8e95509b58ad4be7abda2674c.zip |
OOUIfy CheckMatrix in PHP and JS
This is to make sure that the design is similar, but also so
that the widget can be read in JS where needed and that we
can toggle the disabled state on/off through the whole widget,
that is made from a series of checkbox widgets.
Bug: T199946
Change-Id: I9943b0aa1746fdfb60c7d4c88d6d4d7ac0589a2c
Diffstat (limited to 'includes/widget/CheckMatrixWidget.php')
-rw-r--r-- | includes/widget/CheckMatrixWidget.php | 204 |
1 files changed, 204 insertions, 0 deletions
diff --git a/includes/widget/CheckMatrixWidget.php b/includes/widget/CheckMatrixWidget.php new file mode 100644 index 000000000000..7783f3185235 --- /dev/null +++ b/includes/widget/CheckMatrixWidget.php @@ -0,0 +1,204 @@ +<?php + +namespace MediaWiki\Widget; + +/** + * Check matrix widget. Displays a matrix of checkboxes for given options + * + * @copyright 2018 MediaWiki Widgets Team and others; see AUTHORS.txt + * @license MIT + */ +class CheckMatrixWidget extends \OOUI\Widget { + + protected $name = ''; + protected $columns = []; + protected $rows = []; + protected $tooltips = []; + protected $values = []; + protected $forcedOn = []; + protected $forcedOff = []; + + /** + * CheckMatrixWidget constructor + * + * Operates similarly to MultiSelectWidget, but instead of using an array of + * options, uses an array of rows and an array of columns to dynamically + * construct a matrix of options. The tags used to identify a particular cell + * are of the form "columnName-rowName" + * + * @param array $config Configuration array with the following options: + * - columns + * - Required list of columns in the matrix. + * - rows + * - Required list of rows in the matrix. + * - force-options-on + * - Accepts array of column-row tags to be displayed as enabled but unavailable to change + * - force-options-off + * - Accepts array of column-row tags to be displayed as disabled but unavailable to change. + * - tooltips + * - Optional array mapping row label to tooltip content + * - tooltip-class + * - Optional CSS class used on tooltip container span. Defaults to mw-icon-question. + */ + public function __construct( array $config = [] ) { + // Configuration initialization + + parent::__construct( $config ); + + $this->name = isset( $config['name'] ) ? + $config[ 'name' ] : null; + $this->id = isset( $config['id'] ) ? + $config['id'] : null; + + // Properties + $this->rows = isset( $config['rows'] ) ? + $config['rows'] : []; + $this->columns = isset( $config['columns'] ) ? + $config['columns'] : []; + $this->tooltips = isset( $config['tooltips'] ) ? + $config['tooltips'] : []; + + $this->values = isset( $config['values'] ) ? + $config['values'] : []; + + $this->forcedOn = isset( $config['forcedOn'] ) ? + $config['forcedOn'] : []; + $this->forcedOff = isset( $config['forcedOff'] ) ? + $config['forcedOff'] : []; + + // Build the table + $table = new \OOUI\Tag( 'table' ); + $tr = new \OOUI\Tag( 'tr' ); + // Build the header + $tr->appendContent( $this->getCellTag( "\u{00A0}" ) ); + foreach ( $this->columns as $columnLabel => $columnTag ) { + $tr->appendContent( + $this->getCellTag( $columnLabel ) + ); + } + $table->appendContent( $tr ); + + // Build the options matrix + foreach ( $this->rows as $rowLabel => $rowTag ) { + $table->appendContent( + $this->getTableRow( $rowLabel, $rowTag ) + ); + } + + // Initialization + $this->addClasses( [ 'mw-widget-checkMatrixWidget' ] ); + $this->appendContent( $table ); + } + + /** + * Get a formatted table row for the option, with + * a checkbox widget. + * + * @param string $label Row label + * @param string $tag Row tag name + * @return \OOUI\Tag The resulting table row + */ + private function getTableRow( $label, $tag ) { + $row = new \OOUI\Tag( 'tr' ); + $tooltip = $this->getTooltip( $label ); + $labelFieldConfig = $tooltip ? [ 'help' => $tooltip ] : []; + // Build label cell + $labelField = new \OOUI\FieldLayout( + new \OOUI\Widget(), // Empty widget, since we don't have the checkboxes here + [ + 'label' => $label, + 'align' => 'inline', + ] + $labelFieldConfig + ); + $row->appendContent( $this->getCellTag( $labelField ) ); + + // Build checkbox column cells + foreach ( $this->columns as $columnTag ) { + $thisTag = "$columnTag-$tag"; + + // Construct a checkbox + $checkbox = new \OOUI\CheckboxInputWidget( [ + 'value' => $thisTag, + 'name' => $this->name ? "{$this->name}[]" : null, + 'id' => $this->id ? "{$this->id}-$thisTag" : null, + 'selected' => $this->isTagChecked( $thisTag ), + 'disabled' => $this->isTagDisabled( $thisTag ), + ] ); + + $row->appendContent( $this->getCellTag( $checkbox ) ); + } + return $row; + } + + /** + * Get an individual cell tag with requested content + * + * @param string $content Content for the <td> cell + * @return \OOUI\Tag Resulting cell + */ + private function getCellTag( $content ) { + $cell = new \OOUI\Tag( 'td' ); + $cell->appendContent( $content ); + return $cell; + } + + /** + * Check whether the given tag's checkbox should + * be checked + * + * @param string $tagName Tag name + * @return boolean Tag should be checked + */ + private function isTagChecked( $tagName ) { + // If the tag is in the value list + return in_array( $tagName, (array)$this->values, true ) || + // Or if the tag is forced on + in_array( $tagName, (array)$this->forcedOn, true ); + } + + /** + * Check whether the given tag's checkbox should + * be disabled + * + * @param string $tagName Tag name + * @return boolean Tag should be disabled + */ + private function isTagDisabled( $tagName ) { + return ( + // If the entire widget is disabled + $this->isDisabled() || + // If the tag is 'forced on' or 'forced off' + in_array( $tagName, (array)$this->forcedOn, true ) || + in_array( $tagName, (array)$this->forcedOff, true ) + ); + } + + /** + * Get the tooltip help associated with this row + * + * @param string $label Label name + * @return string Tooltip. Null if none is available. + */ + private function getTooltip( $label ) { + return isset( $this->tooltips[ $label ] ) ? + $this->tooltips[ $label ] : null; + } + + protected function getJavaScriptClassName() { + return 'mw.widgets.CheckMatrixWidget'; + } + + public function getConfig( &$config ) { + $config += [ + 'name' => $this->name, + 'id' => $this->id, + 'rows' => $this->rows, + 'columns' => $this->columns, + 'tooltips' => $this->tooltips, + 'forcedOff' => $this->forcedOff, + 'forcedOn' => $this->forcedOn, + 'values' => $this->values, + ]; + return parent::getConfig( $config ); + } +} |