Multi sort in admin generator
Here we go !
The sort in admin generator is for a single field only, but in some complex list, it can be usefull to sort by multiple criterias. This is the main goal of this snippet. Those functions therefore override the ones of your auto-generated class. (1) And to display what are the ongoing sort criterias, you have to modify your '_list_th_tabular.php' file.
1 - In your 'action.class.php'
//
/**
* Add a sort criteria
*/
protected function processSort ()
{
$sort = $this->getRequestParameter('sort');
$type = $this->getRequestParameter('type');
// Register sort
if ($sort) {
$this->getUser()->setAttribute($sort, $type, 'sf_admin/produits/sort');
}
}
/**
* Add the sort criterias to the query
*/
protected function addSortCriteria(&$c)
{
$multisort = $this->getUser()->getAttributeHolder()->getAll('sf_admin/produits/sort');
if ($multisort) {
foreach($multisort as $sort_column => $sort_type) {
$sort_column = Propel::getDB($c->getDbName())->quoteIdentifier($sort_column);
if ($sort_type == 'asc') {
$c->addAscendingOrderByColumn($sort_column);
}
elseif ($sort_type == 'desc') {
$c->addDescendingOrderByColumn($sort_column);
}
}
} else {
// Default sort
$sort_column = Propel::getDB($c->getDbName())->quoteIdentifier('libelle');
$c->addAscendingOrderByColumn($sort_column);
}
}
/**
* Specific function for multi-sort
*/
protected function processFilters ()
{
if ($this->getRequest()->hasParameter('filter'))
{
$filters = $this->getRequestParameter('filters');
// Multi-sort initialisation
if (!is_array($filters)) {
$this->getUser()->getAttributeHolder()->removeNamespace('sf_admin/produits/sort');
}
$this->getUser()->getAttributeHolder()->removeNamespace('sf_admin/produits/filters');
$this->getUser()->getAttributeHolder()->add($filters, 'sf_admin/produits/filters');
}
}
2 - In '_list_th_tabular.php'
(for each sortable field)
<?php
$multisort = $sf_user->getAttributeHolder()->getAll('sf_admin/produits/sort');
?>
<th id="sf_admin_list_th_libelle">
<?php
if (isset($multisort['libelle'])) {
echo link_to('Libellé', 'Produits/list?sort=libelle&type='. ($multisort['libelle'] == 'asc' ? 'desc' : 'asc'));
echo ' ('. $multisort['libelle'] . ')';
} else {
echo link_to('Libellé', 'Produits/list?sort=libelle&type=asc');
}
?>
</th>
'Produits' is the module name, 'libelle' is the field to sort.
Notes:
The 'reset button' of filters also initialize the multi-sort. The sort is made from the first field clicked to the last. That means, if you want a different primary sort you will have to use the reset filter button before.
PS: Obviously, this modification can be easly integrated in your backoffice theme, note that the default sort criteria set in the 'generator.yml' is used in the addSortCriteria function (from line // default sort)
COil :)

浙公网安备 33010602011771号