Magento – Add category tree structure in custom module form

adminformcategory-treemagento-1.9module

I want to have category tree structure in my custom module form as shown in below image-
enter image description here

i tried this link but no luck-
Add Category tree in custom extension

my module name is assel_po

here is my form.php

<?php

class Assel_Po_Block_Adminhtml_Poproduct_Edit_Form extends Mage_Adminhtml_Block_Widget_Form {

  protected function _prepareForm() {
        $form = new Varien_Data_Form(
            array(
                'id' => 'edit_form',
                'action' => $this->getUrl('*/*/save', array('po_product_id' => $this->getRequest()->getParam('po_product_id'))),
                'method' => 'post',
                'enctype' => 'multipart/form-data'
            )
        );

        $form->setUseContainer(true);
        $this->setForm($form);

        $fieldset1 = $form->addFieldset('poproduct_form', array('legend' => Mage::helper('po')->__('Add Product')));
        $fieldset2 = $form->addFieldset('poproduct_detail_form', array('legend' => Mage::helper('po')->__("Product's More Details")));

        //var_dump(Mage::getSingleton('po/brands')->getAllbrands());

        if (Mage::getSingleton('adminhtml/session')->getPoproductData()) 
        {
            $data = Mage::getSingleton('adminhtml/session')->getPoproductData();

            Mage::getSingleton('adminhtml/session')->getPoproductData(null);
        } 
        elseif (Mage::registry('poproduct_data')) 
        {
            $data = Mage::registry('poproduct_data')->getData();
        }


        /* Add fields in form */
        $po_id=$this->getRequest()->getParam('po_id');
        $data['po_id'] = $po_id;
        $fieldset1->addField('po_id', 'hidden', array(
            'name'      => 'po_id', 
            'value'      => $po_id,
        ));
    /*  
        $fieldset1->addField('new_exist', 'radios', array(
          'label'     => Mage::helper('po')->__('Choose any one'),
          'name'      => 'new_exist',
          'onclick' => "",
          'onchange' => "",
          'class'=>'new_exist',
          'value'  => '2',
          'values' => array(
                            array('value'=>'new','label'=>'Add New Product'),
                            array('value'=>'exist','label'=>'Update Existing Product'),
                       ),
          'disabled' => false,
          'readonly' => false,
          'tabindex' => 1
        ));
    */  

        $fieldset1->addField('product_id', 'text', array(
                'label' => Mage::helper('po')->__('Product Id'),
                'class' => 'product-id',
                'required' => true,
                'name' => 'product_id',
                'disabled' => true,
                //'readonly'=> $data['product_id']==''?true:false,
        ));

        $fieldset1->addField('product_name', 'text', array(
                'label' => Mage::helper('po')->__('Product Name'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'product_name',
        ));

        $fieldset1->addField('brand', 'select', array(
                'label' => Mage::helper('po')->__('Brand'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'brand',
                'values'    => Mage::getSingleton('po/brands')->getAllbrands(),
        ));

        $fieldset1->addField('case', 'text', array(
                'label' => Mage::helper('po')->__('Case'),
                'class' => '',
                'required' => false,
                'name' => 'case',
        ));

        $fieldset1->addField('upc', 'text', array(
                'label' => Mage::helper('po')->__('UPC'),
                'class' => '',
                'required' => true,
                'name' => 'upc',
        ));

        $fieldset1->addField('billed_qty', 'text', array(
                'label' => Mage::helper('po')->__('Billed Qty'),
                'class' => 'validate-digits',
                'required' => true,
                'name' => 'billed_qty',
        ));

        $fieldset1->addField('free_qty', 'text', array(
                'label' => Mage::helper('po')->__('Free Qty'),
                'class' => 'validate-digits',
                'required' => true,
                'name' => 'free_qty',
                'value'  => '0',
        ));


    /*  
        $fieldset1->addField('qty', 'text', array(
                'label' => Mage::helper('po')->__('Qty'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'qty',
        ));
    */

        $dateFormatIso = Mage::app()->getLocale()->getDateFormat(Mage_Core_Model_Locale::FORMAT_TYPE_SHORT);
        $fieldset1->addField('expiry_date', 'date', array(
                'label' => Mage::helper('po')->__('Expiry Date'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'expiry_date',
                'image'  => $this->getSkinUrl('images/grid-cal.gif'),
                'input_format' => $dateFormatIso,
                'format'       => $dateFormatIso,
                'time' => true
        ));

        $fieldset1->addField('mrp', 'text', array(
                'label' => Mage::helper('po')->__('MRP'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'mrp',
        ));

        $fieldset1->addField('rate', 'text', array(
                'label' => Mage::helper('po')->__('Rate'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'rate',
        ));


        $fieldset1->addField('tax', 'select', array(
                'label' => Mage::helper('po')->__('Tax(%)'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'tax',
                'values' => array(''=>'Select Tax','0' => 'Tax 0%','5' => 'Tax 5%', '14.5' => 'Tax 14.5')
        ));

        $fieldset1->addField('tax_amount', 'text', array(
                'label' => Mage::helper('po')->__('Tax Amount'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'tax_amount',
        ));

        $fieldset1->addField('special_price', 'text', array(
                'label' => Mage::helper('po')->__('Special Price'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'special_price',
        ));

        $fieldset1->addField('gross_amount', 'text', array(
                'label' => Mage::helper('po')->__('Gross Amount'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'gross_amount',
        ));


        $fieldset1->addField('net_amount', 'text', array(
                'label' => Mage::helper('po')->__('Net Amount'),
                'class' => 'required-entry',
                'required' => true,
                'name' => 'net_amount',
        ));

        $fieldset2->addField('category_ids', 'hidden', array(
                'label' => Mage::helper('po')->__('Category'),
                'class' => 'required-entry',
                'required' => false,
                'name' => 'category_ids',
        ));

        $fieldset2->addField('label', 'label', array(
                'label' => Mage::helper('po')->__('Category'),
                'class' => 'required-entry',
                'required' => false,
                'after_element_html' => $this->getLayout()->createBlock('po/adminhtml_poproduct_edit_categories')->toHtml(),
        ));





        $form->setValues($data);

        return parent::_prepareForm();

  }

}

here is categories.php-

<?php
class Assel_Po_Block_Adminhtml_Poproduct_Edit_Categories extends Mage_Adminhtml_Block_Catalog_Category_Tree {


    protected $_categoryIds = null;
    protected $_selectedNodes = null;
    public function __construct() {
        parent::__construct();
        $this->setTemplate('assel/po/categories.phtml');
        $this->_withProductCount = false;
    }

    public function getpoproduct(){
        return Mage::registry('current_poproduct'); //use other registration key if you have one
    }

    public function getCategoryIds(){
        if (is_null($this->_categoryIds)){
            $categories = $this->getpoproduct()->getSelectedCategories();
                $ids = array();
                foreach ($categories as $category){
                    $ids[] = $category->getId();
                }
                $this->_categoryIds = $ids;
        }
        return $this->_categoryIds;
    }


    public function getIdsString(){
        return implode(',', $this->getCategoryIds());
    }


    public function getRootNode(){
        $root = $this->getRoot();
        if ($root && in_array($root->getId(), $this->getCategoryIds())) {
            $root->setChecked(true);
        }
        return $root;
    }

    public function getRoot($parentNodeCategory = null, $recursionLevel = 3){
        if (!is_null($parentNodeCategory) && $parentNodeCategory->getId()) {
            return $this->getNode($parentNodeCategory, $recursionLevel);
        }
        $root = Mage::registry('category_root');
        if (is_null($root)) {
            $rootId = Mage_Catalog_Model_Category::TREE_ROOT_ID;
            $ids = $this->getSelectedCategotyPathIds($rootId);
            $tree = Mage::getResourceSingleton('catalog/category_tree')
                ->loadByIds($ids, false, false);
            if ($this->getCategory()) {
                $tree->loadEnsuredNodes($this->getCategory(), $tree->getNodeById($rootId));
            }
            $tree->addCollectionData($this->getCategoryCollection());
            $root = $tree->getNodeById($rootId);
            Mage::register('category_root', $root);
        }
        return $root;
    }


    protected function _getNodeJson($node, $level = 1){
        $item = parent::_getNodeJson($node, $level);
        if ($this->_isParentSelectedCategory($node)) {
            $item['expanded'] = true;
        }
        if (in_array($node->getId(), $this->getCategoryIds())) {
            $item['checked'] = true;
        }
        return $item;
    }


    protected function _isParentSelectedCategory($node){
        $result = false;
        // Contains string with all category IDs of children (not exactly direct) of the node
        $allChildren = $node->getAllChildren();
        if ($allChildren) {
            $selectedCategoryIds = $this->getCategoryIds();
            $allChildrenArr = explode(',', $allChildren);
            for ($i = 0, $cnt = count($selectedCategoryIds); $i < $cnt; $i++) {
                $isSelf = $node->getId() == $selectedCategoryIds[$i];
                if (!$isSelf && in_array($selectedCategoryIds[$i], $allChildrenArr)) {
                    $result = true;
                    break;
                }
            }
        }
        return $result;
    }


    protected function _getSelectedNodes(){
        if ($this->_selectedNodes === null) {
            $this->_selectedNodes = array();
            $root = $this->getRoot();
            foreach ($this->getCategoryIds() as $categoryId) {
                if ($root) {
                    $this->_selectedNodes[] = $root->getTree()->getNodeById($categoryId);
                }
            }
        }
        return $this->_selectedNodes;
    }

    public function getCategoryChildrenJson($categoryId){
        $category = Mage::getModel('catalog/category')->load($categoryId);
        $node = $this->getRoot($category, 1)->getTree()->getNodeById($categoryId);
        if (!$node || !$node->hasChildren()) {
            return '[]';
        }
        $children = array();
        foreach ($node->getChildren() as $child) {
            $children[] = $this->_getNodeJson($child);
        }
        return Mage::helper('core')->jsonEncode($children);
    }

    public function getLoadTreeUrl($expanded = null){
        return $this->getUrl('*/*/categoriesJson', array('_current' => true));
    }

    public function getSelectedCategoryPathIds($rootId = false){
        $ids = array();
        $categoryIds = $this->getCategoryIds();
        if (empty($categoryIds)) {
            return array();
        }
        $collection = Mage::getResourceModel('catalog/category_collection');
        if ($rootId) {
            $collection->addFieldToFilter('parent_id', $rootId);
        }
        else {
            $collection->addFieldToFilter('entity_id', array('in'=>$categoryIds));
        }

        foreach ($collection as $item) {
            if ($rootId && !in_array($rootId, $item->getPathIds())) {
                continue;
            }
            foreach ($item->getPathIds() as $id) {
                if (!in_array($id, $ids)) {
                    $ids[] = $id;
                }
            }
        }
        return $ids;
    }
}

here is controller file-

<?php

class Assel_Po_Adminhtml_PoproductController extends Mage_Adminhtml_Controller_Action
{

    protected function _initAction() {
        $this->loadLayout()
            ->_setActiveMenu('Purchase')
            ->_addBreadcrumb(Mage::helper('adminhtml')->__('Purchase Order Product'), Mage::helper('adminhtml')->__('Purchase Order Product'));

        return $this;
    }

    public function indexAction() {
        $this->_initAction()
            ->_addContent($this->getLayout()->createBlock('po/adminhtml_poproduct'))
            ->renderLayout();
    }

    public function newAction() {
        $this->_forward('edit');
    }

    public function editAction() {
        $poid  = $this->getRequest()->getParam('po_product_id');
        $model  = Mage::getModel('po/poproduct')->load($poid);
        if ($model->getPoProductId() || $poid == 0) {
            $this->_initAction();
            $data = Mage::getSingleton('adminhtml/session')->getFormData(true);
            if (!empty($data)) {
                $model->setData($data);
            }

            Mage::register('poproduct_data', $model);
            //$this->getLayout()->getBlock('head')->setCanLoadExtJs(true);
            $this->_addContent($this->getLayout()->createBlock('po/adminhtml_poproduct_edit'));
                //->_addLeft($this->getLayout()->createBlock('sharkslideshow/adminhtml_sharkrevslider_edit_tabs'));

            $this->renderLayout();
        } else {
            Mage::getSingleton('adminhtml/session')->addError(Mage::helper('po')->__('Purchase product does not exist'));
            $this->_redirect('*/*/');
        }
    }


    public function saveAction() 
    {
         if ($data = $this->getRequest()->getPost())
         {
             $model = Mage::getModel('po/poproduct');
             if ($id = $this->getRequest()->getParam('po_product_id')) {
                $model->load($id);
             } 

             $model_poproduct = Mage::getModel('po/poproduct');
             $model_poproduct->setData($data)->setId($this->getRequest()->getParam('po_product_id'));

             /*save existing product with product_id */
             $product_id= $data['product_id'];

             $product_name= $data['product_name'];
             $product_expiry_date=$data['expiry_date'];
             $product_mrp=$data['mrp'];
             $product_rate=$data['rate'];
             $tax_rate=$data['tax'];
             $special_price=$data['special_price'];
             $product_qty=$data['qty'];
             if($product_id)
             {
                  try{ 
                         /* get all attributes of all products */
                         Mage::app()->setCurrentStore(Mage_Core_Model_App::ADMIN_STORE_ID);

                         $product = Mage::getModel("catalog/product")->load($product_id);

                         $product->setName($product_name);
                         $product->setPrice($product_mrp);
                         $product->setExpiryDate($product_expiry_date);
                         $product->setSpecialPrice($special_price);
                         if($tax_rate==0){$product->setTaxClassId(1);}
                         elseif($tax_rate==5){$product->setTaxClassId(5);}
                         else{$product->setTaxClassId(6);}

                         $product_current_qty= (int)Mage::getModel('cataloginventory/stock_item')->loadByProduct($product)->getQty();
                         $product->setStockData(array(
                                                       'use_config_manage_stock' => 0, 
                                                       'manage_stock'=>1, 
                                                       'min_sale_qty'=>1, 
                                                       'is_in_stock' => 1, 
                                                       'qty' => $product_current_qty+$product_qty
                                                  )
                                                );
                        $product->save();
                    }
                     catch(Exception $e){
                        Mage::log($e->getMessage());
                     }
             }
             else
             {
                 Mage::app()->setCurrentStore(Mage_Core_Model_App::ADMIN_STORE_ID);
                 $product = Mage::getModel('catalog/product');
                 try
                 {
                     $product
                        ->setStoreId(1) //you can set data in store scope
                        ->setWebsiteIds(array(1)) //website ID the product is assigned to, as an array
                        ->setAttributeSetId(9) //ID of a attribute set named 'default'
                        ->setTypeId('simple') //product type
                        ->setCreatedAt(strtotime('now')) //product creation time
                    //    ->setUpdatedAt(strtotime('now')) //product update time

                    //  ->setSku('testsku61') //SKU
                        ->setName($product_name) //product name
                    //  ->setWeight(4.0000)
                        ->setStatus(1) //product status (1 - enabled, 2 - disabled)
                    //  ->setTaxClassId(4) //tax class (0 - none, 1 - default, 2 - taxable, 4 - shipping)
                        ->setVisibility(Mage_Catalog_Model_Product_Visibility::VISIBILITY_BOTH) //catalog and search visibility
                    //  ->setManufacturer(28) //manufacturer id
                    //  ->setColor(24)
                    //  ->setNewsFromDate('06/26/2014') //product set as new from
                    //  ->setNewsToDate('06/30/2014') //product set as new to
                    //  ->setCountryOfManufacture('AF') //country of manufacture (2-letter country code)

                        ->setPrice($product_mrp) //price in form 11.22
                    //  ->setCost(22.33) //price in form 11.22
                        ->setSpecialPrice($special_price) //special price in form 11.22
                    //  ->setSpecialFromDate('06/1/2014') //special price from (MM-DD-YYYY)
                    //  ->setSpecialToDate('06/30/2014') //special price to (MM-DD-YYYY)
                    //  ->setMsrpEnabled(1) //enable MAP
                    //  ->setMsrpDisplayActualPriceType(1) //display actual price (1 - on gesture, 2 - in cart, 3 - before order confirmation, 4 - use config)
                    //  ->setMsrp(99.99) //Manufacturer's Suggested Retail Price

                    //  ->setMetaTitle('test meta title 2')
                    //  ->setMetaKeyword('test meta keyword 2')
                    //  ->setMetaDescription('test meta description 2')

                    //  ->setDescription('This is a long description')
                    //  ->setShortDescription('This is a short description')

                    //  ->setMediaGallery (array('images'=>array (), 'values'=>array ())) //media gallery initialization
                    //  ->addImageToMediaGallery('media/catalog/product/1/0/10243-1.png', array('image','thumbnail','small_image'), false, false) //assigning image, thumb and small image to media gallery

                        ->setStockData(array(
                                           'use_config_manage_stock' => 0, //'Use config settings' checkbox
                                           'manage_stock'=>1, //manage stock
                                           'min_sale_qty'=>1, //Minimum Qty Allowed in Shopping Cart
                                           'max_sale_qty'=>2, //Maximum Qty Allowed in Shopping Cart
                                           'is_in_stock' => 1, //Stock Availability
                                           'qty' => $product_qty //qty
                                       )
                        );

                        if($tax_rate==0){$product->setTaxClassId(1);}
                        elseif($tax_rate==5){$product->setTaxClassId(5);}
                        else{$product->setTaxClassId(6);}

                    //  ->setCategoryIds(array(3, 10)); //assign product to categories
                    $product->save();
                 }
                 catch(Exception $e){
                        Mage::log($e->getMessage());
                 }

             }

             try {
                 $model_poproduct->save();

                Mage::getSingleton('core/session')->addSuccess(Mage::helper('po')->__('Product has been saved succesfully'));
                Mage::getSingleton('core/session')->setFormData(false);
                if ($this->getRequest()->getParam('back')) { /* true if save and continue edit button is clicked*/
                    $this->_redirect('*/*/edit', array('po_id' => $this->getRequest()->getParam('po_id'),'po_product_id' => $model_poproduct->getPoProductId()));
                    return;
                }

                $this->_redirect('po/adminhtml_po/edit',array('po_id' => $this->getRequest()->getParam('po_id')));
                return;
             }
             catch (Exception $e) {
                Mage::getSingleton('core/session')->addError($e->getMessage());
                Mage::getSingleton('core/session')->setFormData($data);
                $this->_redirect('po/adminhtml_poproduct/edit',array('po_id' => $this->getRequest()->getParam('po_id')));
                return;
            }
         }
    }


    public function deleteAction() {
        Mage::getSingleton('core/session', array('name'=>'adminhtml'));
        if(  Mage::getSingleton('admin/session')->isLoggedIn() )
        {
            $po_productId=$this->getRequest()->getParam('po_product_id');
            if( $po_productId > 0 ) {
                try {
                    $po_product = Mage::getModel('po/poproduct')->load($po_productId);
                    $po_product->setIsDeleted(1)->setId($po_productId)->save();

                    Mage::getSingleton('adminhtml/session')->addSuccess(Mage::helper('adminhtml')->__('Product  was successfully deleted',$po_productId));
                    $this->_redirect('po/adminhtml_po/edit/po_id/'.$this->getRequest()->getParam('po_id').'/po_product_id/'.$po_productId);
                } catch (Exception $e) {
                    Mage::getSingleton('adminhtml/session')->addError($e->getMessage());
                    $this->_redirect('po/adminhtml_po/edit/po_id/'.$this->getRequest()->getParam('po_id'));
                }
            }
        }
        else
        {
            Mage::getSingleton('adminhtml/session')->addError(Mage::helper('adminhtml')->__('You are not authorized to perform this action'));
        }
        $this->_redirect('*/*/');
    }


    public function massDeleteAction() {
        $poproductsIds = $this->getRequest()->getParam('po_product_id');

        // only superadmin cam perform this action
        Mage::getSingleton('core/session', array('name'=>'adminhtml'));
        if(  Mage::getSingleton('admin/session')->isLoggedIn() )
        {
            if(!is_array($poproductsIds)) {
                Mage::getSingleton('adminhtml/session')->addError(Mage::helper('adminhtml')->__('Please select product(s)'));
            } else {
                try {
                    foreach ($poproductsIds as $poproductsId) {
                        $poProduct = Mage::getModel('po/poproduct')->load($poproductsId);
                        $poProduct->setIsDeleted(1)->setId($poproductsId)->save();
                    }
                    Mage::getSingleton('adminhtml/session')->addSuccess(
                        Mage::helper('adminhtml')->__(
                            'Total of %d Product(s) were successfully deleted', count($poproductsIds)
                        )
                    );
                } catch (Exception $e) {
                    Mage::getSingleton('adminhtml/session')->addError($e->getMessage());
                }
            }
        }
        else
        {       
            Mage::getSingleton('adminhtml/session')->addError(Mage::helper('adminhtml')->__('You are not authorized to perform this action'));
        }
        $this->_redirect('*/*/index');
    }

    public function categoriesJsonAction(){
        $this->_initPoproduct();
        $this->getResponse()->setBody(
            $this->getLayout()->createBlock('po/adminhtml_poproduct_edit_categories')
                ->getCategoryChildrenJson($this->getRequest()->getParam('category'))
        );
    }

    protected function _initPoproduct(){
        $this->loadLayout();
        $this->renderLayout();
        $poproductId  = (int) $this->getRequest()->getParam('po_product_id');
        $poproduct    = Mage::getModel('po/poproduct');

        if ($poproductId) {
            $poproduct->load($poproductId);
        }
        Mage::register('current_poproduct', $poproduct);
        return $poproduct;
     }
}

Please anyone help me to solve this.

hanks in advance.

Best Answer

public function getCategoriesArray() {

    $categoriesArray = Mage::getModel('catalog/category')
            ->getCollection()
            ->addAttributeToSelect('name')
            ->addAttributeToSort('path', 'asc')
            ->load()
            ->toArray();

    $categories = array();
    foreach ($categoriesArray as $categoryId => $category) {
        if (isset($category['name']) && isset($category['level'])) {
            $categories[] = array(
                'label' => $category['name'],
                'level'  =>$category['level'],
                'value' => $categoryId
            );
        }
    }

    return $categories;
}

to add in form

 $fieldset->addField('categories', 'multiselect', array(
            'label' => $this->__('Categories'),
            'name' => 'categories',
            'values' => $this->getCategoriesArray(),
        ));
Related Topic