Joomla: How to Add Filtering and Ordering to a Component Backend Page

This tutorial will teach you how to add filtering and ordering to a component back-end page in Joomla. For easiness, I’m breaking the steps in three parts:

  1. Create a class that will generate the drop-down menu options.
  2. Modify the view to show the form drop-down.
  3. Modify the model to fetch data from database and also set values.

Extending JFormFieldList

Basically, your ordering & filtering fields will be very simple. May a drop-down list of one of the columns that will display on the current page. Creating your own field element is not difficult because it will have less code. I’m using the below code to generate drop-down element to filter by anything for example companies. Save below code in models/fields/yourfieldname.php.

[code type=”php”]
<?php

defined(‘JPATH_BASE’) or die;
jimport(‘joomla.form.helper’);
jimport(‘joomla.form.formfield’);
jimport(‘joomla.html.html’);
JFormHelper::loadFieldClass(‘list’);

class JFormFieldMyCompany extends JFormFieldList //Class Specifies the custom class by field name
{

protected $type = ‘MyCompany’;

public function getOptions()
{
// Initialize variables.
$options = array();

$db     = JFactory::getDbo();
$query  = $db->getQuery(true);

$query->select(‘id As value, name As text’);
$query->from(‘#__my_companies AS a’);
$query->order(‘a.name’);
$query->where(‘state = 1’);

// Get the options.
$db->setQuery($query);

$options = $db->loadObjectList();

// Check for a database error.
if ($db->getErrorNum()) {
JError::raiseWarning(500, $db->getErrorMsg());
}

return $options;
}
}
?>
[/code]

Note: In the database, I’ll recommend not to change text names and value but you can change if you are expert.

Modify Model

Now create a file in models/anything.php directory and put two functions.

[code type=”php”]
//Add this handy array with database fields to search in
protected $searchInFields = array(‘text’,’a.name’,’someotherfieldtosearchin’);

//Override construct to allow filtering and ordering on our fields
public function __construct($config = array()) {
$config[‘filter_fields’]=array_merge($this->searchInFields,array(‘a.company’));
parent::__construct($config);
}

protected function populateState($ordering = null, $direction = null)
{
// Initialise variables.
$app = JFactory::getApplication(‘administrator’);

// Load the filter state.
$search = $this->getUserStateFromRequest($this->context.’.filter.search’, ‘filter_search’);
//Omit double (white-)spaces and set state
$this->setState(‘filter.search’, preg_replace(‘/\s+/’,’ ‘, $search));

//Filter (dropdown) state
$state = $this->getUserStateFromRequest($this->context.’.filter.state’, ‘filter_state’, ”, ‘string’);
$this->setState(‘filter.state’, $state);

//Filter (dropdown) company
$state = $this->getUserStateFromRequest($this->context.’.filter.company’, ‘filter_company’, ”, ‘string’);
$this->setState(‘filter.company’, $state);

//Takes care of states: list. limit / start / ordering / direction
parent::populateState(‘a.name’, ‘asc’);
}

protected function getListQuery(){
$db = JFactory::getDBO();
$query = $db->getQuery(true);

//CHANGE THIS QUERY AS YOU NEED…
$query->select(‘id As value, name As text, somefield’)
->from(‘#__my_companies AS a’)
->order(        $db->escape($this->getState(‘list.ordering’, ‘pa.id’)) . ‘ ‘ .
$db->escape($this->getState(‘list.direction’, ‘desc’)));

// Filter search // Extra: Search more than one fields and for multiple words
$regex = str_replace(‘ ‘, ‘|’, $this->getState(‘filter.search’));
if (!empty($regex)) {
$regex=’ REGEXP ‘.$db->quote($regex);
$query->where(‘(‘.implode($regex.’ OR ‘,$this->searchInFields).$regex.’)’);
}

// Filter company
$company= $db->escape($this->getState(‘filter.company’));
if (!empty($company)) {
$query->where(‘(a.company=’.$company.’)’);
}

// Filter by state (published, trashed, etc.)
$state = $db->escape($this->getState(‘filter.state’));
if (is_numeric($state)) {
$query->where(‘a.state = ‘ . (int) $state);
}
elseif ($state === ”) {
$query->where(‘(a.state = 0 OR a.state = 1)’);
}

//echo $db->replacePrefix( (string) $query );//debug
return $query;
}

[/code]

Now in view model put the following lines of code.

[code type=”php”]
$this->items  = $this->get(‘Items’);
$this->pagination= $this->get(‘Pagination’);
$this->state = $this->get(‘State’);
$this->searchterms = $this->state->get(‘filter.search’);
$this->sortDirection = $this->state->get(‘list.direction’);
$this->sortColumn  = $this->state->get(‘list.ordering’);
[/code]

Now go to views/anyname/tmpl/default.php put the following code.

[code type=”php”]
JFormHelper::addFieldPath(JPATH_COMPONENT . ‘/models/fields’);
$companies = JFormHelper::loadFieldType(‘MyCompany’, false);
$companyOptions=$companies->getOptions(); // works only if you set your field getOptions on public!!
[/code]

You have done everything now set filter on your template like below:

[code type=”php”]
<fieldset id=”filter-bar”>
<div>
<input type=”text” name=”filter_search” id=”filter_search” value=”<?php echo $this->escape($this->searchterms); ?>” title=”<?php echo JText::_(‘Search in company, etc.’); ?>” />
<button type=”submit”>
<?php echo JText::_(‘JSEARCH_FILTER_SUBMIT’); ?>
</button>
<button type=”button” onclick=”document.id(‘filter_search’).value=”;this.form.submit();”>
<?php echo JText::_(‘JSEARCH_FILTER_CLEAR’); ?>
</button>
</div>
<div>
<select name=”filter_state” onchange=”this.form.submit()”>
<option value=””>
<?php echo JText::_(‘JOPTION_SELECT_PUBLISHED’);?>
</option>
<?php echo JHtml::_(‘select.options’, JHtml::_(‘jgrid.publishedOptions’, array(‘archived’=>false)), ‘value’, ‘text’, $this->state->get(‘filter.state’), true);?>
</select>
</div>
</fieldset>
[/code]

I hope you will find this tutorial useful.

Duan Lingxin

Duan Lingxin

Content crafter and chief editor at Scratching Info. Also regular contributor on other major online tech platforms. Security Specialist by day and a writer by night, he does his best to instill his knowledge about tech while delivering inspiring and life changing resources through his writing,

More Posts - Website

Leave a Comment