How to call a controller from a view in opencart? - php

I'm new to opencart. I want to create a custom theme and some custom controllers and models. I can't find any tutorials relative to this, but I tried to create a view along a controller. When I call that view from home or header view page, like $header (in home file) and $search (in header file), then it shows undefined variable.
My code looks like this. It's in controller (path is catalog\controller\common\test.php).
<?php
class ControllerCommonTest extends Controller{
public function index() {
if(file_exists(DIR_TEMPLATE.this->config->get('config_template').'/template/test/test.tpl')) {
$this->response->setOutput($this->render());
} else {
return $this->load->view('default/template/common/header.tpl');
}
}
}
?>
And my view is in \view\theme\MyTheme\template\common\test.tpl
<?php
echo "Test file";
?>
And in my home file, I call my controller like below...
<?php
echo $header;
echo $test;
echo $footer;
?>
When I run this it shows the below error:
Notice: Undefined variable: test in C:\xampp\htdocs\opencart\catalog\view\theme\MyCustome\template\common\home.tpl on line 4
So, please provide any tutorial links and any examples for developing a custom module in opencart.
Thanks in advance.

To display test module tpl i.e. test.tpl on home page, You have load test controller on home controller. Please add following code in catalog/controller/common/home.php
add this code
$data['test'] = $this->load->controller('common/test');
After
$data['header'] = $this->load->controller('common/header');

Related

Problem load view from controller in Codeigniter 3

I want to load a main view from my controller in CodeIgniter 3.0, but instead of showing the view, the page shows the "Object of class CI_Loader could not be converted to string", and the view I want to show is on the top of my page not in the center of my page.
Here is the error screenshot :
This is my controller:
if($this->session->userdata('logged_in')){
$data['utama'] = $this->load->view('spvcoll/v_list');
$data['judul'] = 'List Assign';
$this->load->view('v_index',$data);
}else{
redirect('c_index');
}
Here I want to call the variable:
<?php echo $utama;?>
TRY This
$data['utama'] = $this->load->view('spvcoll/v_list', TRUE);
Instead of
$data['utama'] = $this->load->view('spvcoll/v_list');

CI routing issue

i am currently learning CI and i have come to an issue that i cant seem to solve.
i set up my wamp server in a drive and inside the www(root) folder i have extracted the codeigniter files.
![example][1][1]: http://i.stack.imgur.com/7RKqG.png
then I created my php files for view/model and controller and set the default route in the config/routes.php
so now when I go to my browser and type localhost I get the post.php displayed without anyissue.
but I am unable to access any of the views from here. for example i have a new_post.php view and when i type in the address bar localhost/new_post.php i get a "Not Found
The requested URL /new_post.php was not found on this server." error.
what am i doing wrong? below i have posted the code which i have written in the post.php controller along with a image of the file structure/names i have.
posts.php - controller
<?php
class Posts extends CI_Controller
{
function __construct()
{
parent::__construct();
$this->load->model('post'); //loads the post model u created in the models folder
}
function index() //goes to this function 1st when u access the controller
{
$data['posts']=$this->post->get_posts(); // load all the data from the get_posts function in post model to the data array posts
$this->load->view('post_index', $data); //loads the view
}
function post($postID)
{
$data['post']=$this->post->get_post($postID);
$this->load->view('post', $data);
}
function new_post()
{
if($_POST)
{
$data=array(
'title'=> $_POST['title'],
'post'=> $_POST['post'],
'active' =>1
);
$this->post->insert_post($data);
redirect(base_url(). 'posts/');
}
else
{
$this->load->view('new_post');
}
}
function editpost($postID)
{
$data['success']=0;
if($_POST)
{
$data_post=array(
'title'=> $_POST['title'],
'post'=> $_POST['post'],
'active' => 1
);
$this->post->update_post($postID,$data);
$data['success'] =1;
}
$data['post']=$this->post->get_post($postID);
$this->load->view('edit_post',$data);
}
function deletepost($postID)
{
$this->post->delete_post($postID);
redirect(base_url(). 'posts/');
}
}
![structure][1] [1]: http://i.stack.imgur.com/SnsbW.png
In CodeIgniter you have to use controller to get access to his function
you are saying "when i type in the address bar localhost/new_post.php i get a Not Found" because you try to direct access its function name you have to use example.com/controllername/functionname like this
http://localhost/posts/new_post
for more information check codeignier url
https://ellislab.com/codeigniter/user-guide/general/urls.html
if you not removed index.php using .htaccess then you have to use your url like this
http://localhost/index.php/posts/new_post
In CodeIgniter, everything runs through the main "index.php" file, in your root directory.
So, you would access your new post page, like this;
http://localhost/index.php/posts/new_post
Have a read through the CodeIgniter user guide, it will answer any problem you have.
https://ellislab.com/codeigniter/user-guide/

How to structure a dynamic website with Codeigniter

I have some experience with php, but I just recently started learning Codeigniter. I used to have a website with a fixed navigation pane and sidebar, but the main section of the site loaded dynamically based on a Get variable. It was basically
include head.php
include navbar.php
include sidebar.php
include the page requested from the get variable (home, about, contact, etc.)
include footer.php
I liked this because the entire site did not have to reload when the user navigated from page to page.
I can't figure out how do this with Codeiginiter. Should I be using a controller for each page or one controller with a function for each page? Do anyone know of a good tutorial that does something similar? All the tutorials I've seen reload the entire site for every page.
Edit: Essentially I want to do this but with Codeigniter
Since it looks like you want relatively static content, but loaded dynamically you can do with one controller and (maybe) one method in the controller.
To do it with one method, do this in the welcome controller:
public page( $page_id ){
// views/header.php
$this->load->view( "header" );
if( $page_id = "about" ){
$this->load->view("about"); // views/about.php
}
else if( $page_id = "contact" ){
$this->load->view("contact"); // views/contact.php
}
// views/footer.php
$this->load->view("footer");
}
This takes a single get variable and figures out what page to load in between the header and footer.
This way www.yoursite.com/page/about will load the about page, www.yoursite.com/page/contact will load the contact page
Now, if you want to get rid of the /page part, you need to do some URL rerouting in application/config/routes.php
Alternatively you could use several methods in one controller:
public about( ){
// views/header.php
$this->load->view( "header" );
$this->load->view( "about" );
// views/footer.php
$this->load->view("footer");
}
public contact( ){
// views/header.php
$this->load->view( "header" );
$this->load->view( "contact" );
// views/footer.php
$this->load->view("footer");
}
Now your URLs look nicer without routing, but you have to load the header/footer for every page.
do you really like to copy/paste many $this->load->view() to any controller function?
It's a spaghetti code. You can try next: for example we have main.php controller as default controller. This main controller contain main function:
public function index()
{
ob_start();
$this->load->model('mainmodel');
$data = $this->mainmodel->_build_blocks(); //return array with needed blocks (header, menu, content, footer) in correct order
foreach ($data->result_array() as $row) {
$this->load->module($row['block_name']);
$this->name = new $row['block_name'];
$this->name->index();
}
ob_end_flush();
}
So, each other controller also have index() function which can dispatch actions depends on url segments, prepare params etc.
Footer controller as example (I use Smarty as template engine):
public function index()
{
$this->mysmarty->assign('year', date("Y"));
$this->mysmarty->view('footer');
return true;
}
Content controller will have:
public function index()
{
$name = $this->uri->segment(1, 'index');
$act = $this->uri->segment(2, 'index');
$this->load->module($name);
$this->name = new $name;
$pageData = $this->name->_show($act);
if ($pageData)
{
$this->mysmarty->assign($name, $pageData);
}
$this->mysmarty->view($name);
}
Thats mean what if you want to show http://site.name/page/contactus , we do next:
1) main.php start cycle by needed blocks
2) firstly we show header.tpl by header controller
3) then we show menu
4) then we call content controller which parse url, found what he should call _show() function in Page controller and pass action='contactus' to it. _show() function can contain some switch/case construction which show templates depends of action name (contactus.tpl in this case)
5) in the end we show footer template
In such case we have flexible structure. All controllers should have index() functions and all controllers who can be called in content should have _show($act) function. Thats all.
In codeIgniter you can do that like this, you can load different views at the same time from your controller. for example:
for example in your navbar view you have a Contacts button in your menu that would look like this:
<a href='contacts'>Contacts</a>
In your controller:
public function contacts()
{
$this->load->view('header');
$this->load->view('navbar');
$this->load->view('sidebar');
$this->load->view('contacts_view');
$this->load->view('footer');
}
So we're assuming here that you have the following views already that is ready to be loaded (header.php, navbar.php, sidebar.php, contacts_view.php, footer.php).
UPDATE:
you don't need to have $_GET[] request, just provide the method name from your controller in the <a> anchor tag
in codeigniter i using template
first make template file in one folder with header.php, navbar.php, etc.
example : template.php
<?php
echo $this->load->view('header'); //load header
echo $this->load->view('navbar');//load navbar
echo $this->load->view('sidebar');//load sidebar
echo $this->load->view($body); //load dynamic content
echo $this->load->view('footer');//load footer
?>
second in controller
function index( ){
$data['body'] = 'home'; // cal your content
$this->load->view('template', $data);
}

Custom error pages with templates in CodeIgniter

I'm using the template library for CodeIgniter, http://williamsconcepts.com/ci/codeigniter/libraries/template/reference.html, and now I want to implement custom error pages too. I found one method involving a MY_Router extending the default router: http://maestric.com/doc/php/codeigniter_404 but that only treats 404 errors. I want all errors to show a simple user-friendly page, including database errors etc, and I want it to go through a controller, partly so I can use the template library, and partly so I can also implement an email function to send myself information about the error that occurred.
Someone asked about extending the functionality of the above MY_Router method for other errors, like error_db, but got no answer from the author, so I'm turning here to see if anyone knows how to do this, along the lines of the above method or any other simple way of achieving it. Please note that I'm a newbie, so do not assume too much about my knowledge of basic CodeIgniter functionality :-)
I've created an extension for the Exceptions class.
In this extension I've replaced the $this->Exceptions->show_error(); method, witch is used by the show_error() function of CI.
when I call show_error('User is not logged in', 401); this custom method is looking for an error_$status_code file first. In the case of the example above, it will look for an error_401.php file.
When this file does not exists, it wil just load the error_general.php file, like the default $this->Exceptions->show_error(); does.
In your case, you can use the following code to use in your library, controller or whatever should throw an error.
<?php
if(!(isset($UserIsLoggedin))){
$this->load->view('template/header');
show_error('User is not logged in', 401);
$this->load->view('template/footer');
}
?>
Your error_401.php file should than look like this:
<div id="container">
<h1><?php echo 'This is an 401 error'; ?></h1>
<?php echo $message; ?>
</div>
/application/core/MY_Exceptions.php:
<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
class MY_Exceptions extends CI_Exceptions
{
function show_error($heading, $message, $template = 'error_general', $status_code = 500)
{
if((!isset($template)) || ($template == 'error_general')){
if(file_exists(APPPATH.'errors/error_'.$status_code.'.php')) {
$template = 'error_'.$status_code;
}
}
if (!isset($status_code)) $status_code = 500;
set_status_header($status_code);
$message = '<p>'.implode('</p><p>', ( ! is_array($message)) ? array($message) : $message).'</p>';
if (ob_get_level() > $this->ob_level + 1)
{
ob_end_flush();
}
ob_start();
include(APPPATH.'errors/'.$template.'.php');
$buffer = ob_get_contents();
ob_end_clean();
return $buffer;
}
}
?>
I do it like this:
I create my own error page, and whenever I should throw a 404 error, I actually load my 404 page.
So say my default controller is site.php, my site.php looks like this:
<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
class Site extends CI_Controller {
public function index()
{
$this->load->view('welcome_message');
}
public function view($page = "home" , $function = "index")
{
do_something();
if($status == "404")
{
$function = "404";
}
$this->load->view('templates/header', $data);
$this->load->view($page.'/'.$function, $data);
$this->load->view('templates/footer', $data);
}
}
/* End of file welcome.php */
/* Location: ./application/controllers/welcome.php */
So I serve the home/404.php whenever an error occurs. i.e., I don't allow CodeIgniter to call show_404(); therefore the 404 page looks like any other page.
p.s. I assume that you followed the nice tutorial in CodeIgniter's website.
The simplest way to create custom error pages is to edit the files at /application/views/errors/html/error_*.php such as error_404.php (for 404s), error_db.php (for database errors) and error_general.php (for most other errors).
As these pages are within your application directory, you are free to customise them to your needs.
If your normal view template looks something like this:
<?php $this->load->view('includes/header'); ?>
...
...
<?php $this->load->view('includes/footer'); ?>
You can adapt this in your /application/views/errors/html/error_*.php files like so:
<?php
$page_title = $heading;
include VIEWPATH.'includes'.DIRECTORY_SEPARATOR.'header.php';
?>
<div class="well">
<h1><?php echo $heading; ?></h1>
<?php echo $message; ?>
</div>
<?php include VIEWPATH.'includes'.DIRECTORY_SEPARATOR.'footer.php'; ?>
Notice that we're no longer using views, but instead including the view files for the header & footer.
Another thing to note:
In the header view, I'm passing a $data object which includes $data['page_title']. As the error pages don't use views, you have to add any variables that you'd normally pass into the view, hence the presence of $page_title.
config/routes.php
edit
$route['404_override'] = '';
type here your controller for example Error
create a function index and load your view

CakePHP controller/action question with http://mysite.com/mycontroller/absentaction

Suppose someone hits in url http://mysite.com/comments/view/13
But that absentaction is not present in comments controller.
Then it gets normal error like that =>
Error: The action view is not defined in controller CommentsController
Error: Create CommentsController::view() in file: app/controllers/comments_controller.php.
<?php
class CommentsController extends AppController {
var $name = 'Comments';
function view() {
}
}
?>
Notice: If you want to customize this error message, create app/views/errors/missing_action.ctp
What i'm trying to do is that if someone hits url http://mysite.com/comments/view/13 and if the action is not present then it will redirect to http://mysite.com/.
How can i do this for unknown/absent action?
This trick is actually working pretty well.
You need to create a file app/app_error.php
<?php
class AppError extends ErrorHandler {
public function error404($params){
extract($params);
if(!isset($url)){
$url = $action;
}
if(!isset($message)){
$message ="";
}
if(!isset($base)){
$base = "";
}
$this->controller->redirect(array('controller'=>'pages','action'=>'home'));
//Or the page you want...
}
}
?>
How does it work?
It actually override the error404() function from the ErrorHandler and redirect the user whith $this->controller->redict();
Notice at the bottom of the error message, it says you can customize it by creating app/views/errors/missing_action.ctp. So all you need to do is create that .ctp file and include a redirect in it like this:
<?php
header( 'Location: http://mysite.com' ) ;
?>
It says it right in the error...
create app/views/errors/missing_action.ctp
And that's what you should do...
Try using a header in the missing_action.ctp to redirect to where you want the page to go.
You can either customise app/views/errors/missing_action.ctp or you can turn off debugging in app/config/core.php

Categories