My PHP script queries a database and returns the rows as li elements to a div in a jQuery Dialog. It does this by building an array in the PHP while loop that processes the query row responses. Each li element has some data, an HTML button, and some javascript to execute on that li element when the button is clicked.
If I write "bad HTML" with the same id for each li element, the javascript executes, but only on the first li element. When I write "good HTML" with a unique id for each li element, I can't get the javascript to execute. I've researched and tried lots of things, but can't find anything this complicated to fix this. What should I do? Here's the stripped down code. The problem seems to be in the lengthy $error_ListActives line, but I'm open to suggestions.
$rowCount = 0;
while ($row = mysql_fetch_array($fetch)) {
$storedStreetAddress = $row["streetAddress"];
$storedCity = $row['city'];
$error_NumberOfActives = "<li>Welcome back. You have . . .</li>";
$errorMessages[0] = $error_NumberOfActives;
$idMaker = "inactive" . $rowCount;
$error_ListActives = "<li> $storedStreetAddress, $storedCity $idMaker
<button type='button' id=$idMaker onclick='makeInactive()'>Pause this</button>
<script type='text/javascript'>function makeInactive()
//do stuff
{document.getElementById($idMaker).innerHTML='Inactive Completed';}
</script> </li>";
$errorMessages[] = $error_ListActives;
$rowCount++;
}
foreach( $errorMessages as $statusMessage ) {
echo $statusMessage;
}
Please be specific, and code is helpful. I don't follow general instructions well in this area, as I'm a newbie with PHP.
You're going to end up with a lot of problems here because you are writing your javascript function inside a while loop. That means that you will get several copies of the same function, and only the last one is going to actually fire!
To fix this, write a generic javascript function for makeInactive(id) and then just call it with the id of the element you are working on.
Outside of the php loop:
<script type='text/javascript'>function makeInactive(id)
//do stuff
{document.getElementById(id).innerHTML='Inactive Completed';}
</script>
Then change the php loop to:
while ($row = mysql_fetch_array($fetch)) {
$storedStreetAddress = $row["streetAddress"];
$storedCity = $row['city'];
$error_NumberOfActives = "<li>Welcome back. You have . . .</li>";
$errorMessages[0] = $error_NumberOfActives;
$idMaker = "inactive" . $rowCount;
$error_ListActives = "<li> $storedStreetAddress, $storedCity $idMaker
<button type='button' id='$idMaker' onclick='makeInactive($idMaker)'>Pause this</button>
</li>";
$errorMessages[] = $error_ListActives;
$rowCount++;
}
Why not:
<button onClick="makeInactive(<?php echo $row['id'] ?>);">...</button>
embed the ID code as a parameter to your MakeInactive() call. Other alternatives are to simply use some DOM, e.g.
<li id="xxx"><button onclick="makeInactive(this);">...</button></li>
<script>
function makeInactive(el) {
el.getParent('li').disable(); // not real code, but shows the basic idea
}
</script>
First of all, you're creating the same exact function multiple times on your page. Your other buttons don't know which makeInactive() function to use. Why don't you give all of your buttons the same class, and then create ONE function that is included on the page that fires when the buttons are clicked.
No offense, but this is kind of bad markup here.
Related
I have something that im currently working on, however it appears that the $_GET doesn't completely work.
I have a JavaScript light box that brings up an image in a little window, this works however i can only guess that it is using the same URL over and over again.
However when i view the source for the page (and even click one of the links in the source) it will display the correct data.
But the lightbox only seems to display the first image.
This is the JavaScript
<script>
//Checkes if any key pressed. If ESC key pressed it calls the lightbox_close() function.
window.document.onkeydown = function (e)
{
if (!e){
e = event;
}
if (e.keyCode == 27){
lightbox_close();
}
}
</script>
<script>
//This script makes light and fade divs visible by setting their display properties to block.
//Also it scrolls the browser to top of the page to make sure, the popup will be on middle of the screen.
function lightbox_open(){
window.scrollTo(0,0);
document.getElementById('light').style.display='block';
document.getElementById('fade').style.display='block';
}
</script>
<script>
//This makes light and fade divs invisible by setting their display properties to none.
function lightbox_close(){
document.getElementById('light').style.display='none';
document.getElementById('fade').style.display='none';
}
</script>
I wont show the CSS i dont think thats relivant (If someone wants it then ask away)
The relevant part that creates the links is this, its part of a ForEach statement all PHP
$i = 0;
foreach ($nrows as $nrow)
{
$id = $nrow['id'];
$rid = $nrow['RaidID'];
$bid = $nrow['BossID'];
$normal = $nrow['NormalKills'];
$heroic = $nrow['HeroicKills'];
$boss = substr($nrow['BossName'], 0, 3);
$p1 = $id + $bid.".php";
$image = $boss . $p1;
#echo $image;
echo $bid;
if ($oid != $rid)
{
$i = 0;
}
if ($i == 0) {
?><td style="width: 176px;"><center><b><?php echo $nrow['raid']; ?> </b></center></td> </tr><?php
$i++;
}
?><tr><td style="width: 176px;"><div align="left"><?php echo $nrow['BossName']; ?><div id="light"><img src="bossdata/template.php?boss=<?php echo $bid;?>"></a></div><div id="fade" onClick="lightbox_close();"></div>
</div>
<?php
if ($heroic == 0)
{
if ($normal > 0)
{
echo '<img src="images/whiteskull.png" align="right" alt="Normal Kill">';
}
else
{
echo '<img src="images/redx.png" align="right" alt="Not Killed">';
}
}
else
{
echo '<img src="images/redskull.png" align="right" alt="Normal Kill">';
}
?>
</td></tr><?php
$oid = $id;
}
Now this all works, and it actually displays an image with data, however no matter what link i click the boss data is always from the first one on the list.
To me this means that the data is getting through, and reaching the the right parts on image so its "Working", but all the links do the same thing and show the same data :(
*Removed last code Bulk
You have multiple div with the same ID "light" since you create them in a foreach loop.
<div id="light">
Your function lightbox_open() opens all the divs that have id "light".
document.getElementById('light').style.display='block';
That's why you always see the first lightbox. Because the others are behind the first one.
you should try something like this :
function lightbox_open(elem){
window.scrollTo(0,0);
elem.getElementByClass('light').style.display='block';
elem.getElementByClass('fade').style.display='block';
}
And change this :
<a href="#" onclick="lightbox_open();">
By this :
<a href="#" onclick="lightbox_open(this);">
And replace id by class in your div definition :
<div class="light">
$_GET is working correctly in your code.
The issue is in the way you are combining JavaScript and PHP in the second code box. First, all of your divs have the same ID: "light" which is wrong because they all IDs are meant to be unique within the HTML document. You need to identify them uniquely, for example appending the BossID to them.
After identifying each div uniquely you'll have to edit lightbox_open and lightbox_close so they can receive the BossID of the divs that you want to show and hide.
I'm just starting out with PHP, and I am attempting to move some jQuery ajax into PHP. Here is my PHP file:
<?php
include 'config.php';
include 'opendb.php';
$query = "SELECT * FROM agency ORDER BY name";
$result = mysql_query($query);
while($row = mysql_fetch_assoc($result)){
$id = $row['id'];
$name = $row['name'];
echo "<li class=\"agency\">$name<ul class=\"agency-sub\"></ul></li>";
}
include 'closedb.php';
?>
Here is my current js function:
//Add Agency content
$("ul.top-level").on("click", "li.agency a", function (event) {
if($(this).next().length) {
var numbs = $(this).attr("href").match(/id=([0-9]+)/)[1];
showContentAgency(numbs, this);
} else {
$(this).closest('ul').find('a').removeClass('sub-active');
}
event.preventDefault();
});
And here is the showContentAgency(); function:
function showContentAgency(id, elem) {
$.post("assets/includes/contentAgency.php?id=id", {
id: id
}, function (data) {
$(elem).addClass("nav-active").parent().find("ul").html(data).show();
});
}
What I'd like to do is have PHP render the unordered list rather than have jQuery insert it. This is how it is currently featured in the above PHP file:
echo "<li class=\"agency\">$name<ul class=\"agency-sub\"></ul></li>"
So I would like the PHP to populate the <ul class="agency-sub"> list.
The structure of your code is a little bit unclear to me, but the broad outline is this: You take whatever function is generating the content in contentAgency.php and call that to get the HTML, then stick that inside when you're building up the list.
Php can not access the DOM of the page like Jquery can. If you wanted to access the DOM with Php, you would have to parse the entire web page, which is probably impractical for what you want to do. Php can only modify the page before it is loaded by the browser. If you want to run code after page load, you have to use javascript.
We might be able to help you more if you post more of your code, as we currently don't know what the page's code looks like.
Is this a list inside list?
By the way you can write php code like below, it is more readable
<?php
include 'config.php';
include 'opendb.php';
$query = "SELECT * FROM agency ORDER BY name";
$result = mysql_query($query);
while($row = mysql_fetch_assoc($result)){
$id = $row['id'];
$name = $row['name'];
echo "<li class='agency'><a href='contentAgency.php?id=$id'>$name</a><ul class='agency-sub'></ul></li>";
}
include 'closedb.php';
?>
if you are using double quotes in echo you can use single quotes inside.
I'm uncertain as to what exactly you want but it sounds like you're looking for the 'foreach' loop. When I wanna populate a list of stuff from a result set i simple use:
<ul>
<? foreach($result as $object) ?>
<li><?=$object?></li>
<? endforeach; ?>
</ul>
foreach acts a for loop but doing all the logic in the background. Hope this helps.
I want to:
Read in text line from "textfile.txt".
'echo' that line to the page in a <div> element.
Read in a text line from "namefile.txt".
Make this line become some sort of pop-up-text for that <div> element.
My script:
<? PHP
$fhtext = fopen("textfile.txt","a+") or exit("Error 1");
$fhname = fopen("namefile.txt","a+") or exit("Error 2");
while(!feof($fhtext))
{
echo "<div title="HERE IS WHERE I AM STUCK">".fgets($fhtext)."<div/><br />";
}
Could I perhaps go:
echo "<div title="<? fgets($fhname) ?>".fgets($fhtext)."<div/><br />";
?
<?php
$fhtext = fopen("textfile.txt","a+") or exit("Error 1");
$fhname = fopen("namefile.txt","a+") or exit("Error 2");
while(!feof($fhtext) && !feof($fhname))
{
echo "<div title=\"", fgets($fhname), "\">", fgets($fhtext), "<div/><br />";
}
?>
I haven't used PHP in a long time, but this should work:
echo "<div title='" . fgets($fhname) ."'>" .fgets($fhtext). "<div/><br />";
Regarding:
Make this line become some sort of pop-up-text for that '' element.
If you mean 'popup' text, as in tooltips of the type you get when you hover over links/images, this is only available on some elements when their title attribute has been set, not DIVs.
As such you can either change the DIV to a A (link) element. Or use Javascript to detect a hover over the DIV and display a popup.
If you are sure both files have the same number of lines you could use the „file“-function of PHP. This will read the file into an array and you can loop over it with a for-loop:
<?php
$file1 = file('file1');
$file2 = file('file2');
for ($i = 0, $max = count($file1); $i < $max; $i++) {
echo $file1[$i].' '.$file2[$i];
}
Before you dump your fgets() data to the browser, you really ought to HTML encode it first. That will prevent accidental (or not so accidental) problems caused by HTML fragments that might be in your text files, or if the file name can be entered by the user (either as part of the URL or as part of a form).
As a rule of thumb, always HTML encode anything coming from a data source you don't control before spitting it out to the browser. That includes form fields, etc.
Is there a way I can use Jquery to insert '' tags after every three dynamically generated table cells so that I end up with a dynamic three column table?
Please excuse my lack of knowledge, I'm literally trying to write my first jquery script ever, so I know absolutely nothing. I know php and I have a table that has a loop within it that is dynamically creating <td></td> with the information inside each tag. In other words it is dynamically creating the table cells within a static <tr></tr> tag. The problem is that it keeps outputing tables without breaking them up into rows which leaves me with a bunch of columns. I've read other articles on this but none seem to have the exact same problem as I do, and I am still struggling to understand how to write custom Jquery code.
The php code is very long and is full of numerous if statements and other functions so I'm not going to post it here but just to make it a little simpler, I made miniature mockup of what I'm trying to do.
<table id="mytable" width="266" border="1" cellspacing="10" cellpadding="10">
<tr>
<?php
$x=0;
while (have_products($x)) {
echo '<td>' . somelongassfunction() . '</td>';
$x++;
if (fmod($x,3) == 0) {
echo '</tr><tr>';
continue;
}
if ($x==20){
echo '</tr>';
}
}
function somelongassfunction(){
return 'Hello';
}
function have_products($a){
return $a<=20;
}
?>
</table>
This code loops and dynamically adds table cells up to the limit I give it which would represent my database items. Every three rows, it adds either a <tr></tr> or just a </tr> depending on whether the loop continues or not. This creates a 3 column table. I can't apply this code for my script because it is a very long and complex script that has a lot of if statements and functions. There is no way of doing it like this without breaking the code or having to rewrite everything from scratch all over again.
Is there anyway I can append the tr tags dynamically with Jquery and how would I go about to applying this to?
The jQuery approach would be to loop through all of the tabs, and add them to newly created tags, which themselves are added to the html of the table. Roughly:
var thisCount=0;
var currenttag="<tr />";
var table=$("table");
$("td").each(function ()
{
if(thiscount==2)
{
table.appendChild(currenttag);
thisCount=0;
currenttag="<tr />";
}
currenttag.appendChild(this);
}
( this is just to give an idea, not intended as a formal JQ answer. If anyone wants to edit it so it works fully, feel free ).
You can use a selector to select every third row:
$('#table_id > tr:nth-child(3n)').whatever_function()
However if you are trying to append end /tr tags, try doing it in PHP using a counter that resets itself (this code should get you started):
echo "<tr>";
$x = 0;
$y = 0;
while (have_products($x)) {
echo '<td>' . somelongassfunction() . '</td>';
$y++;
if ($y == 3) {
$y = 0;
echo "</tr><tr>";
}
$x++;
}
echo "</tr>";
I'm not a developer but I've been dabbling around with this for a while. Hope you can help
I have several div's with ID:s that are given to them dynamically through php. I have a function that is called through a checkbox which hides and shows the divs. What I want to do now is to get the div ids from the document and put them into the function.
I've kind of copied codes from different forums and it works if I'm hard coding the div names. Not sure what I'm doing now though, any help would be appreciated.
Here's what I have
Assigns id's to the divs:
$a .= "<div id='$go[media_caption]" . $i . "'>";
The function:
var editorial = [id^='editorial']);
function visiblox(arrDiv, hs) {
var disp = (hs) ? 'none' : 'block';
for(var x = 0; x < arrDiv.length; x++) {
document.getElementById(arrDiv[x]).style.display = disp;
}
}
function chk(what, item) {
if(item) {
visiblox(what, false);
} else {
visiblox(what, true);
}
}
Calls the function:
<input type='checkbox' onclick='chk(editorial, this.checked);' checked> Editorial</p>
Can you have your PHP output an array for your Javascript to use? As PHP outputs the IDs, it would also add them to a string that is in the syntax of a Javascript array. Something like this:
$a .= "<div id='$go[media_caption]" . $i . "'>";
$jsIDs .= "'$go[media_caption]',";
Then at the end of the file, just before you the PHP file closes the </body> and </html> tags, output the array as a script:
$jsIDs = substr($jsIDs, 0, strlen($jdIDs)-1); // strip off the last comma
$jsIDs = "<script type='text/javascript'>var idArr = [" . $jsIDs . "];</script>";
echo($jsIDs);
Then inside the javascript, you don't need to look up the IDs in the DOM. You can just use the array (in my example, I called it idArr).
UPDATE: Martin says the IDs output by PHP sometimes start with "editorial", some start with something else. To collect only the ones that start with "editorial", change the line above that starts with $jsIDs .= to these two lines:
if ( substr($go[media_caption], 9) == "editorial" )
$jsIDs .= "'$go[media_caption]',";
That should do the trick.