Welcome Guest, Not a member yet? Register   Sign In
Please help: Questions about: Dynamic Routing, Dynamic Pages, Dynamic Navigation
#1

[eluser]CtheB[/eluser]
Hi i'm new to CI, and while reading the userguide and the forum, i'm trying to understand how CI really works.
Most of the CI Developers aims for a dynamic application, with modules, dynamic menu's and dynamic pagination.
I'm having some questions about:

- How to set up a Dynamic router.
- How to set up Dynamic pages with a Dynamic navigation structure:

/home (loads the pages module)
/about (loads the pages module)
/news (loads the news module)
/about/what-about/our-company (loads the pages module)
/about/news (loads the news module)
/news/about (loads the pages module)
/about/what-about/latest-news (loads the news module)

So it must be possible to load a module EVERYWHERE in the navigation.
I have a working example below to making things clear to everybody:

To keep things as simple as possible for this topic: i'm having a clean CI installation running with only Modular Extensions 5.1 installed.

The database design
To start of with this dynamic application, we have to design the database.
In the database, I have 2 tables: 1 for the Navigation and 1 for the Pages.
Code:
#
# Table structure for table 'navigations'
#

CREATE TABLE /*!32312 IF NOT EXISTS*/ `navigations` (
  `id` int(11) NOT NULL auto_increment,
  `parent_id` int(11) NOT NULL,
  `active` tinyint(1) NOT NULL,
  `weight` int(11) NOT NULL,
  `title` varchar(100) NOT NULL,
  `link` varchar(100) NOT NULL,
  `loc_id` int(11) NOT NULL default '0',
  `module` varchar(100) default NULL,
  `pages_id` int(11) default NULL,
  PRIMARY KEY  (`id`),
  KEY `active` (`active`),
  KEY `weight` (`weight`),
  KEY `parent_id` (`parent_id`),
  KEY `loc_id` (`loc_id`),
  KEY `pages_id` (`pages_id`)
) ENGINE=MyISAM AUTO_INCREMENT=12 DEFAULT CHARSET=utf8;

#
# Table structure for table 'pages'
#

CREATE TABLE /*!32312 IF NOT EXISTS*/ `pages` (
  `id` int(11) NOT NULL auto_increment,
  `active` tinyint(1) NOT NULL,
  `uri` varchar(40) NOT NULL,
  `menu_title` varchar(100) NOT NULL,
  `title` varchar(255) NOT NULL,
  `meta_keywords` varchar(255) default NULL,
  `meta_description` varchar(255) default NULL,
  `body` text NOT NULL,
  PRIMARY KEY  (`id`),
  KEY `uri` (`uri`),
  KEY `active` (`active`)
) ENGINE=MyISAM AUTO_INCREMENT=9 DEFAULT CHARSET=utf8;

config/routes.php
Here i need some real help. I want to route the 'module' in the pages table, to the correct module in the application:
Code:
require(APPPATH.'config/database.php');

mysql_connect($db[$active_group]['hostname'], $db[$active_group]['username'], $db[$active_group]['password']);
mysql_select_db($db[$active_group]['database']);

$result = mysql_query("SELECT        A.id,
                                    IF(D.link <> '', CONCAT(D.link,'/',C.link,'/',B.link,'/',A.link), IF(C.link <> '', CONCAT(C.link,'/',B.link,'/',A.link), IF(B.link <> '', CONCAT(B.link,'/',A.link), A.link))),
                                    A.module
                        FROM        navigations A
                        LEFT JOIN    navigations B ON A.parent_id = B.id
                        LEFT JOIN    navigations C ON B.parent_id = C.id
                        LEFT JOIN    navigations D ON C.parent_id = D.id
                        ORDER BY    A.id DESC
                        ");
while($regel = mysql_fetch_array($result)) {
    list($menuId, $menuUrl, $module) = $regel;
    if(file_exists(APPPATH . 'modules/' . $module . '/controllers/' . $module . '.php'))
    {
        $route[$menuUrl] = $module .'/index';
        $route[$menuUrl.'/(.*)'] = $module .'/index/$1';
    }
}
mysql_close();
$route['default_controller'] = "pages";
$route['scaffolding_trigger'] = "";


/* End of file routes.php */
/* Location: ./system/application/config/routes.php */

Getting the correct page
Oke, we've routed the page to the correct module, now we have to "pass" the $menuId to this module. Since we can't pass the id from the navigations table directly from the router to the controller, i made a library wich does:

Code:
&lt;?php
class MY_Pagination extends Controller {

    public $url = '';
    private $num = 1;
    private $new_length;
    public $menuId = 0;
    
    public function __construct()
    {
        parent::Controller();
    
        if ( $this->uri->segment(1) )
        {
            while ( $segment = $this->uri->segment($this->num))
            {
                $this->url .= $segment.'/';
                $this->num++;
            }
            $this->new_length = strlen($this->url) - 1;
            $this->url = substr($this->url, 0, $this->new_length);
        }
        else
        {
            $this->url = 'home';
        }
        
        $query = $this->db->query("SELECT        A.id
                            FROM        navigations A
                            LEFT JOIN    navigations B ON A.parent_id = B.id
                            LEFT JOIN    navigations C ON B.parent_id = C.id
                            LEFT JOIN    navigations D ON C.parent_id = D.id
                            WHERE        IF(D.link <> '', CONCAT(D.link,'/',C.link,'/',B.link,'/',A.link), IF(C.link <> '', CONCAT(C.link,'/',B.link,'/',A.link), IF(B.link <> '', CONCAT(B.link,'/',A.link), A.link))) = '$this->url'
                            ORDER BY    A.id DESC
                            ");
        if($row = $query->row())
        {
            $this->menuId = $row->id;
        }
    }
}
/* End of file MY_Pagination.php */
/* Location: ./application/libraries/MY_Pagination.php */
#2

[eluser]CtheB[/eluser]
Now we can make a module called pages, here is the controller:
Code:
&lt;?php

class Pages extends Controller {
    
    public function __construct()
    {
        parent::Controller();
        $this->load->model('pages_model');
        $this->load->library('pagination');
    }

    public function index()
    {
            if ( $page = $this->pages_model->get_page($this->pagination->menuId) )
            {
                $view['pages'] = $page;
                $this->load->view('index', $view);
            }
            else
            {
                $this->output->set_header("HTTP/1.0 404 Not Found");
                $this->load->view('404');

            }
        }

}
/* End of file pages.php */
/* Location: ./application/modules/pages/controllers/pages.php */

And here is the model:
Code:
&lt;?php

    class Pages_Model extends Model {
        
        protected $table;
        protected $menu;
        
        public function __construct()
        {
            parent::Model();
            $this->table = 'pages';
            $this->menu = 'navigations';
        }

        public function get_page($id)
        {
            $this->db->join($this->menu, $this->table . '.id =' . $this->menu . '.pages_id ', 'left')->where($this->menu . '.id', $id);
            $query = $this->db->get($this->table, 1);

            if ( $query->num_rows() == 1 )
            {
                return $query->row_array();
            }
            else
            {
                return false;
            }
        }
    }
/* End of file pages_model.php */
/* Location: ./application/modules/pages/models/pages_model.php */

In the view now, i can echo the title of the current page: $pages['title'];
etc etc.

The Help I need
Is this the correct way for doing this? I think things can be smarter, better..
What about the routing? Is there a way arround my current methode?
What about the library? Is there another way getting the id of the current page?

Please help me!
My thanks will be great!


Carlos
#3

[eluser]CtheB[/eluser]
Hi,

Is there anyone on this forum who could help me on this?

Thanks in advanced,

Carlos
#4

[eluser]TheFuzzy0ne[/eluser]
I think I would have extended and overridden the Router class. If you can do that right, there's no reason to change the routes.php file.




Theme © iAndrew 2016 - Forum software by © MyBB