I'm fairly new to PHP and MySQL, have a little experience with jQuery and almost no experience with JSON, just to give you some background. I am trying to implement cascading dropdowns in my form.
I have two tables:
|city|
|city_id INT| - PK
|city VARCHAR (45)|
|state_state_id INT | - FK
|state|
|state_id INT| - PK
|state VARCHAR (25)|
Here's my form:
State:<br />
<select name="state" id="stateName">
<?php foreach($rows as $row): ?>
<option value="<?php echo htmlentities($row['state'],ENT_QUOTES,'UTF-8');?>"><?php echo htmlentities($row['state'],ENT_QUOTES,'UTF-8');?>
</option>
<?php endforeach; ?>
</select>
<br /><br />
City:<br />
<select name="city" id="cityName"></select>
<input type="submit" name="work_order_submit" id="" value="Add Work Order" />
I populate the State dropdown with this query:
$query = "SELECT * FROM state WHERE 1 ORDER BY state";
try{
$stmt = $db->prepare($query);
$stmt->execute();
}catch(PDOException $ex){
//On production remove getMessage.
die("Failed to run query: " . $ex->getMessage());
}
$rows = $stmt->fetchAll();
Here's the jQuery I've created to run the JSON and populate the City dropdown with the cascaded values from the state dropdown when a state is selected:
<script>
function populateCityName(){
$.getJSON('state-names.php', {stateName:$('#stateName').val()},
function(data){
var select = $('#cityName');
var options = select.prop('options');
$('option', select).remove();
$.each(data, function(index, array){
options[options.length] = new Option(array['city']);
});
});
}
$(document).ready(function(){
populateCityName();
$('#stateName').on('change', function(){
populateCityName();
});
});
</script>
And here's the code in the state-names.php file (I connect to the database before this code):
$rows = array();
if(isset($_GET['stateName'])){
$query = "SELECT city FROM city INNER JOIN state ON city.state_state_id = state.state_id WHERE state = :state ORDER BY city";
$query_params = array(":state" => $_GET['stateName']);
try{
$stmt = $pdo->prepare($query);
$stmt->execute($query_params);
}catch(PDOException $ex){
//On production remove .getMessage.
die("Failed to run query: " . $ex->getMessage());
}
$rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
}
echo json_encode($rows);
Nothing happens when I select the state in the form. I don't even get an error. I've tested the SQL and it runs fine and retrieves the values that I want, but for some reason that I can't figure out, the values aren't being cascaded into the City dropdown.
Any help is very much appreciated.
EDIT: As I'm doing more debugging and realizing a few things, this is what I've found so far. The JSON comes in like this:
[{"city":"Salt Lake City"},{"city":"Toole"},{"city":"Provo"},{"city":"St. George"}]
I now know the JSON is working correctly. When I changed the dropdown selection in the state dropdown to a state that I know had entries for the cities, the city dropdown showed blank 'option' fields for the number of entries that there actually were. So, using the answer below and MANY different tutorials on cascading dropdowns and chained dropdowns, I finally figured it out. I've submitted an answer with the working code.
Can you try:
$.each(data, function(index, array){
// new Option(text [, value, defaultSelected, selected]);
select.add(new Option(array['city'], index), null);
});
??
All of the code above worked except the jQuery function. Well, the jQuery worked for what I told it to do, not for what I really wanted the code TO DO... Big difference.
Here's the working jQuery that populates the city dropdown based on a selection made in the state dropdown:
<script>
function populateCityName(){
$.getJSON('state-names.php', {stateName: $('#stateName').val()},
function(data){
var html = '<option value="';
var htmlEnd = '</option>';
var options = '';
var select = $('#cityName');
$('option', select).remove();
$.each(data, function(index, array){
options += html + array['city'] + '">' + array['city'] + htmlEnd;
});
$('#cityName').append(options);
});
}
$(document).ready(function(){
populateCityName();
$('#stateName').on('change', function(){
populateCityName();
});
});
</script>
Before, the code would find the number of entries and the select box would show this number, but the selections were blank. With this code, the number of entries is found, but the values for those entries also show. Hope this helps someone else later.
Related
So I'm having this issue with geting a value from a dropdown list in HTML into a variable so that I can do the mysql query. This will be a little tricky to explain but I will do my best. (Do not be shy in correcting my english or my expressions so that the question becomes more concrete and easy to understand).
So I have this dropdown list that gets his values from a mysql query.
<td>Designação atual :</td> <td><select name="desig_act" id="desig_act">
<?php
while ($row2 = mysql_fetch_assoc($result4)) {
echo "<option size=30 value=".$row2['new_name_freg'].">".$row2["new_name_freg"]."</option>";
}
?>
</select>
This "connects" with this query:
$sql4 = ("SELECT DISTINCT new_name_freg FROM freguesias WHERE codg_cc = '$pesq'");
$result4 = mysql_query($sql4, $link);
This query will populate the dropdown list with values. What I'm seeking to do is to populate another dropdown list. For examples I select a list of countrys, and when I select on country it should appear all it's citys in the other dropdown list.
I have been searching guys. Belive me I have.
P.s: Please do not get mad if I change the question a couple of times when I see that you guys show me a way to explain it better. Sorry if my english isn't perfect. Thank you guys for the help.
You can do it with ajax and jquery. I try to write little example
<!-- index.php -->
<select name="desig_act" id="desig_act">
<?php while ($row2 = mysql_fetch_assoc($result4)): ?>
<option value="<?=$row2['new_name_freg']?>">
<?=$row2["new_name_freg"]?>
</option>
<?php endwhile; ?>
</select>
<!-- select tag for countries -->
<select name="country" id="country"></select>
write a little script to return countries as json
<?php //ajax-countries.php
$link = mysql_connect(); // connect as usual
$query = ("SELECT * FROM countries");
$result = mysql_query($query, $link);
$json = array();
while ($row = mysql_fetch_assoc($result)) $json[] = $row;
echo json_encode($json);
?>
Then you can have some sort of script like:
// script.js
$("#desig_act").change(function(){
$.getJSON( "ajax-countries.php", function( data ) {
$.each( data, function(key, val) {
$("#desig_act").append("<option val='" + key + "'>" + val + "</option>");
});
});
I hope it can be useful
1: Create a PHP script to return the data
Essentially just generate the value based off the $_GET input.
2: Create a json request in jquery
Calls the PHP file which will return the data and you will use that data to add more values to the select.
<?php
//Step 1 - The posted ajax data that will return our json request.
if(isset($_GET['fetchrow'])) //Is our ajax request called on page load? If yes, go to this code block
{
//Other stuff like DB connection
$pesq = mysql_escape_string($_GET['fetchrow']); //Put our variable as the variable sent through ajax
$sql4 = ("SELECT DISTINCT new_name_freg FROM freguesias WHERE codg_cc = '$pesq'"); //Run our query
$result4 = mysql_query($sql4, $link); //Please change from mysql_* to mysqli
$data = array(); //The array in which the data is in
while($row = mysql_fetch_assoc($result4)) //Look through all rows
{
array_push($data, $row); //Put the data into the array
}
echo json_encode($data); //Send all the data to our ajax request in json format.
die; //Don't show any more of the page if ajax request.
}
?>
<html>
<head>
<script type='application/javascript' src='https://cdnjs.cloudflare.com/ajax/libs/jquery/3.0.0-alpha1/jquery.min.js'></script> <!--Include jquery -->
<script>
//Step #2:
//The jquery script calls ajax request on change of the first select
$( "#desig_act" ).change(function() {
$.getJSON('thisfilename.php', {fetchrow:$("#desig_act").val()}, function(data){ //Get the json data from the script above
var html = '';
var len = data.length;
for (var i = 0; i< len; i++) { //Loop through all results
html += '<option value="' + data[i].new_name_freg + '">' + data[i].new_name_freg + '</option>'; // Add data to string for each row
}
$('#otherselect').html(html); //Add data to the select.
});
});
</script>
</head>
<body>
<!-- Your html code -->
<td>Designação atual :</td> <td><select name="desig_act" id="desig_act">
<?php
while ($row2 = mysql_fetch_assoc($result4)) {
echo "<option size=30 value=".$row2['new_name_freg'].">".$row2["new_name_freg"]."</option>";
}
?>
</select>
</td>
<!-- The new select -->
<select name='otherselect' id='otherselect'>
</select>
<!-- Rest of html code -->
</body>
</html>
I have a form where in one table row a dropdown state field is there and in another tr another dropdown is there for selecting city, I need that before submitting the form when user selects a state from dropdown list automatically the city dropdown should fetch and display only those city from the selected state.
I don't want to use AJAX but want to do it with jquery.
Backend database has two tables one is state with two fields id and state, second is city table having 3 fields id, state and city where state is my foreign key.
How can I do it with jquery any help regarding this will be appreciated since I am a newbie, please help
If you don't want to use ajax you can always preload the full list of states with cities into a javascript object and call it from there.
Example:
<select id="stateDrop">
<option value="state1">State 1</option>
<option value="state2">State 2</option>
</select>
<select id="cityDrop"></select>
<script>
var cities = {'state1':['city_one', 'city_two', 'city_three'], 'state2':['city_four', 'city_five', 'city_six']};
$('#stateDrop').on('change', function(){
var cityList = cities[$(this).val()];
console.log(cityList);
var output = '';
$(cityList).each(function(k, v){
output += '<option value="'+v+'">'+v+'</option>';
});
$('#cityDrop').html(output);
});
</script>
Fiddle
If you want to avoid using an ajax call, you will need to build a mapping from state-id's to lists of cities. Then bind a function to the change event of the state select-element, and populate the city select-element with the values.
Assuming State ID 0 has the cities A and B, with city id's 0 and 1:
var map = [[{id:0,name:"A"},{id:1,name:"B"}]]
$("#states").on("change",function() {
var cities = map[$(this).val()];
$("#cities option").remove(); //remove previous options
$.each(cities, function(i,e) {
$("#cities").append('<option value="'+e.id+'">'+e.name+'</option>');
});
});
Example: http://jsfiddle.net/HQLQU/
The php/mysql part for building the JS-map could be something like this (untested!):
$query = "SELECT city_id, city_name, state_id FROM cities";
$result = mysql_query($query); //or preferably use a more modern extension
$cities = array();
foreach (mysql_fetch_assoc($result) as $row) {
$cities[$row['state_id']][] = array("id"=>$row['city_id'],"name"=>$row['city_name']);
}
echo "var map = " . json_encode($cities);
I'm trying to figure out a couple things here and seem to be pretty close but hit a road block. My issue is, after I select a dropdown option (used to filter a large number of results), the results which should be available when I start typing in the autocomplete box are not available. If I hardcode a value that the dropdown is passing and start typing in the autocomplete box, everything works fine. It's only when I pass in that value that I am having the issue.
I have two PHP pages, one containing the layout which includes a dropdown (SQL for its results) and an autocomplete box and the other which contains the SQL for the autocomplete.
search.php
<select id="loc">
<?php
// sql for dropdown
while ($row = odbc_fetch_array($result)) {
echo "<option value\"".$row['Location']"\">".$row['Description']."</option>";
}
?>
</select>
<label for="search">Search: </label>
<input type="text" id="search" />
<script>
// Send value entered in the autocomplete box to data.php for it to be used in sql statement
$(document).ready(function(){
$('#search').autocomplete({
minLength: 3,
source: function(query, process) {
$.ajax({
url: 'data.php',
type: 'GET',
data: "name=" + $('#search').val(),
dataType: 'JSON',
async: true,
success: function(data) {
process(data);
}
});
}
});
});
// Append selected dropdown value to URL so it can be accessed
$(document).ready(function() {
$('#search').change(function() {
var res = $(this).val();
location.href = "search.php?src="+res;
});
});
</script>
data.php
<?php
if (isset($_GET['src'])) {
$loc = $_GET['src'];
$fullname = explode(" ", $_GET['name']);
$sql = "SELECT p.lastname + ', ' + p.firstname as fullname,
l.city as city
FROM people p
JOIN location l on p.city = l.city
WHERE p.lastname like '".$fullname[1]."%' AND p.firstname like '".$fullname[0]."%'
AND l.city = '$loc'
GROUP BY p.lastname + ', ' + p.firstname, l.city
ORDER BY p.lastname + ', ' + p.firstname";
// DB connection and execute connection here
$array = array();
while ($row = odbc_fetch_array($db)) {
$array[] = $row['fullname'];
}
echo json_encode($array);
}
?>
So when I have my code like this and select an option from the dropdown, it runs through the select statement since the selected value is being passed in. If I echo the results on the search.php page, they are filtered correctly or if I navigate directly to the data.php page and pass in the correct parameters everything is correct. After I make a selection though, and start typing in the autocomplete box, I'm not getting any results. I'm guessing I need to somehow filter the results based on the selection, get those results and run a different query when I start typing?
Thanks in advance for any help and please let me know if I'm not clear on anything.
Well just like it ususally happens, after taking a break from it I've got it working now.
Below is the revised code with comments showing what I changed.
search.php
<select id="loc">
<?php
// sql for dropdown
while ($row = odbc_fetch_array($result)) {
echo "<option value\"".$row['Location']"\">".$row['Description']."</option>";
}
?>
</select>
<label for="search">Search: </label>
<input type="text" id="search" />
<script>
/* Send value entered in the autocomplete box to data.php
* for it to be used in sql statement */
$(document).ready(function(){
$('#search').autocomplete({
minLength: 3,
source: function(query, process) {
// Added the variable below to get the dropdown's selected value
var res = $('#loc').val();
$.ajax({
url: 'data.php',
type: 'GET',
// Edited: included the dropdown value
data: "src="+res + "&name=" + $('#search').val(),
dataType: 'JSON',
async: true,
success: function(data) {
process(data);
}
});
}
});
});
/* This event is not needed since the value is set when a selection
* is made. 'change' passed that value to search.php causing
* the query to run without the search value. This caused a HUGE
* number of results, and usually causing the page to timeout.
* Making sure all variables get passed prior to running the query
* is a must. I knew this but got stuck on how to make it work. */
// Append selected dropdown value to URL so it can be accessed
//$(document).ready(function() {
// $('#search').change(function() {
// var res = $(this).val();
// location.href = "search.php?src="+res;
// });
//});
</script>
data.php
<?php
if (isset($_GET['src'])) {
$loc = $_GET['src'];
}
// Moved the $loc variable into the if statement above
// $loc = $_GET['src'];
$fullname = explode(" ", $_GET['name']);
$sql = "SELECT p.lastname + ', ' + p.firstname as fullname,
l.city as city
FROM people p
JOIN location l on p.city = l.city
WHERE p.lastname like '".$fullname[1]."%'
AND p.firstname like '".$fullname[0]."%'
AND l.city = '$loc'
GROUP BY p.lastname + ', ' + p.firstname, l.city
ORDER BY p.lastname + ', ' + p.firstname";
// DB connection and execute connection here
$array = array();
while ($row = odbc_fetch_array($db)) {
$array[] = $row['fullname'];
}
echo json_encode($array);
?>
I haven't finished a couple pieces on the main page such as disabling/hiding the autocomplete box until a selection is made from the dropdown and adjusting the query for additional filtering but those are next on my list. I'm sure there are a few other things I could clean up as well but my first goal was to get it working correctly and that's accomplished now!
If anyone is using php and has a few hundred thousand + results and would like to use an autocomplete box to filter those without waiting a ridiculous amount of time for the results to display, I hope this may be of some help. Not nearly as complex as I originally made it out to be but over thinking it will do that to you. Also, even though it's working now, feel free to add some suggestions and apologies for any grammatical errors!
<?php
$sql = "SELECT `docid`, `fullname` FROM `doctors` ORDER BY fullname ASC";
$result = $database->query($sql) or die('cannot connect to the database');
while($row = mysql_fetch_array($result))
{
echo"<option value= ".$row['docid'].">".$row['fullname']."</option>";
}
?>
This is my select box which i am populating through datbase table.
$('.sheUpdate').click(function(){
var deptment = $(this).attr('dptname');
var deptid = $(this).attr('dptid');
i want to make this one as SELECTED ITEM ON THE Select box
$("#Deptmentselectbox").prepend('<option value='+deptid+'>'+deptment+'</option>')
});
This is my jquery code. When i click ".sheUpdate" link i have couple of values that i am grabing using attr function. i am grabing depatment name and department value which i want to show as the SELECTED ITEM ON THE SELECT BOX
I think we need to see more code to be able to properly help. What is the html code of the element with the .sheUpdate class?
Does this link element actually have attributes dptname and dptid?
What is the code you use on #Deptmentselectbox?
The code you added is working properly.
just need to set the new added element as selected.
please check this fiddle
Also please let me know what value you get if you write this
alert($(this).attr('dptname'));
alert($(this).attr('dptid'));
$('.sheUpdate').click(function(){
var deptment = $(this).attr('dptname');
var deptid = $(this).attr('dptid');
$("#Deptmentselectbox").prepend('<option value='+deptid+'>'+deptment+'</option>')
$("#Deptmentselectbox").get(0).selectedIndex = 0;
// OR $("#Deptmentselectbox").val(deptid);
});
Assuming that your initial select box is like this:
<select id="Deptmentselectbox">
<option value=''> Select a department </option>
</select>
To remove the placeholder on first option selected:
$('.sheUpdate').click(function(){
var deptment = $(this).attr('dptname');
var deptid = $(this).attr('dptid');
if($("#Deptmentselectbox").val() == '')
$("#Deptmentselectbox").html('<option value='+deptid+'>'+deptment+'</option>');
else
$("#Deptmentselectbox").prepend('<option value='+deptid+'>'+deptment+'</option>');
$("#Deptmentselectbox").val(deptid);
}
Here is a Solution Hope it Helps
$(document).ready(function(){
$("#test1").click(function(){
var data = $("#t").val();
var data1 = $("#r").val();
$("#try").prepend('<option value='+data+' selected="selected">'+data1+'</option>');
});
});
Click Here For Demo
I have 2 tables, Provinces and Districts. I would like to populate a select field with options as District names based on which Province is chosen in another select. The Districts table has a ProvinceID field to reference which Province it belongs to. I know this is doable, I just can't figure it out. I also want to create and update the new Districts select without refreshing the page.
UPDATE: I'm writing it in PHP and MySQL, using jQuery as sparingly as possible.
In order to do it without AJAX, prepopulate a Javascript dataset... warning, if you have a lot of data this could be slow, but if it's a manageable list length, you could save some overhead from multiple AJAX requests loading the same data over and over.
var provinces = {};
provinces['province_a_id'] = [
{ name:'District A', id:'district_a_id' },
{ name:'District B', id:'district_b_id' }
];
provinces['province_b_id'] = [
{ name:'District C', id:'district_c_id' },
{ name:'District D', id:'district_d_id' }
];
function getDistricts( referenced_select ) {
var selected_province = $(referenced_select).val();
var district_select = $('#districts');
district_select.empty();
if ( provinces[selected_province] ) {
$.each( provinces[selected_province], function(i,v) {
district_select.append( $('<option value="' + v['id'] + '">').text( v['name'] ) );
} );
}
}
$(document).ready( function() {
$('#provinces').bind( 'change', function() {
getDistricts(this);
} );
} );
-- HTML
<select id="provinces" name="provinces">
<option value="province_a_id">Province A</option>
<option value="province_b_id">Province B</option>
</select>
<select id="districts" name="districts">
</select>
Make a php script and call it dp.php ( dp, short for data_provider, use any name you like). In dp.php
// get province id passed in via `post` or `get`
$pid = $_REQUEST['pid'];
// get the districts in that province
$query = "SELECT `district_id`, `district` FROM `districts` WHERE province_id` ='$pid'";
// link to your database
$link = mysqli_connect(HOST, USER, PASS, DBNAME);
// execute your query
$result = mysqli_query($link, $query);
// parse the options
while($row = mysqli_fetch_assoc($result)) {
$options .= '<option value="' . row['district_id'] . '">' . $row['district'] . "</option>\n";
}
// send options
echo $options
With the following markup in your page:
<select id="province" name="province">
<option value="ny">New York</option>
...
</select>
<select id="district" name="district">
</select>
Include the following jQuery:
// whenever a different province is selected
$('#province').change(function() {
// remove all options in district select
$('#district').html('');
// find the new province selected
var my_province = $('#province').val();
// get new options from server and put them in your district select
$('#district').get('path/to/dp.php?pid=' + my_province);
)};
You didn't state what server side technology you are using (if any). Here's an example in ASP.net - it should point you in the right direction:
http://www.mikesdotnetting.com/Article/97/Cascading-DropDownLists-with-jQuery-and-ASP.NET
I actually figured this out on my own using jQuery and post. On the primary select, I added onchange="getDistricts()" and used this for that function:
function getDistricts()
{
var province_id = $("#provinces").val();
$.post("handler.php",
{
"mode" : "get_districts",
"pid" : province_id
},
function(data)
{
$("#districts").html(data);
}, "text");
}
And then in handler.php, I have a case that catches the mode, and runs the following code:
<query on districts table>
while($row = $sql->fetchrow($result);
{
$id = $row['id'];
$name = $row['name'];
$html .= "<option value='$id' id='$id'>$name</option>";
}
echo $html;
I'm not a fan of this solution, and would really like something better, but it does what I need it to do for the moment. I hope this can help someone else out.