⚠ In case you've missed it, we have migrated to our new website, with a brand new forum. For more details about the migration you can read our blog post for website migration. This is an archived forum. ⚠

  •     

profile picture

Categories and subcategories with Grocery Croud



vnt
  • profile picture
  • Member

Posted 12 February 2012 - 21:57 PM

Hi,
how can I do to manage and displaying categories and unlimited subcategories?

Examples:
Main Category
Main Category->Subcategory->
Main Category->Subcategory->Child category
Main Category->Subcategory->Child category->Child Subcategory
Main Category->Subcategory->Child category->Child Subcategory-> upto any level

CREATE TABLE `categories` (
`id` int(11) NOT NULL auto_increment,
`sortorder` int(11) NOT NULL,
`status` enum('1','0') NOT NULL,
`type` int(11) NOT NULL,
`parent` int(11) NOT NULL default '0',
`name` varchar(150) NOT NULL,
`description` text NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM AUTO_INCREMENT=106 DEFAULT CHARSET=latin1 AUTO_INCREMENT=1 ;

Thanks

web-johnny
  • profile picture
  • Administrator
  • 1,166 posts

Posted 16 February 2012 - 19:20 PM

Hello @vnt and sorry for the delayed answer. I have a working example below that I hope that can help you:


public function webpages($parent_id = null)
{
$c = new grocery_CRUD();

$c->where( empty($parent_id) ? 'parent IS NULL' : array('parent' => $parent_id) );
$c->set_table('webpages');
$c->order_by('priority');
$c->set_subject('Webpage');
$c->columns('menu_title','url','status','priority');

$c->change_field_type('parent', 'hidden',$parent_id);

$c->callback_column('menu_title',array($this,'_callback_webpage_url'));

$output = $c->render();
$this->_view_output($output);
}

public function _callback_webpage_url($value, $row)
{
return "<a href='".site_url('admin/webpages/'.$row->id)."'>$value</a>";
}


A similar thing you can do at your categories thing. And it is unlimited subcategories ;-) . The only thing that you have to do is the breadcrumb with the parent_id .

For now this is the only way as there is not yet included to grocery CRUD a tree-relation field.

vnt
  • profile picture
  • Member

Posted 18 February 2012 - 15:27 PM

Hello web-Johnny

You can post the table that you used for this example?


public function webpages($parent_id = null)
{
$c = new grocery_CRUD();

$c->where( empty($parent_id) ? 'parent IS NULL' : array('parent' => $parent_id) );
$c->set_table('webpages');
$c->order_by('priority');
$c->set_subject('Webpage');
$c->columns('menu_title','url','status','priority');
$c->change_field_type('parent', 'hidden',$parent_id);
$c->callback_column('menu_title',array($this,'_callback_webpage_url'));
$output = $c->render();
$this->_view_output($output);
}
public function _callback_webpage_url($value, $row)
{
return "<a href='".site_url('admin/webpages/'.$row->id)."'>$value</a>";
}



Thank you,
D.

web-johnny
  • profile picture
  • Administrator
  • 1,166 posts

Posted 18 February 2012 - 18:22 PM


CREATE TABLE IF NOT EXISTS `webpages` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`menu_title` varchar(250) NOT NULL,
`content` text,
`status` enum('public','hidden','private') NOT NULL DEFAULT 'public',
`url` varchar(250) NOT NULL,
`parent` int(11) DEFAULT NULL,
`priority` int(3) NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `url` (`url`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;


vnt
  • profile picture
  • Member

Posted 18 February 2012 - 23:36 PM

[b]Fatal error[/b]: Call to undefined function admin_url() in [b]/Users/vnt/Sites/vdlabs/vnt/application/controllers/admin.php[/b] on line [b]150[/b]

web-johnny
  • profile picture
  • Administrator
  • 1,166 posts

Posted 19 February 2012 - 10:44 AM

Replace that with:

public function _callback_webpage_url($value, $row)
{
return "<a href='".site_url('admin/webpages/'.$row->id)."'>$value</a>";
}


the 'admin' is the name of your controller. Sorry I just copy-paste my code. I have a general helper that do just this:

function admin_url($url = '')
{
return site_url('admin/'.$url);
}


I edited my post so other users can use this.

vnt
  • profile picture
  • Member

Posted 19 February 2012 - 13:02 PM

1) There is a bug when you insert a first level, the value of field "parent" is 0 instead of null!
2) How make for see field parent into the list?
3) In table contents I have field idCategories, how can I do to display the categories in a select how tree-relation field?

Magento Commerce has an excellent system of management categories!
I hope you can insert a feature for tree-relation field in the next version of Grocery Croud!

web-johnny
  • profile picture
  • Administrator
  • 1,166 posts

Posted 19 February 2012 - 18:45 PM

Hello @vnt .
I have the answers to your questions:

The below code shows your answers to the questions in comments.


<?php
public function webpages($parent_id = null)
{
if(!is_numeric($parent_id) || empty($parent_id) ) // This is for Question 1
$parent_id = null; // This is for Question 1

$this->load->view('echo',array('data' => $this->getWebpageBreadcrumb($parent_id))); // This is for Question 2

$c = new grocery_CRUD();

$c->where( $parent_id === null ? 'parent IS NULL' : array('parent' => $parent_id) ); // This is for Question 1
$c->set_table('webpages');
$c->order_by('priority');
$c->set_subject('Webpage');
$c->columns('menu_title','url','status','priority');

$c->change_field_type('parent', 'hidden', $parent_id === null ? '' : $parent_id ); // This is for Question 1

$c->callback_column('menu_title',array($this,'_callback_webpage_url'));

$output = $c->render();
$this->_view_output($output);
}
public function _callback_webpage_url($value, $row)
{
return "<a href='".admin_url('webpages/'.$row->id)."'>$value</a>";
}

public function getWebpageBreadcrumb($id = null, $breadcrumb_string = '')
{
if(empty($id) && empty($breadcrumb_string))
return "/";
if(empty($id))
return $breadcrumb_string;

$this->db->where('id',$id);
$result = $this->db->get('webpages')->row();

$breadcrumb_string = " / <a href='".site_url('admin/webpages/'.$result->id)."'>".$result->menu_title."</a>" . $breadcrumb_string;

return $this->getWebpageBreadcrumb($result->parent, $breadcrumb_string);
}


You just need a breadcrumb to show in which category you are.

The "echo" view is just a view at application/views/echo.php that has only this code:

<?php
echo $data;


3) For now you are not able to do with an easy way a tree relation select input . The only way is to try it by yourself with the callback_add_field and callback_edit_field

[left]The tree relation is not so easy to included it at grocery CRUD and it will not be at the next version and I am sorry. I try hard to add as many new features in the new version of grocery CRUD. Of course if I had 375+ employees (as Magento have) to do grocery CRUD it will be more easy for me to promise you this feature at the next version ;) . But... I am only one person and I do my best to each new release to be stable, with great interface and easy to use new features.[/left]

vnt
  • profile picture
  • Member

Posted 20 February 2012 - 08:33 AM

There is a small bug in the input fields of the form! Typed characters are not seen!
Your GroceryCroud is fantastic! Is young and has a great future!

web-johnny
  • profile picture
  • Administrator
  • 1,166 posts

Posted 20 February 2012 - 18:51 PM

It is probably just a CSS issue. Add to your template CSS a different height and you will not have any problem with this. For example: height: 30px; and see how it will go.

vnt
  • profile picture
  • Member

Posted 07 March 2012 - 20:47 PM

Hi Johnny,
I need your help!
In the module for insert and edit the record, I need to insert a selct menu where you show this structure:

Examples:
Category A
Category A ->Subcategory->
Category A ->Subcategory->Child category
Category A ->Subcategory->Child category->Child Subcategory

Category B
Category B ->Subcategory->
Category B ->Subcategory->Child category
Category B ->Subcategory->Child category->Child Subcategory
Category B ->Subcategory->Child category->Child Subcategory-> upto any level

Category C
Category C ->Subcategory->
Category C ->Subcategory->Child category

Category D

Thanks so much for your help!

web-johnny
  • profile picture
  • Administrator
  • 1,166 posts

Posted 07 March 2012 - 22:24 PM

Hello @vnt,

I am sorry but I don't have any example or anyone that has a post about a similar situation. You can try by yourself and if you need any help just post it here.

Kindest Regards
Johnny

vnt
  • profile picture
  • Member

Posted 11 April 2012 - 20:09 PM

On the web I found this code that creates a list of categories and unlimited subcategories. Must be customized for <select> and Grocercy croud.


View 1;

Capitali
-- Capitali Americane
---- Canada
------ Ottawa
-- Capitali Asiatiche
-- Capitali europee
---- Italia
-- Capitali Oceaniche
Dove siamo

or view 2;

Capitali
Capitali -> Capitali Americane
Capitali -> Capitali Americane -> Canada
Capitali -> Capitali Americane -> Canada -> Ottawa
Capitali -> Capitali Asiatiche
Capitali -> Capitali europee
Capitali -> Capitali europee -> Italia
Capitali -> Capitali Oceaniche

<?php
/*DATABASE:
CREATE TABLE `vnt_categorie` (
`categoria_id` int(11) NOT NULL AUTO_INCREMENT,
`parent_id` int(11) DEFAULT '0',
`sito_id` int(11) NOT NULL,
`lingua_id` int(11) DEFAULT NULL,
`gruppo_id` tinyint(4) DEFAULT NULL,
`stato` tinyint(1) DEFAULT NULL,
`posizione` int(3) DEFAULT NULL,
`menu` tinyint(1) DEFAULT '1',
`categoria` varchar(255) DEFAULT NULL,
`display_mode` varchar(50) DEFAULT NULL,
`display_qta` tinyint(4) NOT NULL DEFAULT '0',
`url_rewrite` varchar(255) DEFAULT NULL,
`redirect_link` varchar(255) DEFAULT NULL,
`descrizione` text,
`immagine` varchar(255) DEFAULT NULL,
`tag_title` varchar(255) DEFAULT NULL,
`tag_description` varchar(255) DEFAULT NULL,
`tag_keyword` varchar(255) DEFAULT NULL,
`note` varchar(255) DEFAULT NULL,
PRIMARY KEY (`categoria_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=12 ;

--
-- Dump dei dati per la tabella `vnt_categorie`
--

INSERT INTO `vnt_categorie` VALUES(1, NULL, 10, NULL, NULL, 1, 1, 1, 'Capitali', NULL, 0, 'capitali', NULL, NULL, NULL, 'Capitali', 'Capitali', 'capitali', NULL);
INSERT INTO `vnt_categorie` VALUES(2, 1, 8, NULL, NULL, 1, 1, 1, 'Capitali europee', NULL, 0, 'europee', NULL, NULL, NULL, 'Capitali europee', 'Capitali europee', 'Capitali europee', NULL);
INSERT INTO `vnt_categorie` VALUES(3, 1, 10, NULL, NULL, 1, 2, 1, 'Capitali Americane', NULL, 0, 'americane', NULL, NULL, NULL, 'Capitali Americane', 'Capitali Americane', 'Capitali Americane', NULL);
INSERT INTO `vnt_categorie` VALUES(4, 1, 10, NULL, NULL, 1, 1, 1, 'Capitali Asiatiche', NULL, 0, 'asiatiche', NULL, NULL, NULL, 'Capitali asiatiche', 'Capitali asiatiche', 'Capitali asiatiche', NULL);
INSERT INTO `vnt_categorie` VALUES(5, 1, 0, NULL, NULL, 1, 4, 1, 'Capitali Oceaniche', NULL, 0, 'capitali-oceaniche', NULL, NULL, NULL, 'Capitali Oceaniche', 'Capitali Oceaniche', 'Capitali Oceaniche', NULL);
INSERT INTO `vnt_categorie` VALUES(6, NULL, 10, NULL, NULL, 1, NULL, 1, 'Home', '9', 11, 'home', NULL, NULL, '89e1c-Mappa-sito-mt.jpg', 'Home page', 'Home page', 'Home page', NULL);
INSERT INTO `vnt_categorie` VALUES(7, NULL, 10, 3, NULL, 1, NULL, 1, 'Dove siamo', NULL, 0, 'dove-siamo', NULL, NULL, NULL, 'Dove siamo', 'Dove siamo', 'Dove siamo', NULL);
INSERT INTO `vnt_categorie` VALUES(9, 2, 0, NULL, NULL, 1, NULL, 1, 'Italia', '9', 0, 'italia', NULL, NULL, NULL, NULL, NULL, NULL, NULL);
INSERT INTO `vnt_categorie` VALUES(10, 3, 0, NULL, NULL, 1, NULL, 1, 'Canada', NULL, 0, 'canada', NULL, NULL, NULL, NULL, NULL, NULL, NULL);
INSERT INTO `vnt_categorie` VALUES(11, 10, 0, NULL, NULL, 1, NULL, 1, 'Ottawa', NULL, 0, 'ottawa', NULL, NULL, NULL, NULL, NULL, NULL, NULL);
//Connection to database

$link = mysql_connect('localhost', 'root', '');
if (!$link) {
die('Not connected : ' . mysql_error());
}

if (! mysql_select_db('vnt_cms') ) {
die ('Can\'t use foo : ' . mysql_error());
}

$refs = array();
$list = array();

$sql = "SELECT categoria_id, parent_id, categoria FROM vnt_categorie ORDER BY categoria";
$result = mysql_query($sql);
while($data = @mysql_fetch_assoc($result)) {
$thisref = &$refs[ $data['categoria_id'] ];

$thisref['parent_id'] = $data['parent_id'];
$thisref['categoria'] = $data['categoria'];
$thisref['categoria_id'] = $data['categoria_id'];

if ($data['parent_id'] == 0) {
$list[ $data['categoria_id'] ] = &$thisref;
} else {
$refs[ $data['parent_id'] ]['children'][ $data['categoria_id'] ] = &$thisref;
}
}

function toUL($arr){
$html = '<ul>'.PHP_EOL;
foreach ($arr as $v){
$html .= '<li>' . $v['categoria'];
if (array_key_exists('children', $v)){
$html .= toUL($v['children']);
}
$html .= '</li>'.PHP_EOL;
}
$html .= '</ul>'.PHP_EOL;
return $html;
}

// Inizio funzione per creare e riempire la select
function creaSelect($arr){
foreach ($arr as $v){
$html .= '<option value="'.$v['categoria_id'].'">' . $v['categoria'].'</option>';
if (array_key_exists('children', $v)){
// $html .= '<option value="';
// $html .=toSelect($v['children']);
// $html .= '">-';
$html .=creaSelect($v['children']);
// $html .=toSelect($v['children']);
// $html .=toSelect('<option value="'.$v['categoria_id'].'">' . $v['categoria'].'</option>');
$html .= '</option>';

}
$html .= ''.PHP_EOL;
}
return $html;
}

echo '<select name="categoria">';
echo toSelect($list);
echo '</select>';
// build the list and output it

echo toUL($list);







function struttura($parent_id = null)
{
if(!is_numeric($parent_id) || empty($parent_id) ) // This is for Question 1
$parent_id = null; // This is for Question 1

$this->load->view('admin/include/echo',array('data' => $this->getStrutturaBreadcrumb($parent_id))); // This is for Question 2

$crud = new grocery_CRUD();

$crud->where( $parent_id === null ? 'parent_id IS NULL' : array('parent_id' => $parent_id) ); // This is for Question 1
$crud->set_theme('datatables');
$crud->set_table('vnt_categorie');
$crud->order_by('posizione');
$crud->set_subject('categoria');

$parent_id === null ? $crud->columns('stato','categoria','lingua_id','gruppo_id','menu') : $crud->columns('stato','categoria','riservato','menu');
$parent_id === null ? $crud->fields('stato','menu','gruppo_id','lingua_id','categoria','url_rewrite','redirect_link','parent_id','display_mode','display_qta','posizione','descrizione','immagine','tag_title','tag_description','tag_keyword','note') : $crud->fields('stato','menu','gruppo_id','categoria','url_rewrite','parent_id','display_mode','display_qta','posizione','descrizione','immagine','tag_title','tag_description','tag_keyword','note');
$crud->set_field_upload('immagine','uploads/images');
$crud->add_action('Contenuti', '', 'admin/contenuti','ui-icon-plus');

$crud->change_field_type('parent_id', 'hidden', $parent_id === null ? '' : $parent_id ); // This is for Question 1
//$crud->set_relation('parent_id','vnt_categorie','categoria');

$crud->callback_column('categoria',array($this,'_callback_struttura_url'));

$crud->set_relation('stato','vnt_opzioni','opzione_nome' ,array('gruppo' => 'stato'),'posizione ASC');
$crud->set_relation('gruppo_id','vnt_gruppi','gruppo');

$crud->set_relation('lingua_id','vnt_lingue','titolo');

$crud->set_relation('display_mode','vnt_opzioni','opzione_nome' ,array('gruppo' => 'display_mode'),'posizione ASC');
$crud->set_relation('display_qta','vnt_opzioni','opzione_nome' ,array('gruppo' => 'display_qta'),'posizione ASC');

$crud->set_relation('lingua_id','vnt_lingue','titolo');
$crud->display_as('lingua_idmenu_id','Lingua');
$crud->display_as('gruppo_id','Riservata');

$this->grocery_crud->callback_edit_field('parent_id',array($this,'edit_field_callback_1'));

$output = $crud->render();
$this->_view_output($output);
}
public function _callback_struttura_url($value, $row)
{
return "<a href='".site_url('admin/struttura/'.$row->categoria_id)."'>$value</a>";
}
public function getStrutturaBreadcrumb($categoria_id = null, $breadcrumb_string = '')
{
if(empty($categoria_id) && empty($breadcrumb_string))
return " / ";
if(empty($categoria_id))
return $breadcrumb_string;

$this->db->where('categoria_id',$categoria_id);
$result = $this->db->get('vnt_categorie')->row();
$breadcrumb_string = " / <a href='".site_url('admin/struttura/'.$result->categoria_id)."'>".$result->categoria."</a>" . $breadcrumb_string;
return $this->getStrutturaBreadcrumb($result->parent_id, $breadcrumb_string);
}
function contenuti()
{
$crud = new grocery_CRUD();
$crud->set_theme('datatables');
$crud->set_subject('contenuto');
$crud->set_table('vnt_contenuti');
$crud->set_relation('categoria_id','vnt_categorie','categoria');
$crud->columns('stato', 'titolo', 'categoria_id', 'utente_id', 'data_inizio', 'gruppo_id');
$crud->fields('stato', 'categoria_id', 'gruppo_id', 'utente_id', 'titolo', 'url_rewrite','redirect_link', 'pagina', 'immagine', 'tag_title', 'tag_description', 'tag_keyword', 'data_inizio', 'data_fine', 'note');
$crud->set_field_upload('immagine','uploads/images');

$crud->display_as('categoria_id','Categoria');
$crud->display_as('utente_id','Utente');
$crud->display_as('gruppo_id','Riservato');
$crud->set_relation('gruppo_id','vnt_gruppi','gruppo');