In this article, we’re going to create a custom order totals extension in OpenCart. The order totals extensions allow you to manipulate the order amount during the checkout. It’s a really useful way to alter the price by either adding extra taxes or providing discount through the different methods. We’ll create a fully fledged custom order totals extension which will apply a custom tax defined by the back-end configuration form.
To create a custom order totals extension, we need to set up files in the back-end and front-end. The back-end files are used to set up a configuration form, and the front-end files are used to define the logic of the extension. Of course, OpenCart won’t detect your extension during checkout without front-end files.
We’ll use the latest version of OpenCart. Also, I assume that you’re familiar with the basic module development process in OpenCart. If you are not familiar with it, here’s a nice article explaining custom module development.
Let’s go ahead and start right away!
Back-End File Setup
In this section, we’ll create files related to the back-end section. At the end of this section, you’ll be able to see our custom order totals extension in the list along with the other order totals extensions. Also, you’ll be able to install and configure it using the custom configuration form.
Go ahead and create a controller file admin/controller/total/customot.php
with the following contents.
<?php class ControllerTotalCustomot extends Controller { private $error = array(); public function index() { $this->load->language('total/customot'); $this->document->setTitle($this->language->get('heading_title')); $this->load->model('setting/setting'); if (($this->request->server['REQUEST_METHOD'] == 'POST') && $this->validate()) { $this->model_setting_setting->editSetting('customot', $this->request->post); $this->session->data['success'] = $this->language->get('text_success'); $this->response->redirect($this->url->link('extension/total', 'token=' . $this->session->data['token'], 'SSL')); } $data['heading_title'] = $this->language->get('heading_title'); $data['text_edit'] = $this->language->get('text_edit'); $data['text_enabled'] = $this->language->get('text_enabled'); $data['text_disabled'] = $this->language->get('text_disabled'); $data['text_none'] = $this->language->get('text_none'); $data['entry_customtax'] = $this->language->get('entry_customtax'); $data['entry_status'] = $this->language->get('entry_status'); $data['entry_sort_order'] = $this->language->get('entry_sort_order'); $data['button_save'] = $this->language->get('button_save'); $data['button_cancel'] = $this->language->get('button_cancel'); if (isset($this->error['warning'])) { $data['error_warning'] = $this->error['warning']; } else { $data['error_warning'] = ''; } $data['breadcrumbs'] = array(); $data['breadcrumbs'][] = array( 'text' => $this->language->get('text_home'), 'href' => $this->url->link('common/dashboard', 'token=' . $this->session->data['token'], 'SSL') ); $data['breadcrumbs'][] = array( 'text' => $this->language->get('text_total'), 'href' => $this->url->link('extension/total', 'token=' . $this->session->data['token'], 'SSL') ); $data['breadcrumbs'][] = array( 'text' => $this->language->get('heading_title'), 'href' => $this->url->link('total/customot', 'token=' . $this->session->data['token'], 'SSL') ); $data['action'] = $this->url->link('total/customot', 'token=' . $this->session->data['token'], 'SSL'); $data['cancel'] = $this->url->link('extension/total', 'token=' . $this->session->data['token'], 'SSL'); if (isset($this->request->post['customot_customtax'])) { $data['customot_customtax'] = $this->request->post['customot_customtax']; } else { $data['customot_customtax'] = $this->config->get('customot_customtax'); } if (isset($this->request->post['customot_status'])) { $data['customot_status'] = $this->request->post['customot_status']; } else { $data['customot_status'] = $this->config->get('customot_status'); } if (isset($this->request->post['customot_sort_order'])) { $data['customot_sort_order'] = $this->request->post['customot_sort_order']; } else { $data['customot_sort_order'] = $this->config->get('customot_sort_order'); } $data['header'] = $this->load->controller('common/header'); $data['column_left'] = $this->load->controller('common/column_left'); $data['footer'] = $this->load->controller('common/footer'); $this->response->setOutput($this->load->view('total/customot.tpl', $data)); } protected function validate() { if (!$this->user->hasPermission('modify', 'total/customot')) { $this->error['warning'] = $this->language->get('error_permission'); } return !$this->error; } }
As you can see, it’s a fairly standard back-end controller set up in OpenCart. The main purpose of this controller file is to set up the labels and other elements which will be used to display the configuration form. Of course, it handles the form submission by validating a form and saving values to the database.
Now, let’s go ahead and create a language file at admin/language/english/total/customot.php
with the following contents.
<?php // Heading $_['heading_title'] = 'Custom Order Total'; // Text $_['text_success'] = 'Success: You have modified custom order total!'; $_['text_edit'] = 'Edit Custom Order Total'; // Entry $_['entry_customtax'] = 'Custom Tax (%)'; $_['entry_status'] = 'Status'; $_['entry_sort_order'] = 'Sort Order'; // Error $_['error_permission'] = 'Warning: You do not have permission to modify custom order total!';
Again, It should be pretty easy to understand as we’re just defining labels.
Finally, we’ll create a view template file at admin/view/template/total/customot.tpl
.
<?php echo $header; ?><?php echo $column_left; ?> <div id="content"> <div class="page-header"> <div class="container-fluid"> <div class="pull-right"> <button type="submit" form="form-customot" data-toggle="tooltip" title="<?php echo $button_save; ?>" class="btn btn-primary"><i class="fa fa-save"></i></button> <a href="<?php echo $cancel; ?>" data-toggle="tooltip" title="<?php echo $button_cancel; ?>" class="btn btn-default"><i class="fa fa-reply"></i></a> </div> <h1><?php echo $heading_title; ?></h1> <ul class="breadcrumb"> <?php foreach ($breadcrumbs as $breadcrumb) { ?> <li><a href="<?php echo $breadcrumb['href']; ?>"><?php echo $breadcrumb['text']; ?></a></li> <?php } ?> </ul> </div> </div> <div class="container-fluid"> <?php if ($error_warning) { ?> <div class="alert alert-danger"><i class="fa fa-exclamation-circle"></i> <?php echo $error_warning; ?> <button type="button" class="close" data-dismiss="alert">×</button> </div> <?php } ?> <div class="panel panel-default"> <div class="panel-heading"> <h3 class="panel-title"><i class="fa fa-pencil"></i> <?php echo $text_edit; ?></h3> </div> <div class="panel-body"> <form action="<?php echo $action; ?>" method="post" enctype="multipart/form-data" id="form-customot" class="form-horizontal"> <div class="form-group"> <label class="col-sm-2 control-label" for="input-customtax"><?php echo $entry_customtax; ?></label> <div class="col-sm-10"> <input type="text" name="customot_customtax" value="<?php echo $customot_customtax; ?>" placeholder="<?php echo $entry_customtax; ?>" id="input-customtax" class="form-control" /> </div> </div> <div class="form-group"> <label class="col-sm-2 control-label" for="input-status"><?php echo $entry_status; ?></label> <div class="col-sm-10"> <select name="customot_status" id="input-status" class="form-control"> <?php if ($customot_status) { ?> <option value="1" selected="selected"><?php echo $text_enabled; ?></option> <option value="0"><?php echo $text_disabled; ?></option> <?php } else { ?> <option value="1"><?php echo $text_enabled; ?></option> <option value="0" selected="selected"><?php echo $text_disabled; ?></option> <?php } ?> </select> </div> </div> <div class="form-group"> <label class="col-sm-2 control-label" for="input-sort-order"><?php echo $entry_sort_order; ?></label> <div class="col-sm-10"> <input type="text" name="customot_sort_order" value="<?php echo $customot_sort_order; ?>" placeholder="<?php echo $entry_sort_order; ?>" id="input-sort-order" class="form-control" /> </div> </div> </form> </div> </div> </div> </div> <?php echo $footer; ?>
This file contains the XHTML code for our configuration form.
So that’s it as far as our back-end set up is concerned. Go to Extensions > Order Totals. You should be able to see our extension Custom Order Total listed along with other extensions. Let’s install and configure it as shown in the following screenshot.
I’ve set the Custom Tax value to 5, so it’ll charge 5% of the total order value. Fill in the values and save the form.
Front-End File Setup
In this section, we’ll define files for the front-end, so that our extension is detected in the front-end checkout flow.
Create a model file catalog/model/total/customot.php
with the following contents.
<?php class ModelTotalCustomot extends Model { public function getTotal(&$total_data, &$total, &$taxes) { $this->load->language('total/customot'); // get customtax $customtax_percentage = $this->config->get('customot_customtax'); if ($customtax_percentage > 0) { $customtax_value = round(($total * $customtax_percentage) / 100); $total_data[] = array( 'code' => 'customot', 'title' => $this->language->get('text_customot'), 'value' => $customtax_value, 'sort_order' => $this->config->get('customot_sort_order') ); $total += $customtax_value; } } }
It’s an important file and the central logic of our extension goes here. Conventionally, OpenCart calls the getTotal
method for every order totals extension during the checkout. You should notice the important arguments $total_data
, $total
and $taxes
.
The $total_data
variable represents an array of all the order total extensions data. The $total
variable is the total order amount, and $taxes
contains the taxes applied.
In that method, we’re fetching a Custom Tax value which was set from the back-end configuration form. Further, we calculate the custom tax amount and assign it to the $customtax_value
variable. Next, we plug in our order totals extension information to the $total_data
array and add the custom tax amount to the $total
variable.
Finally, we need to define a language file at catalog/language/english/total/customot.php
with the following contents.
<?php $_['text_customot'] = 'Custom Tax Value';
So that’s it for the front-end!
Demo in the Front-End
Go ahead and add products to cart, and you’ll be able to see our custom tax applied as shown in the following screenshot.
So in this way, you could influence the order amount using the order totals extension.
Conclusion
In this article, we've learned how to create a custom order totals extension and manipulate the order amount. It’s a really useful way to attach any custom taxes and discounts.
If you're looking for additional OpenCart tools, utilities, extensions, and so on that you can leverage in your own projects or for your own education, don't forget to see what we have available in the marketplace.
Suggestions and queries are always welcome!
Comments