As you already know the real category filtering is taking place in app/code/core/Mage/Catalog/Model/Layer/Filter/Category.php
, more specifically in _getItemsData()
. Let us inspect that method.
<?php
$categoty = $this->getCategory();
$categories = $categoty->getChildrenCategories();
$this->getLayer()->getProductCollection()
->addCountToCategories($categories);
$data = array();
foreach ($categories as $category) {
if ($category->getIsActive() && $category->getProductCount()) {
$data[] = array(
'label' => Mage::helper('core')->escapeHtml($category->getName()),
'value' => $category->getId(),
'count' => $category->getProductCount(),
);
}
}
As you can see, the method loads child categories of $categoty
in layered navigation filter. That means we need to set this variable to a parent category in level 2 (Every main categories lies in level 2), according to the current category that we stands.
We can achieve this in many ways. In my method, I dig into the codes further and find the exact position where the category is set for layered navigation.
It resides here app/code/core/Mage/Catalog/Model/Layer.php
in getCurrentCategory()
. The method look like this.
<?php
public function getCurrentCategory()
{
$category = $this->getData('current_category');
if (is_null($category)) {
if ($category = Mage::registry('current_category')) {
$this->setData('current_category', $category);
}
else {
$category = Mage::getModel('catalog/category')->load($this->getCurrentStore()->getRootCategoryId());
$this->setData('current_category', $category);
}
}
return $category;
}
In short, it loads the current category to the variable $categoty
(variable that I mentioned in _getItemsData()
) if it set, otherwise loads the root-category
to variable categoty
. Replace this method with this code
<?php
/**
* Retrieve current category model
* If no category found in registry, the root will be taken
*
* @return Mage_Catalog_Model_Category
*/
public function getCurrentCategory()
{
$category = $this->getData('current_category');
if (is_null($category)) {
$category = Mage::registry('current_category');
if ($category) {
/*
* Check whether the current category is in level 2.
* If yes set it as current category.
* Else check for any parent categories with level 2
*/
if($category->getLevel() != 2) {
//gets all parent categories
$parentCategories = Mage::registry('current_category')->getParentCategories();
/*
* If parent categories exist,search for parent categories in level 2.
* If exist set it as current category.
*else set root category as current category.
*/
if(count($parentCategories) > 0)
{
foreach ( $parentCategories as $parentCategory ) {
if($parentCategory->getLevel() == 2 ) {
$category = Mage::getModel('catalog/category')->load($parentCategory->getId());
$this->setData('current_category', $category);
break;
}
}
}
else {
$category = Mage::getModel('catalog/category')->load($this->getCurrentStore()->getRootCategoryId());
$this->setData('current_category', $category);
}
}
else {
$this->setData('current_category', $category);
}
}
else {
$category = Mage::getModel('catalog/category')->load($this->getCurrentStore()->getRootCategoryId());
$this->setData('current_category', $category);
}
}
return $category;
}
What we are doing here is, we get the parent category in level 2 from the current category and set it to $categoty
, so that we can see all child categories in layered navigation.
As I already mentioned, you can achieve it in many ways. All you need to do is to set $categoty
variable with parent category in level 2. Above I have altered the root files. It is not a good practice. You have to create a module that rewrites the model file app/code/core/Mage/Catalog/Model/Layer.php
and then overwrite the method getCurrentCategory()
.
Hope it helps