Show data from another table with modal - Codeigniter - php

i have 2 tables
Now when i click detail , i want to show data from table 2 which have reportcode as i click on table 1 (image 1)
And now i want to show it on modal , so here is the example
1) click detail button -> get reportcode -> show reimbursename,etc to modal
Can you explain to me what should i do first ? and can you suggest me a plan please ,any answers will be appreciated. Thanks

My suggestion is:
1 - Add one class to detail button, i.e: detailButton and a data attribute or href with the especific reportCode.
<table>
<tr>
<td> ... </td>
<td> <button class='detailButton' href='<?php echo $reportCode; ?>' ... </button> </td>
2 - Add jquery to the bottom of the page:
$('.detailButton').click(function(e){
e.preventDefault();
var reportCode = $(this).attr('href');
var url = "yourUrl/controller/function";
$.post(url,{ code:reportCode },function(data){
//do stuff
//i.e: $('.modal').html(data).show();
});
});
Now you have a function that gets the reportCode, sends it to your controller by POST, you return something and the function gets the response and attach to a html.
Note, this way you must return a table from your controller. You could build dinamically too.
Hope it helps!
UPDATE:
You could check the values to your model and then use a exisitin template (for example one that generates the detail table), and return to your view as data to be attached at the correct position (method 1):
function detail(){
$getcode= $this->input->post('reportCode');
$data['showdetail'] = $this->model_expreport->showdetail($getcode);
$ret = $this->load->view('detail_template',$data,true); //return as data
print_r($ret);
}
Or you could use the Method 2:
function detail(){
$getcode= $this->input->post('reportCode');
$data['showdetail'] = $this->model_expreport->showdetail($getcode);
$this->output->set_content_type('application/json');
$this->output->set_output(json_encode($data));
}
This way, the view will recive a JSON that you could iterate and build your own page. Or you could create the full view and return it as data (in order to only append to your view).
You could use both.
In the view, you will recive either a full view:
$.post(url,{ code:reportCode },function(data){
$('#modal').html(data); //put the 'detail' response to the modal
}
Or with JSON you must iterate and build your own div dinamically, there are a lot of tutorials for this: https://uno-de-piera.com/cargar-json-con-jquery-y-codeigniter/

Related

Use CodeIgniter to render to a view at a specific anchor

In order to delete a person from the database, I would like to check its connections with other objects like inventories before deleting then display a bootstrap dialog message within the same page.
Using CodeIgniter, I have a page named "Person's details" that has a link to check these connections like so:
<a class="btn btn-custom" href="person/checkConnections/<?=$ID_Person?>">Delete</a>
In the controller "person", the method "checkConnections" looks like:
public function checkConnections($ID_Person)
{
$data["strConnections"] = "3 connections with inventories found";
$this->load->view("person/showdetails", $data)
// launch the dialog box #deleteMsg
???
}
How can I launch the bootstrap dialog box which has an id="deleteMsg" and which is in the "Person's details" page?
if it was an html url, the url would look like : http://mywebsite/person/showdetails/134#deleteMsg. But how can I have the same result using the codeIgniter method to render a view?
I can check these connections when loading the page the first time. But it wouldn't be efficient to do it every time since the delete action is rarely used.
You can use ajax to call the delete method and then show the response in a model form like below.
$('.btn-custom').click(function(e){
var url = $(this).attr('href');
$.ajax({
type: 'GET',
url: url,
success: function(rtn)
{
//load the bootstrap model setting the rtn as html content.
}
});
return false;
});
the controller should return the html output of your view.
public function checkConnections($ID_Person)
{
$data["strConnections"] = "3 connections with inventories found";
echo $this->load->view("person/showdetails", $data, true);
}
note the third parameter true of the view load method, this will return the output of the view.

Using one delete function for a post jquery request of php request

I'm looking to find out how I can accomplish this next task. I have a controller that loads a view with a table that lists pages in my database. In every row that is made in the table there is a spot for a icon that when clicked will do one of two things.
If the user does not have javascript enabled:
Clicking on the icon will redirect to the delete function in the controller with id of the page as a paramter
Delete controller function will run delete function in model sending page id to delete model function
Delete function in model will delete the page from the database and when returned back to page controller delete function it will redirect back to index function to show list of pages table again.
After redirect it will display a title and message as to a success/fail.
If the user does have javascript enabled:
Send a post to the delete function in controller with jquery post
method with the data page id
Delete controller function will run delete function in model sending page id to delete model function
Delete function in model will delete the page from the database and when returned back to page controller delete function it create a message array for the json object to return to the success function of the post request.
A message with my pnotify plugin will create a message that is formed from that json object and display it to the user
What I would like to know is with doing this how to properly accommodate for these two scenarios? I have started attempting this but would like to some clarification if I have made a mistake so far.
<?php
// Controller delete function
public function delete($content_page_id)
{
if (isset($content_page_id) && is_numeric($content_page_id))
{
$content_page_data = $this->content_page->get($content_page_id);
if (!empty($content_page_data))
{
//update is ran instead of delete to accompodate
//for the soft delete functionality
$this->content_page->update('status_id', 3);
if ($this->input->is_ajax_request())
{
//return json data array
}
}
}
}
?>
Global JS file to be used for multiple tables with delete buttons
/* Delete Item */
$('.delete').click(function(event) {
event.preventDefault();
var item_id = $(this).attr('rel');
$.post(<?php echo current_url(); ?>'delete', { item_id : item_id }, function(data)
{
if (data.success)
{
var anSelected = fnGetSelected( oTable );
oTable.fnDeleteRow( anSelected[0] );
}
}, 'json');
});
I think that you should have two functions in PHP:
public function delete($content_page_id) {
// Your delete code
return "a string without format";
}
public function deleteAjax($content_page_id) {
return json_encode($this->delete($content_page_id));
}
So, when the user has JS enabled, you call deleteAjax passing a parameter in your $.post function to let PHP know that JS is enabled:
$.post(<?php echo current_url(); ?>'delete', { item_id : item_id, js: 1 }, function(data)
{
if (data.success)
{
var anSelected = fnGetSelected( oTable );
oTable.fnDeleteRow( anSelected[0] );
}
}, 'json');
And if JS is disabled, call the other function. You should use an AJAX specialized controller instead a function in the same class.
1) As far as "displaying a message" - the view-itself could be ready for a 'message' if one exists. Bringing us back to...
2) Can you have your delete function return the message you want displayed? Your AJAX approach will ignore this message while your View will display it...
3) I agree that your 'Controller delete function' should 'finish' with different outcomes based on whether the request is AJAX or not. I like what #Skaparate (answered Aug 30 at 18:37) was doing with adding: js:1 In your delete function, you could use this in a simple conditional:
if js = 1
header('HTTP/1.1 200');
else
call view and include/pass-in the 'message'

Just can't get this to work

I have been trying to figure out this problem I've been having all day. I will give you a simplified run down of what I have been trying to do. The user enters a number, and however much the number is, is the number of categories there are going to be on the following page. Within each category, there is an input text button, along with an "Add Textbox" button that adds additional input textboxes dynamically. However, the problem here is that each category has this same setup on the same page. For example, if the user enters the number "3", then the page will vertically load three categories looking something like the following:
Category #1
(Initial user input textbox for category #1)
("Add Textbox" button to allow user to fill out another option)
Category #2
(Initial user input textbox for category #2)
("Add Textbox" button to allow user to fill out another option)
Category #3
(Initial user input textbox for category #3)
("Add Textbox" button to allow user to fill out another option)
The struggle I have been encountering is that each category button will need to have its own function, to tell the button where to place the textbox. This coupled with the fact that the number of categories changes depending on the user's input, has made things difficult. I started with the following:
var categoryCount = <?php echo $categoryCount; ?>;
var click = {};
for (var num=1;num<=categoryCount;num++) {
var newClick = "click_" + num;
click[newClick] = function() {
// some contents when this button is clicked
};
}
This JS creates an object of functions, which in JS would be able to be accessed by doing something like the following:
click['click_' + someID]();
However, the problem is that I cannot do this using the "onclick" attribute in my HTML/PHP button. I cannot access this object of functions, and cannot call any of the individual functions, obviously. I think I am going to need to rethink all of this and start again. I just can't think of another way to get this to work. Please share your ideas with me! Your help would be greatly appreciated.
For something like this, I'd write a constructor I could use like this
var cat1 = new Category(document.body);
Luckily for you, I also wrote one as an example. See the DEMO HERE. I haven't styled it at all for the new lines etc, though.
var Category = (function () {
var categoryCount = 0;
function elem(tag) { // shortcut
return document.createElement(tag);
}
function text(str) { // shortcut
return document.createTextNode(str);
}
function Category(node) {
var self = this; // this should have been var'd, oops!!
this.categoryId = ++categoryCount;
// make add button
this.addButton = elem('button');
this.addButton.appendChild(text('Add Textbox'));
this.addButton.addEventListener('click', function () {
self.addTextbox();
});
// make wrapper
this.wrapper = elem('section');
this.wrapper.setAttribute('id', 'cat'+this.categoryId);
this.wrapper.appendChild(this.addButton);
// make textboxes
this.textboxes = [];
this.addTextbox();
// append to document
if (node) {
this.append(node);
}
}
Category.prototype.addTextbox = function () {
var e = elem('textarea');
e.setAttribute('name', 'cat-'+this.categoryId+'-textbox[]');
this.textboxes.push(e);
this.wrapper.insertBefore(e, this.addButton);
};
Category.prototype.append = function (node) {
return node.appendChild(this.wrapper);
};
return Category;
}());

Hiding in foreach loop

I am getting json in "data" and passing it in for loop. Onclick of buy button, it goes to the App function. On success I need to hide the buy button and display the download label.
My problem is onclick of 1st buy button, download link for both the buttons appear.
Ideally oneclick of first buy button, buy button should be hidden and download label should appear. similarly oneclick of second buy button, buy button should be hidden and download label should appear.
How do I get particular id of each button so that I can hide one at a time?
Please help me out
function (data)
{
var Class ='';
for (var i=0; i <data.length;i++)
{
Class += '<div name="buy\''+data[i].id+'\'" class="btn btn-primary btn-small" onclick="buy(\''+data[i].identifier+'\',\''+data[i].id+'\',\''+data[i].url +'\'); return false;" href=""></div><div class="download\''+data[i].id+'\'" id="download">D<span style="font-size:15px"></span></div>';
}
return Class;
}
App = function(identifier, app_id, url) {
$.ajaxSetup({
data : {
csrf_test_name : $.cookie('csrf_cookie_name')
}
});
var jqxhr = $.post(SITE_URL + 'admin/appstore/purchaseApp', {
identifier : identifier,
ap_id : ap_id
}).done(function(data1) {
obj = JSON.parse(data1);
bootbox.alert(obj.status, obj.label);
$("#download").html('<a href='+download_url+app_id+'>Download!</a>');
});
};
it is for loop am using.. am passing '; now how do I hide buy id? $("#buys"+"'"+data[i].id+"'").hide(); is this the right way? It gives me error
if you look at the actual markup generated in Class, you will see that your buy buttons don't have an id at all. perhaps something like
Class += '<div id="buy-button-'+data[i].id+'" name="...
Now you have a unique id on each button. The next part of your problem is knowing which button to remove after a successful Ajax call. You will need to include that in the data1, returned from the server. For the sake of argument, let's say the server returns the value in your data1 object as app_id. Then all you need to do is
jQuery('#buy-button-'+data1.app_id).hide();
Slightly off-topic, I'm not too keen on the way you're using single quotes in the buttons' name attributes, either, but I don't think that's relevant here.

how to ajaxify zend_pagination results (already working with partialoop) using jquery

in the controller i have :
$paginator = Zend_Paginator::factory($mdlPost->getPosts($this->moduleData->accordion, 'name ASC'));
if(isset($params['cities'])) {
$paginator->setCurrentPageNumber(intval($params['cities']));
}
$paginator->setItemCountPerPage(4);
$this->view->posts = $paginator;
in the view's i have some thing like this :
if ($this->posts != null) {?>
<div id="cities_accord" class="news">
<?php echo $this->partialLoop('partials/post-min.phtml', $this->posts); ?>
</div>
<?php echo $this->paginationControl($this->posts,
'Sliding',
'public/pagination_cont.phtml');
}
the partial/post-min.phtml
<?php
$color = array(1=>'spring',2=>'summer',3=>'autumn',4=>'winter');
?>
<div id='<?php echo $color[$this->partialCounter] ?>' class="accordion_post">
<?php
$link = Digitalus_Uri::get(false, false, array('openCity' =>
$this->id));//$color[$this->partialCounter]));
?>
<h1 class="accordion_post_title"><?php echo $this->title ?></h1>
<p><?php echo $this->teaser ?> <i>read more</i></p>
</div>
the pagination_cont.phtml taken from this link zend ( http://framework.zend.com/manual/en/zend.paginator.usage.html )
will show links that will pass params to the controller to fetch the corresponding whole page which is working alright for now
but i want to change this so that i will be able ajaxify the returned ( i.e. only a single paginated value rather than reloading the whole page ) results how can i do that using jquery and what should i change ..
** EDIT: it would be nice to have a fail-save ,if possible, for browsers(users) that disabled javascript to see the same thing by reloading the page (i.e. keeping the current status for if(javascript_not_enabled ))**
This is what I've done in the past.
First, setup the AjaxContext action helper to enable the html context on your controller action.
Add a .ajax.phtml view that just contains the section of markup that may be replaced via AJAX as well as the pagination control links. You can probably just copy this out of your normal view. Replace that section in your normal view with something like
<div id="reloadable-content">
<?php echo $this->render('controller/action.ajax.phtml') ?>
</div>
This will ensure that your initial and any non-AJAX requests will still include the right content. The <div> id is purely for referencing the loadable block in JavaScript.
Also make sure you include your JS file (using headScript) in the normal view only.
Now, in your JS file, unobtrusively add the appropriate event binding to the paginator links. As you'll be replacing the pagination control section in order to reflect the correct current page and other links, it's probably best to do this using the jQuery live binding. I'm also assuming you'll wrap the pagination control with some kind of identifiable element (<div class="pagination-control"> for example)
$('.pagination-control').find('a').live('click', function(e) {
var link = $(this);
$('#reloadable-content').load(link.attr('href'), { format: 'html' });
return false;
});
Keep in mind that in using this method, you will lose the ability to navigate the paged requests using the normal back / forward browser buttons. You will also lose the ability to bookmark pages directly (though you could always provide a permanent link to the current page as part of the AJAX loaded content).
You can use something like the jQuery history plugin if you're really concerned but that will require more client-side work.
Another caveat is that the above will only work with pagination links. If you want to use a form with dropdown page selection, you need to add another event handler for the submission.
GOT IT and big Thanks to #Phil Brown :
in the controller int() change the response type to json
class NewsController extends Zend_Controller_Action
{
public function init()
{
$contextSwitch = $this->_helper->getHelper('contextSwitch');
$contextSwitch->addActionContext('list', 'JSON')
->initContext();
}
// ...
}
public listAtcion() {
// .............
$paginator = Zend_Paginator::factory($mdlPost->getPosts($this->moduleData->accordion, 'name ASC'));
if(isset($params['cities'])) {
$paginator->setCurrentPageNumber(intval($params['cities']));
}
$paginator->setItemCountPerPage(4);
$post = array();
foreach($paginator as $post ) {
$post[] = $post;
}
$this->view->post = $paginator;
#TODO //add a check here for non-ajax requests (#improvment)
$this->view->posts = $paginator;
}
in one of the views (most probably in the pagination_cont.phtml) on the pagination controller add the ajax links
<?= $this->ajaxLink (
$this->url('cities'=>$this->page_num),array('id'=>'div_id','complete'=>'js_method(json_data)','method'=>post) ,array('format'=>'JSON'));
and add a JavaScript function of js_method(json_data) to modify the div with id = 'div_id' with a json data
function js_method(json_data) {
var content = parse.JSON(json_data);
$('#div_id').html('');
//fill it with the reposnse content some thing like $('#div_id').append(content);
}

Categories