I'm creating a webpage that lists ten characters in a game based on their experience levels and displays them with a picture associated each character. My code works, but the output is in a column when I'd like it to be in a row. I did see where something very similar had been asked here: MySQL data from database align horizontally and I tried to follow that example but either ended up with errors or the faces didn't appear. I'm a hobbyist, I'm just doing this for friends, so my knowledge is pretty basic.
Relevant code:
<table border="3" width="90%">
<tr>
<th width="25%">XP</th>
<td>
<?php
$resultgood = mysqli_query($con,"SELECT * FROM Life WHERE goodxp > 0 ORDER BY goodxp DESC LIMIT 10");
while($row = mysqli_fetch_array($resultgood))
{
$face = mysqli_query($con,"SELECT face FROM Description WHERE charname='$row[charname]'");
$row = mysqli_fetch_row($face);
$face = $row[0];
$name = mysqli_query($con,"SELECT charname FROM Life WHERE charname='$row[charname]'");
$row = mysqli_fetch_row($name);
$name = $row[0];
echo "<left>";
echo "<table border='1'>";
echo "<tr><td>";
echo "<img src='pictures/$face' alt='$name' border='2'>";
echo "</td></tr>";
echo "</table>";
echo "<br>";
}
?>
</td>
</tr>
</table>
Anyone got any suggestions? Thanks!
So after following Bombelman's suggestion below, I got it to work. In case anyone else runs into this problem, here is the working code:
<tr>
<th width="25%">Goody Two Shoes</th>
<td><?php
echo "<table border='1'><tr>";
echo "<left>";
$resultgood = mysqli_query($con,"SELECT * FROM Life WHERE goodxp > 0 ORDER BY goodxp DESC LIMIT 10");
while($row = mysqli_fetch_array($resultgood))
{
$face = mysqli_query($con,"SELECT face FROM Description WHERE charname='$row[charname]'");
$row = mysqli_fetch_row($face);
$face = $row[0];
$name = mysqli_query($con,"SELECT charname FROM Life WHERE charname='$row[charname]'");
$row = mysqli_fetch_row($name);
$name = $row[0];
echo "<td>";
echo "<img src='pictures/$face' alt='$name' border='2'>";
echo "</td>";
}
echo "</tr>";
echo "</table>";
?></td>
</tr>
place the "table" and "row" tag out of the loop, and have the results in between the "td" tags looped only.
Looking at your script, you have several tables.
Make sure only the < td > and < /td > tags are within the while-loop.
The output should be similar to my example.
Hope it helps !
<table style="width:100%">
<tr>
<td>Character 1</td>
<td>Character 2</td>
<td>Character 3</td>
<td>Character 4</td>
<td>Character 5</td>
</tr>
</table>
Looking at the sql queries makes me think you ought to be able to do a basic join upon the two tables rather than having nested queries within a loop. The generation of the html table should be fairly straightforward - iterate through the recordset results for rows in the table and iterate through the fields returned by the query for individual cells within the table row.
$sql='select l.*, d.face from `life` l
join `description` d on d.`charname`=l.`charname`
where l.`goodxp` > 0
order by l.`goodxp` desc
limit 10';
$res=$con->query( $sql );
/* fetch the column names into an array */
$fields=array();
array_walk( $res->fetch_fields(),function( $item, $key, $fields ){
$fields[]=$item->name;
},&$fields );
$html=array();
$html[]='<table>';
/* add field names as column headers */
$html[]='<tr>';
foreach( $fields as $field )$html[]='<th>'.$field.'</th>';
$html[]='</tr>';
/*
iterate through recordset,
add new row for every record
but table cell for every
field in record
*/
while( $rs=$res->fetch_object() ){
$html[]='<tr>';
foreach( $fields as $field ){/* show image or text */
$data = $field=='face' ? "<img src='pictures/{$rs->$field}' />" : $rs->$field;
$html[]='<td>'.$data.'</td>';
}
$html[]='</tr>';
}
$html[]='</table>';
/* render table */
echo implode( PHP_EOL, $html );
Depending upon the version of PHP you may get nagged at when using the array_walk function and passing the third argument by reference. If that is the case then change
$fields=array();
array_walk( $res->fetch_fields(),function( $item, $key, $fields ){
$fields[]=$item->name;
},&$fields );
for
$fields=array();
array_walk( $res->fetch_fields(),function( $item, $key ){
global $fields;
$fields[]=$item->name;
} );
Related
I have the 2020 hurricane name and all the states. I want to loop through my database and see if the options are picked. If they are, populate the spot with the name. If not, add"--". It will look almost like a spreadsheet of data.
When I submit data, it doesn't populate in the right spot and add a bunch of empty cells.
This is my queries:
// DB Connection
$db_connection = mysqli_connect('localhost','root','','hurricane_bowl');
$i = "SELECT * FROM users RIGHT JOIN states USING (state_id) GROUP BY (state_name) ORDER BY state_name ASC";
$state = mysqli_query($db_connection, $i);
$g = "SELECT * FROM users RIGHT JOIN hurricanes USING (hurricane_id) GROUP BY (hurricane_name) ORDER BY hurricane_name ASC";
$hurricane = mysqli_query($db_connection, $g);
This is my loops:
<table class="table table-striped table-bordered">
<thead>
<tr>
<th scope="col">Hurricane Name</th>
<?php
foreach($state as $stval) {
echo '<th scope="col">' . $stval['state_name'] . '</th>';
}
?>
</tr>
</thead>
<tbody>
<?php
foreach($hurricane as $h) {
echo '<tr>';
echo '<th scope="row">' . $h['hurricane_name'] . '</th>';
foreach($state as $st) {
if($st['state_id'] != NULL && $h['hurricane_id'] != NULL) {
echo '<td>' . $st['username'] . '</td>';
} else {
echo '<td>--</td>';
}
}
echo '</tr>';
}
?>
</tbody>
</table>
The first change needs to be to the queries: if you want to display three separate query results, you need three separate tables, otherwise it makes not sense because there is no connection between the three datasets you are retrieving. Alternatively, you need just one dataset. Use JOIN in a query to link multiple table results, assuming there is a link between the tables.
W3Schools on this topic: https://www.w3schools.com/sql/sql_join.asp
Secondly, when loops are nested, each layer is its own dimension. In your case, you are trying to create a sort of 3-dimensional table, which can't work. Typically for a query result you only need one foreach loop, but if you don't have any information on the table fields, you can have two, not more.
I'm making a sports solution to retrieve data from play by play to webpage.
And now I am stuck with a moment to retrieve player name from mysql db, put to boxscore table (that was done), and then retrieve all stats based on this name.
As example - how many points he made, how many assists were associated with his name, etc.
At the end I want to get this kind of table (all formating /styling done and ready):
Here is a php code, question based in the "echo" point.
I cant finnd proper way to count how many assists a.e. player made in the same request.
<?php
require "connection.php";
$game_id = 1760;
$player = 'KURBANOV, NIKITA';
$team = 'CSKA Moscow';
$stmt = $pdo->prepare('SELECT * FROM game_results WHERE game_id = :game_id AND team = :team AND action = "Assist" ORDER BY player DESC');
$stmt->execute(array('game_id' => $game_id, 'team' => $team ));
$result = $stmt -> fetchAll();
echo '<table class="table table-condensed table-hover"><tbody>';
echo '<thead>
<tr>
<th>Name</th>
<th>POS</th>
<th>MIN</th>
<th>PTS</th>
<th>OREB</th>
<th>DREB</th>
<th>TREB</th>
<th>AST</th>
<th>STL</th>
<th>TOV</th>
<th>Fm</th>
<th>Fc</th>
</tr>
</thead>';
foreach( $result as $row ) {
echo '<tr>';
echo '<td>'.$row['player'].'</td>';
echo '<td>'.$row['action'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '<td>'.$row['game_id'].'</td>';
echo '</tr>';
}
echo '</tbody></table>';
Here is the db data example:
DB example
Ok after your edit I think I guessed what you want to do.
You want to count how many entrys you have in your table of a specific player and a specific action.
SELECT player,
Count(CASE action
WHEN 'Assist' THEN 1
ELSE 0
end) AS assists,
Count(CASE action
WHEN '<other case>' THEN 1
ELSE 0
end) AS other_case
FROM `game_results`
WHERE 1
GROUP BY player
This above SQL Select should do what you want, replace other case with what ever you else have.
EDIT:
You should be able to print it out just like you did before:
<?php
// your other code ...
echo '<table class="table table-condensed table-hover"><tbody>';
echo '<thead>
<tr>
<th>Name</th>
<th>assists</th>
<th>other case</th>
</tr>
</thead>';
foreach( $result as $row ) {
echo '<tr>';
echo '<td>'.$row['player'].'</td>';
echo '<td>'.$row['assits'].'</td>';
echo '<td>'.$row['other_case'].'</td>';
echo '</tr>';
}
echo '</tbody></table>';
I have a webpage that displays cars from the first car in the table to the last car with a while loop.
I have the following columns: Make, Model, Price. In my syntax I have an anchor tag around the Make rows that links to the description page of the Make you click on.
I want my <h> tags to change to the Model of the corresponding Make.
I've spent over an hour trying to achieve this but all I could come up with is this:
<?php
$query = "SELECT Model FROM inventory;";
$Vtitle = $conn->query($query);
$Vtitle_ar = mysqli_fetch_assoc($Vtitle);
echo "<h1>".$Vtitle_ar['Model']."</h1>";
?>
This works to an extent.
Every anchor I click replaces the <h> tags with only the first result under the Model column in my database.
Here is my code for the the entire car inventory page
<?php
$query = "SELECT * FROM inventory;";
/* Try to query the database */
if ($result = $conn->query($query)) {
// Don't do anything if successful.
}
else {
echo "Error getting cars from database:" .$conn->error()."<br>";
}
// Create the table headers
echo "<table id='Grid' style='width: 80%'><tr>";
echo "<th style='width: 50px'>Make</th>";
echo "<th style='width: 50px'>Model</th>";
echo "<th style='width: 50px'>Asking Price</th>";
echo "</tr>\n";
$class = "odd"; // keep track of whether a row was even or odd, so we can style it later
// Loop through all the rows returned by the query, creating a table for each row
while ($result_ar = mysqli_fetch_assoc($result)) {
echo "<tr class=\"$class\">";
echo "<td><a href='viewcar.php?VIN=".$result_ar['VIN']."'>".$result_ar['Make']."<a></td>";
echo "<td>".$result_ar['Model']."</td>";
echo "<td>".$result_ar['ASKING_PRICE']."</td>";
echo "</td></tr>\n";
// if the last row was even, make the next one odd and vice-versa
if ($class=="odd") {
$class = "even";
}
else {
$class = "odd";
}
}
echo "</table>";
$conn->close();
?>
Does anyone how I can do this?
I'm new to programming and I'm trying to use this for an actual project I'm working on for a hair salon's website
Add a WHERE clause to the query.
$vin = $_GET['VIN'];
$stmt = $conn->prepare("SELECT Model FROM inventory WHERE VIN = ?");
$stmt->bind_param("s", $vin);
$stmt->execute();
$stmt->bind_result($model);
$stmt->fetch();
echo "<h1>$model</h1>";
Though not a solution resolved with the use of a where clause as given by #Barmar whilst formatting the code I did find an error within the HTML which was not immediately obvious
The line echo "</td></tr>\n"; has an extra </td> which would break the flow of the html and can have detrimental effects. Also, // Don't do anything if successful. makes no sense - if there are results then process the recordset otherwise show the error ;-)
<?php
$query = "SELECT * FROM inventory;";
if ( $result = $conn->query( $query ) ) {
echo "
<table id='Grid' style='width: 80%'>
<tr>
<th style='width: 50px'>Make</th>
<th style='width: 50px'>Model</th>
<th style='width: 50px'>Asking Price</th>
</tr>";
$i=0;
while( $result_ar = mysqli_fetch_assoc( $result ) ) {
$class = $i %2 == 0 ? 'even' : 'odd';
echo "
<tr class='$class'>
<td><a href='viewcar.php?VIN={$result_ar['VIN']}'>{$result_ar['Make']}<a></td>
<td>{$result_ar['Model']}</td>
<td>{$result_ar['ASKING_PRICE']}</td>
</tr>";
$i++;
}
echo "</table>";
} else {
echo "Error getting cars from database:" .$conn->error()."<br>";
}
$conn->close();
?>
For styling alternate table rows ( the above uses a modulus function to calculate odd/even ) you can do it with some simple CSS - such as
tr:nth-child( odd ){/* rules */}
How can I make a select in database and display that row in a table with 2 columns.
Here is my select
$query="select Interval from Interval_Orar";
$result=mysqli_query($dbc,$query) or die("query failed: " . mysqli_error($dbc));
echo '<table>';
while ($row=mysqli_fetch_array($result))
{
echo'
<tr>
<td>'.$row['Interval'].'</td>
</tr>';
}
echo '</table>';
what i what to display is a table like this
<tr>
<td>Interval 1</td>
<td>Interval 2</td>
</tr>
<tr>
<td>Interval 3</td>
<td>Interval 4</td>
</tr>
<tr>
<td>Interval 5</td>
<td>Interval 6</td>
</tr>
what i dont know to make is to put that 2 by 2 select in the while
You could just do another mysqli_fetch_array in the loop, check if there was a result
and display either an empty cell or one with the content.
Then at the end of the loop you only need to check if the second mysqli_fetch_array had a result. (The empty cell is optional, it depends if you require it e.g. for styling, add not value or other things)
while ($row=mysqli_fetch_array($result))
{
echo'<tr>';
echo '<td>'.$row['Interval'].'</td>';
$row=mysqli_fetch_array($result);
if( $row ) {
echo '<td>'.$row['Interval'].'</td>';
} else {
echo '<td></td>';
}
echo '</tr>';
if( !$row ) {
break;
}
}
Another way would be to use a $counter and a $counter%2 to check in which column the result should be displayed and if an <tr> or </tr> needs to be added, but that would require more work.
EDIT
This is not tested as I neither have php not a mysql setup server right here, but making a function out of it would allow you to re use it with any column count:
function createRows( $result, $columns ) {
if( $columns <= 0 ) {
return;
}
$row = true; //initialize it with true so that the first mysqli_fetch_array will be called
while($row !== null ) {
echo'<tr>';
for( $i=0 ; $i<columns ; $i++ ) {
if( $row !== null && $row=mysqli_fetch_array($result) ) {
echo '<td>'.$row['Interval'].'</td>';
} else {
echo '<td></td>';
}
}
echo '</tr>';
}
}
Dump your entire result set into an array so you can manually move the pointer.
The inside your loop it would be (in plain English)
column1 = row1
column2 = row1+1
row = row + 1
repeat.
I want to show the query results of mysql query in a table,
There are two tables, and some information has to be retrieved from the second table
I want to retrieve title, borrower name and borrower surname from other tables,
I tried to retrieve title, but I was unsuccessful,
Then I want to retrieve the borrower name and borrower surname from the users table
You may also offer a new way to put the results into a table
Here is the code
for($i=0;$i<999999999;$i++){
$sql="SELECT * FROM products WHERE product_id='$i' LIMIT 1";
//echo $sql;
$moviename="SELECT dbid FROM products WHERE product_id='$i'";
$dbid=mysql_query($moviename);
$movname="SELECT title FROM titles WHERE dbid='$dbid' ";
$name=mysql_query($movname);
$title=mysql_fetch_array($name);
print "<table border=1>
<tr><th>Product_ID</th>
<th>dbid</th>
<th>Title</th>
<th>Status</th>
<th>Date</th>
<th>Borrowe_id</th>
<th>Borrower Name</th>
<th>Borrower Surname</th></tr>";
$result=mysql_query($sql);
if($result==NULL){
continue ;
}
while ($row = mysql_fetch_array($result))
{
print "<tr><td>{$row[1]}</td>
<td>{$row[2]}</td>
<td>{$title[0]}</td>
<td>{$row[12]}</td>
<td>{$row[13]}</td>
<td>{$row[14]}</td>
<td>{$borrowername[0]}</td>
<td>{$borrowesurname[0]}</td></tr>";
}
print "</table>";
}
?>
There are a few things going on here which you should definitely not be doing.
Super insane loop with a query inside
for($i=0;$i<999999999;$i++){
// SELECT STATEMENT HERE!
}
Why are you looping potentially 999,999,999 times? And if you do you are going to hit your database 999,999,999 times? That is going to kill your database and it can be done much more efficiently.
Use joins over individual selects
$sql="SELECT * FROM products WHERE product_id='$i' LIMIT 1";
$moviename="SELECT dbid FROM products WHERE product_id='$i'";
$movname="SELECT title FROM titles WHERE dbid='$dbid' ";
Note:
product_id='$i' LIMIT 1
Usually you want your ids to be unique. Why do you need to LIMIT your query?
The query can be simplified to:
select
*
from
products p
left outer join titles t
on p.dbid = t.dbid
Note: SELECTING * IS BAD PRACTICE, BUT I DON'T KNOW WHAT YOUR STRUCT IS
Illogical logic
if($result==NULL){
continue ;
}
while ($row = mysql_fetch_array($result)) {...}
$result is null at this point, so your while loop will never happen.
So after killing that loop, simplifying the query, and revising logic... we can do:
$result_resource = mysql_query($sql);
echo"
<table border=1>
<tr>
<th>Product_ID</th>
<th>dbid</th>
<th> Title</th>
<th>Status</th>
<th>Date</th>
<th>Borrowe_id</th>
<th>Borrower Name</th>
<th>Borrower Surname</th>
</tr>";
while ($row = mysql_fetch_array($result_resource))
{
echo "
<tr>
<td>{$row['ProductID']}</td>
<td>{$row['dbid']}</td>
<td>{$row['Title']}</td>
<td>{$row['Status']}</td>
<td>{$row['Date']}</td>
<td>{$row['Borrowe_id']}</td>
<td>{$borrowername[0]}</td>
<td>{$borrowesurname[0]}</td>
</tr>";
}
echo "</table>";
Looking at $borrower.... I have a feeling you can also join your borrow table to the query to bring that in too.
I would also look into templating. It would definitely separate your data from your display and make your code a lot easier to read.
First,you should debug your code
one thing that pops up is the following error:
you should change the following from:
print "<tr><td>{$row[1]}</td>
<td>{$row[2]}</td> ..."
to:
print "<tr><td>{" . $row[1] . "}</td>
<td>{" . $row[2] . "}</td> ..."
Second, when you say " I was unsuccessful" - please add details, did you get an error ? what was the output ?
(Maybe your question is "too localize")
First I don't recommend this :
for($i=0;$i<999999999;$i++)
because it will take long for the server to compute, and generate a lot of mysql query.
Second, most (all?) of your mysql queries could be merge in only one query.
You can about query on more then one table here (dev.mysql.com) There's several way to join multiples tables, you could read about it
Third, in your code the table header will be repeated each time, because it's in your For loop.
here my suggest to improve your code :
//Print the header
print "<table border=1>
<tr><th>Product_ID</th>
<th>dbid</th>
<th>Title</th>
<th>Status</th>
<th>Date</th>
<th>Borrowe_id</th>
<th>Borrower Name</th>
<th>Borrower Surname</th></tr>";
//adapt the following sql with your tables name / fields
$sql="SELECT products.product_id, products.dbid, title.tiles, product.status, product.date, borrow.id , borrow.name, borrow.surname FROM products,titles,borrow WHERE product.dbid = titles.dbid && borrow.id = product.prodict_id LIMIT 1";
$result=mysql_query($sql);
while ($row = mysql_fetch_array($result))
{
print "<tr><td>{$row[1]}</td>
<td>{$row[2]}</td>
<td>{$row[3]}</td>
<td>{$row[4]}</td>
<td>{$row[5]}</td>
<td>{$row[6]}</td>
<td>{$row[7]}</td>
<td>{$row[8]}</td></tr>";
}
print "</table>";
?>
I know that the sql query isn't the best one, but I think those suggestions could help you.
Here is a function for you to convert any MySQL select statement to a HTML table with table headings.
function createTable_from_sql_select_query($query) {
$sql_link = Connect_MySQLi_DB(); // Your Database Connection
$sql_link->set_charset("utf8");
$result = $sql_link->query($query);
// Adding Missing Array Column Function for Old PHP Versions (<5.5)
if (!function_exists('array_column')) {
function array_column($array, $column) {
$ret = array();
foreach ($array as $row)
$ret[] = $row[$column];
return $ret;
}
}
$headings = json_decode(json_encode($result->fetch_fields()), true);
$headings = array_column($headings, 'name');
$return = '<table>';
$return .= '<thead><tr>';
for ($x = 0; $x <= (count($headings) - 1); $x++) {
$return .= '<th>' . ucwords(str_replace('_', ' ', (strtolower($headings[$x])))) . '</th>';
}
$return .= '</tr></thead><tbody>';
while ($row = $result->fetch_object()) {
$return .= '<tr>';
for ($x = 0; $x <= (count($headings) - 1); $x++) {
$return .= '<td>' . $row->$headings[$x] . '</td>';
}
$return .= '</tr>';
}
$return .= '</tbody></table>';
return $return;
}