157 if ( strpos( $groupDefinition[
'name'], self::RESERVED_NAME_CHAR ) !==
false ) {
158 throw new MWException(
'Group names may not contain \'' .
159 self::RESERVED_NAME_CHAR .
160 '\'. Use the naming convention: \
'camelCase\''
164 $this->name = $groupDefinition[
'name'];
166 if ( isset( $groupDefinition[
'title'] ) ) {
167 $this->title = $groupDefinition[
'title'];
170 if ( isset( $groupDefinition[
'whatsThisHeader'] ) ) {
171 $this->whatsThisHeader = $groupDefinition[
'whatsThisHeader'];
172 $this->whatsThisBody = $groupDefinition[
'whatsThisBody'];
173 $this->whatsThisUrl = $groupDefinition[
'whatsThisUrl'];
174 $this->whatsThisLinkText = $groupDefinition[
'whatsThisLinkText'];
177 $this->type = $groupDefinition[
'type'];
180 $this->isFullCoverage = $groupDefinition[
'isFullCoverage'];
183 $lowestSpecifiedPriority = -1;
184 foreach ( $groupDefinition[
'filters'] as $filterDefinition ) {
185 if ( isset( $filterDefinition[
'priority'] ) ) {
186 $lowestSpecifiedPriority = min( $lowestSpecifiedPriority, $filterDefinition[
'priority'] );
194 $autoFillPriority = $lowestSpecifiedPriority - 1;
195 foreach ( $groupDefinition[
'filters'] as $filterDefinition ) {
196 if ( !isset( $filterDefinition[
'priority'] ) ) {
197 $filterDefinition[
'priority'] = $autoFillPriority;
200 $filterDefinition[
'group'] = $this;
203 $this->registerFilter(
$filter );
229 public function conflictsWith( $other, $globalKey, $forwardKey, $backwardKey ) {
230 if ( $globalKey ===
null || $forwardKey ===
null || $backwardKey ===
null ) {
231 throw new MWException(
'All messages must be specified' );
240 $other->setUnidirectionalConflict(
260 $this->conflictingGroups[] = [
261 'group' => $other->getName(),
262 'groupObject' => $other,
263 'globalDescription' => $globalDescription,
264 'contextDescription' => $contextDescription,
267 $this->conflictingFilters[] = [
268 'group' => $other->getGroup()->getName(),
269 'filter' => $other->getName(),
270 'filterObject' => $other,
271 'globalDescription' => $globalDescription,
272 'contextDescription' => $contextDescription,
275 throw new MWException(
'You can only pass in a ChangesListFilterGroup or a ChangesListFilter' );
322 return $this->filters[
$name] ??
null;
343 if ( isset( $this->whatsThisHeader ) ) {
350 $output[
'messageKeys'],
351 $output[
'whatsThisHeader'],
352 $output[
'whatsThisBody'],
353 $output[
'whatsThisLinkText']
357 usort( $this->filters,
function ( $a, $b ) {
358 return $b->getPriority() <=> $a->getPriority();
361 foreach ( $this->filters as $filterName =>
$filter ) {
362 if (
$filter->displaysOnStructuredUi() ) {
363 $filterData =
$filter->getJsData();
364 $output[
'messageKeys'] = array_merge(
365 $output[
'messageKeys'],
366 $filterData[
'messageKeys']
368 unset( $filterData[
'messageKeys'] );
369 $output[
'filters'][] = $filterData;
373 if ( count( $output[
'filters'] ) === 0 ) {
379 $conflicts = array_merge(
380 $this->conflictingGroups,
381 $this->conflictingFilters
384 foreach ( $conflicts as $conflictInfo ) {
385 unset( $conflictInfo[
'filterObject'] );
386 unset( $conflictInfo[
'groupObject'] );
387 $output[
'conflicts'][] = $conflictInfo;
389 $output[
'messageKeys'],
390 $conflictInfo[
'globalDescription'],
391 $conflictInfo[
'contextDescription']
405 function ( $conflictDesc ) {
406 return $conflictDesc[
'groupObject' ];
419 function ( $conflictDesc ) {
420 return $conflictDesc[
'filterObject' ];
433 return (
bool)count( array_filter(
436 return $filter->isSelected( $opts );
458 &$tables, &$fields, &$conds, &$query_options, &$join_conds,
469 $isStructuredFiltersEnabled );
Represents a filter group (used on ChangesListSpecialPage and descendants)
$filters
Associative array of filters, as ChangesListFilter objects, with filter name as key.
$name
Name (internal identifier)
$whatsThisBody
i18n key for body of What's This?
anySelected(FormOptions $opts)
Check if any filter in this group is selected.
$whatsThisUrl
URL of What's This? link.
$isFullCoverage
Whether this group is full coverage.
modifyQuery(IDatabase $dbr, ChangesListSpecialPage $specialPage, &$tables, &$fields, &$conds, &$query_options, &$join_conds, FormOptions $opts, $isStructuredFiltersEnabled)
Modifies the query to include the filter group.
getFilter( $name)
Get filter by name.
$priority
Priority integer.
getConflictingGroups()
Get groups conflicting with this filter group.
$conflictingFilters
Array of associative arrays with conflict information.
getJsData()
Gets the JS data in the format required by the front-end of the structured UI.
__construct(array $groupDefinition)
Create a new filter group with the specified configuration.
$whatsThisHeader
i18n key for header of What's This?
addOptions(FormOptions $opts, $allowDefaults, $isStructuredFiltersEnabled)
All the options represented by this filter group to $opts.
getConflictingFilters()
Get filters conflicting with this filter group.
$conflictingGroups
Array of associative arrays with conflict information.
setUnidirectionalConflict( $other, $globalDescription, $contextDescription)
Marks that the given ChangesListFilterGroup or ChangesListFilter conflicts with this object.
createFilter(array $filterDefinition)
Creates a filter of the appropriate type for this group, from the definition.
$type
Type, from a TYPE constant of a subclass.
conflictsWith( $other, $globalKey, $forwardKey, $backwardKey)
Marks that the given ChangesListFilterGroup or ChangesListFilter conflicts with this object.
$whatsThisLinkText
i18n key for What's This? link
Represents a filter (used on ChangesListSpecialPage and descendants)
Special page which uses a ChangesList to show query results.