jquery sortable saving to database not working properly - php

I'm trying to incorporate the jquery sortable functionality into my website and saving the positions in the database is giving me all sorts of headaches... I've been fighting this for 3 days now, and I cannot seem to get this work properly.
As it stands, it is saving positions to the database, but not in the order or positions, that you'd expect. Meaning, if I move the item in position 0 to position 1, it saves the positions in a different order in the db. check out a live version here.
Here is my code...
index.php file:
<div id="container">
<?php
require_once 'conn.php';
$q = ' SELECT * FROM items WHERE groupId = 3 ORDER BY position ';
$result = mysqli_query($db, $q);
if ($result->num_rows > 0) {
while($items = $result->fetch_assoc()) {
?>
<div id='sort_<?php echo$items['position'] ?>' class='items'>
<span>☰</span> <?php echo$items['description'] ?>
</div>
<?php
}
}
?>
</div>
js.js file:
$("#container").sortable({
opacity: 0.325,
tolerance: 'pointer',
cursor: 'move',
update: function(event, ui) {
var itId = 3;
var post = $(this).sortable('serialize');
$.ajax({
type: 'POST',
url: 'save.php',
data: {positions: post, id: itId },
dataType: 'json',
cache: false,
success: function(output) {
// console.log('success -> ' + output);
},
error: function(output) {
// console.log('fail -> ' + output);
}
});
}
});
$("#container").disableSelection();
save.php file:
require_once('conn.php');
$itId = $_POST['id'];
$orderArr = $_POST['positions'];
$arr = array();
$orderArr = parse_str($orderArr, $arr);
$combine = implode(', ', $arr['sort']);
$getIds = "SELECT id FROM items WHERE groupId = '$itId' ";
$result = mysqli_query($db, $getIds);
foreach($arr['sort'] as $a) {
$row = $result->fetch_assoc();
$sql = " UPDATE items
SET position = '$a'
WHERE id = '{$row['id']}' ";
mysqli_query($db, $sql);
}
echo json_encode( ($arr['sort']) );
Can anyone please point to where I am going wrong on this?
Thank you in advance.
Serge

In case someone lands on here, here is what worked in my case...
NOTE: I did not create prepared statements in the index.php select function. But you probably should.
index.php file:
<div id="container">
<?php
require_once 'conn.php';
$q = ' SELECT * FROM items WHERE groupId = 3 ORDER BY position ';
$result = mysqli_query($db, $q);
if ($result->num_rows > 0) {
while( $items = $result->fetch_assoc() ){
?>
<div id='sort_<?php echo $items['id'] ?>' class='items'>
<span>☰</span> <?php echo $items['description'] ?>
</div>
<?php
}
}
?>
</div>
jquery sortable file:
var ul_sortable = $('#container');
ul_sortable.sortable({
opacity: 0.325,
tolerance: 'pointer',
cursor: 'move',
update: function(event, ui) {
var post = ul_sortable.sortable('serialize');
$.ajax({
type: 'POST',
url: 'save.php',
data: post,
dataType: 'json',
cache: false,
success: function(output) {
console.log('success -> ' + output);
},
error: function(output) {
console.log('fail -> ' + output);
}
});
}
});
ul_sortable.disableSelection();
update php file:
$isNum = false;
foreach( $_POST['sort'] as $key => $value ) {
if ( ctype_digit($value) ) {
$isNum = true;
} else {
$isNum = false;
}
}
if( isset($_POST) && $isNum == true ){
require_once('conn.php');
$orderArr = $_POST['sort'];
$order = 0;
if ($stmt = $db->prepare(" UPDATE items SET position = ? WHERE id=? ")) {
foreach ( $orderArr as $item) {
$stmt->bind_param("ii", $order, $item);
$stmt->execute();
$order++;
}
$stmt->close();
}
echo json_encode( $orderArr );
$db->close();
}

Change your JS code like this:
{...}
tolerance: 'pointer',
cursor: 'move',
// new LINE
items: '.items', // <---- this is the new line
update: function(event, ui) {
var itId = 3;
var post = $(this).sortable('serialize'); // it could be removed
// new LINES start
var post={},count=0;
$(this).children('.items').each(function(){
post[++count]=$(this).attr('id');
});
// new LINES end
$.ajax({
{...}
With this $.each loop you overwrite your var post -> serialize and define your own sort order. Now look at your $_POST["positions"] with PHP print_r($_POST["positions"]); and you have your positions in your own order.

Related

Creating Dynamic Pages with php and MySQL

I am creating a list of links in main.php using "donemler" table in mySQL database and would like to create a page that shows data from "sikkeler" table (which has a foreing key donemID that is used as a relationship between the two tables) as the user clicks it. (data.php is a part of the index.php which is a infinite scroll page)
Here I tried to call $row["donemID"] with GET method using
$k=$_GET['donemID'] in index.php but did not work.
I have also tried to use SESSIONS method where I add "$_SESSION['donemID']=$row$row["donemID"] to main.php
and called it back in index.php as
$k=$_SESSION['donemID']
but it also did not work.
I would like to learn how to create pages and show relevant data in php.
Thanks in advance!
main.php
<?php
require_once "config.php";
$sql = $conn->query("SELECT * FROM donemler ORDER BY donemID");
if ($sql->num_rows > 0) {
// output data of each row
while($row = $sql->fetch_assoc()) {
echo "<tr><td><a href='index.php?devletID=".$row["devletID"]."&donemID=".$row["donemID"]."'>" .$row["donemler"]. "</a></td></tr>";
}
} else {
echo "0 results";
}
$conn->close();
?>
index.php
<script type="text/javascript">
var start = 0;
var limit = 20;
var reachedMax = false;
var dnmID = $_GET("donemID");
$(window).scroll(function () {
if ($(window).scrollTop() == $(document).height() - $(window).height() )
getData();
});
$(document).ready(function () {
getData();
});
function getData() {
if (reachedMax)
return;
$.ajax({
url: 'data.php',
method: 'POST',
dataType: 'text',
data: {
getData: 1,
start: start,
limit: limit,
dnmID: dnmID,
},
success: function(response) {
if (response == "reachedMax")
reachedMax = true;
else {
start += limit;
$(".results").append(response);
}
}
});
}
</script>
data.php
<?php
if (isset($_POST['getData']) ) {
$conn = new mysqli('localhost', 'usrnm', 'pss', 'db');
$dnmID = $conn->real_escape_string($_POST['dnmID']);
$start = $conn->real_escape_string($_POST['start']);
$limit = $conn->real_escape_string($_POST['limit']);
$sql = $conn->query("SELECT * FROM sikkeler WHERE donemID='$dnmID' ORDER BY kayit_no DESC LIMIT $start, $limit");
if ($sql->num_rows > 0) {
$response = "";
while($data = $sql->fetch_array()) {
$response .= '
<tr>
<td>ICD#'.$data['kayit_no'].'</td>
<td>'.$data['donemi'].'</td>
<td><img src="coin_images/'.$data['resim'].'" border="2" width="200px" /></td>
<td>'.$data['darp'].'</td>
<td>'.$data['tarih'].'</td>
<td>'.$data['birim'].'</td>
<td>'.$data['agirlik'].'</td>
<td>'.$data['cap'].'</td>
<td>'.$data['tip'].'</td>
<td>'.$data['reference'].'</td>
</tr>
';
}
exit($response);
} else
exit('reachedMax');
}
?>
You are checking through two different request methods:
$_POST['getData']
$k=$_GET['donemID']
Since you are using the query strings, it is a GET method to check with.
There is no such variable i.e. getData on main.php

Paginate result using select 2 ajax remote data

Trying to paginate ajax data using Select2 (v 4.0.6.rc1) so that the user can find more results if not present in the first limit ,using the following but not retrieving data.I 'll appreciate if someone helps me out,there is not much of examples about pagination.
i was trying to paginate data using the help of this question Select2 v4 how to paginate results using AJAX its not seems to be working,getting the array but not correct format.
JS:
$('#compose_username').select2({
dropdownParent: $("#modal-compose") ,
placeholder: "Search Username...",
minimumInputLength: 1,
ajax: {
url: "username.php",
dataType: 'json',
delay: 250,
cache: false,
data: function (params) {
return {
term: params.term,
page: params.page || 1
//a: params.term, // search term
//psf: params.page
};
},
processResults: function(data) {
console.log(data);
var result = $.map(data, function (item) { return { id: item.id, text: item.username }});
return { results: result };
}
}
});
PHP
try{
$page= $_GET['page'];
// $resultCount = 10;
// $offset = ($page - 1) * $resultCount;
$pageLength = 20;
$pageStart = ($page - 1) * $pageLength;
$pageEnd = $pageStart + $pageLength;
$stmt = $db_con->query("SELECT id,first_name FROM datatables_demo WHERE first_name LIKE '%".$_GET['term']."%' LIMIT {$pageStart},{$pageEnd}");
$count = $db_con->query("SELECT count(first_name) FROM datatables_demo WHERE first_name LIKE '%".$_GET['term']."%' LIMIT {$pageStart},{$pageEnd}")->fetchColumn();;
$stmt->execute();
$json = [];
while($row = $stmt->fetch(PDO::FETCH_ASSOC)){
$json[] = ['id'=>$row['id'], 'username'=>$row['first_name']];
}
$endCount = $pageStart + $pageLength;
$morePages = $endCount > $count;
$results = array(
"results" => $json,
"pagination" => array(
"more" => $morePages
)
);
echo json_encode($results);
}
catch(PDOException $e){
echo $e->getMessage();
}
Found not much examples about select2 paginate, had to figure it out on my own and here is the full working of how to paginate data(infinite scroll) using Select2: Hope this helps someone else.
JS:
$('#compose_username').select2({
dropdownParent: $("#modal-compose") ,
placeholder: "Search Username...",
minimumInputLength: 1,
allowClear: true,
ajax: {
url: "username.php",
dataType: 'json',
delay: 250,
cache: false,
data: function (params) {
return {
term: params.term,
page: params.page || 1,
};
},
processResults: function(data, params) {
//console.log(data);
// NO NEED TO PARSE DATA `processResults` automatically parse it
//var c = JSON.parse(data);
console.log(data);
var page = params.page || 1;
return {
results: $.map(data, function (item) { return {id: item.col, text: item.col}}),
pagination: {
// THE `10` SHOULD BE SAME AS `$resultCount FROM PHP, it is the number of records to fetch from table`
more: (page * 10) <= data[0].total_count
}
};
},
}
});
PHP(USING PDO):
try{
$page= $_GET['page'];
$resultCount = 10;
$end = ($page - 1) * $resultCount;
$start = $end + $resultCount;
$stmt = $db_con->query("SELECT col,col FROM table WHERE col LIKE '".$_GET['term']."%' LIMIT {$end},{$start}");
$stmt->execute();
$count = $stmt->rowCount();
$data = [];
while($row = $stmt->fetch(PDO::FETCH_ASSOC))
$data[] = ['id'=>$row['id'], 'col'=>$row['col'],'total_count'=>$count];
// IF SEARCH TERM IS NOT FOUND DATA WILL BE EMPTY SO
if (empty($data)){
$empty[] = ['id'=>'', 'col'=>'', 'total_count'=>''];
echo json_encode($empty);
}
else
echo json_encode($data);
}
catch(PDOException $e){
echo $e->getMessage();
}

Autoload results fetching same results over and over

I have implemented the following autoload code. It fetches result from database but it keeps looping the same result over and over.
php code
<?php
require_once("config.php");
$limit = (intval($_GET['limit']) != 0 ) ? $_GET['limit'] : 10;
$offset = (intval($_GET['offset']) != 0 ) ? $_GET['offset'] : 0;
$keywords = $_GET['keywords'];
$sql = "SELECT * FROM blog_posts WHERE postCat LIKE '".$keywords."' ORDER BY postID ASC LIMIT $limit OFFSET $offset";
try {
$stmt = $DB->prepare($sql);
$stmt->execute();
$results = $stmt->fetchAll();
} catch (Exception $ex) {
echo $ex->getMessage();
}
if (count($results) > 0) {
foreach ($results as $res) {
echo '<h3>' . $res['postTitle'] . '</h3>';
}
}
?>
Try this
<?php
$keywords = 'events';
?>
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Test</title>
<script src="bootstrap/js/jquery-1.11.1.min.js"></script>
</head>
<body>
<div class="col-lg-12" id="results"></div>
<div id="loader_image"><img src="loader.gif" alt="" width="24" height="24"> Loading...please wait</div>
<div class="margin10"></div>
<div id="loader_message"></div>
</div>
<script type="text/javascript">
var keywords = '<?php echo $keywords; ?>'; // Changed
var busy = false;
var limit = 15;
var offset = 0;
function displayRecords(lim, off) {
// Changed/New
var data = {
'limit': lim,
'offset': off,
'keywords': keywords,
};
$.ajax({
type: "GET",
async: false,
url: "getrecords.php",
data: data, // Changed
cache: false,
beforeSend: function() {
$("#loader_message").html("").hide();
$('#loader_image').show();
},
success: function(html,textStatus,jqHXR) {
$("#results").append(html);
$('#loader_image').hide();
if (html == "") {
$("#loader_message").html('<button class="btn btn-default" type="button">No records found.</button>').show()
} else {
$("#loader_message").css('display','none');
$("#loader_message").html(html);
}
window.busy = false;
},
});
}
$(document).ready(function() {
// start to load the first set of data
if (busy == false) {
busy = true;
// start to load the first set of data
displayRecords(limit, offset);
}
$(window).scroll(function() {
// make sure u give the container id of the data to be loaded in.
if ($(window).scrollTop() + $(window).height() > $("#results").height() && !busy) {
$('#result').on('scroll', function() { if($(this).scrollTop() + $(this).innerHeight() >= $(this)[0].scrollHeight) { busy = true; offset = limit + offset; setTimeout(function() { displayRecords(limit, offset); }, 500); } })
// you can remove the above code and can use directly this function
// displayRecords(limit, offset);
}
});
});
</script>
</body>
</html>
this is loading same contents over and over because on each ajax call you are sending same 'data' which is
var data = {
'limit': limit,
'offset': offset,
'keywords': keywords,
};
Change the function to use new limit and offset
function displayRecords(lim, off) {
data = {
'limit': lim,
'offset': off,
'keywords': keywords,
};
$.ajax({
type: "GET",
async: false,
url: "getrecords.php",
data: data, // Changed
cache: false,
beforeSend: function() {
$("#loader_message").html("").hide();
$('#loader_image').show();
},
...
...

PHP - variable from GET is changing

I have a svg.php file with some shapes.
<rect onclick="window.location='search.php?filter=1'" width="50" height="50">
<rect onclick="window.location='search.php?filter=2'" width="50" height="50">
Search.php
div class="container">
<textarea class="search" id="search_id"></textarea>
<div id="result"></div>
<?php include("svg.php"); ?>
</div>
//This is for a autocomplete search, took it from http://www.2my4edge.com/2013/08/autocomplete-search-using-php-mysql-and.html
<script type="text/javascript">
$(function(){
$(".search").keyup(function() {
var search_id = $(this).val();
var dataString = 'search='+ search_id;
if (search_id=='') {
$.ajax({
type: "POST",
url: "search_database.php",
data: dataString,
cache: false,
success: function(html) {
$("#result").html(html).hide(); }
});
};
if(search_id!='') {
$.ajax({
type: "POST",
url: "search_database.php",
data: dataString,
cache: false,
success: function(html) {
$("#result").html(html).show(); }
});
}return false;
});
jQuery("#result").live("click",function(e){
var $clicked = $(e.target);
var $name = $clicked.find('.name').html();
var decoded = $("<div/>").html($name).text();
$('#search_id').val(decoded);
});
jQuery(document).live("click", function(e) {
var $clicked = $(e.target);
if (! $clicked.hasClass("search")){
jQuery("#result").fadeOut();
}
});
$('#search_id').click(function(){
jQuery("#result").fadeIn();
});
});
</script>
Then a search_database.php
$search = isset($_GET['filter']) ? $_GET["filter"] : 1;
echo $search; //echos "2".
if ($search=="1") {
echo $search; //enters if, and it's not supposed to, and echos "1"
Select * from table;
}
Search_database.php
$search = isset($_GET['filter']) ? $_GET["filter"] : "1";
echo $search //echos "2";
if ($search=="1") {
$q = $_POST['search'];
$q_length = strlen($q);
$sql = <<<SQL
SELECT * FROM table
LIMIT 6
SQL;
if(!$result = $con->query($sql)){
die('There was an error running the query [' . $con->error . ']');
}
while($row = $result->fetch_array()) { ?>
<div class="show_search">
<?php echo $row['name'] ?> </a>
</div>
<?php } } ?>
I'm on search.php?filter=2 and the first echo is correct ("2") but for some reason it keeps entering the If Clause and echos that $search is "1".
I'm not defining the $search variable anywhere else. Thank you for your help.
Your code is a bit too complicated.
$search = isset($_GET['filter']) ? $_GET["filter"] : 1;
if($search == 1) {
echo $search;
}
Thats enough, you don't need the check if $_POST is available. That make not so much sense because you don't send a form and you don't have post data in that case when you it with window.location.
If there is no other code between following two lines:
echo $search; //echos "2".
AND
if ($_POST AND $search=="1") { ... }
Then, its not possible to go inside if condition. its only possible if your if condition is like if($_POST AND $search=1). Check that, whether you have single = or double == in comparing $search variable.
If there is some php code in between, then show us, whatever it is, so that we can help you.

Passing data back from php to ajax

How can I pass data from a php of then rows back to ajax ?
PHP
$query = 'SELECT * FROM picture order by rand() LIMIT 10';
$result = mysql_query($query);
while ($rec = mysql_fetch_array($result, MYSQL_ASSOC)) {
$url[]=$rec['pic_location'];
$name[]=$rec['name'];
$age[]=$rec['age'];
$gender[]=$rec['gender'];
}
echo json_encode($url);
echo json_encode($name);
echo json_encode($age);
echo json_encode($gender);
Ajax
$(".goButton").click(function() {
var dir = $(this).attr("id");
var imId = $(".theImage").attr("id");
$.ajax({
url: "viewnew.php",
dataType: "json",
data: {
current_image: imId,
direction : dir
},
success: function(ret){
console.log(ret);
var arr = ret;
alert("first image url: " + arr[0][0] + ", second image url: " + arr[0][1]); // This code isnt working
alert("first image Name: " + arr[1][0] + ", second image name: " + arr[1][1]);
$(".theImage").attr("src", arr[0]);
if ('prev' == dir) {
imId ++;
} else {
imId --;
}
$("#theImage").attr("id", imId);
}
});
});
});
</script>
My question is how can I display the values here ? The Alert message is giving me "Undefined" ?
You can do something along these lines.
PHP
$query = 'SELECT * FROM picture order by rand() LIMIT 10';
$res = mysql_query($query);
$pictures = array();
while ($row = mysql_fetch_array($res)) {
$picture = array(
"pic_location" => $row['pic_location'],
"name" => $row['name'],
"age" => $row['age'],
"gender" => $row['gender']
);
$pictures[] = $picture;
}
echo json_encode($pictures);
JS
...
$.ajax({
...
dataType: "json",
...
success: function(pictures){
$.each(pictures, function(idx, picture){
// picture.pic_location
// picture.name
// picture.age
// picture.gender
});
}
});
...
You can't put multiple echo statements for the AJAX response:
echo json_encode($url);
echo json_encode($name);
echo json_encode($age);
echo json_encode($gender);
Join your arrays and send a single response:
$arr = $url + $name + $age + $gender;
echo json_encode($arr);
You can easily do this using a single Array:
$pics = array();
while ($rec = mysql_fetch_array($result, MYSQL_ASSOC)) {
$pics[$rec['id']]['url'] = $rec['pic_location'];
$pics[$rec['id']]['name']=$rec['name'];
$pics[$rec['id']]['age']=$rec['age'];
$pics[$rec['id']]['gender']=$rec['gender'];
}
echo json_encode($pics);

Categories