PHP, CSS navigation bar coding

I like the idea that ‘you know’ they are inside the phones category but I am not sure how you know. Obviously I could add a field to the database called category and it could say “phones” as the entry. If this is what you mean do I have to add this to the URL as well (using the get function). You suggest ‘you know’ it is in phones category without it being in the URL, which sounds fair. But how do you code it in PHP? How does the web site know the category without using the URL?

Matt

In your products table, have a field ‘categoryid’, that links to the category table.

If i’m sitting at products.php?productid=1 , and product #1 has a categoryid of 5, and category #5 is phones, then i know that when i’m looking at product #1, it’s part of the phones category.

OK I understand apart from where you say category table - this implies I am using 2 tables. Why do i need a category table… or do you mean category array in the PHP code??

Matt.

I mean a category table. Because a category is something you want to store information about. The category name, mostly, but if, lets say, later on, you wanted to put a sale on certain categories of your store. You could have a field in your category table for ‘discount’.

A database is not a single table, unless you’re modelling something very, very basic.
The idea is to remove redundancy and overhead. For example. Let’s take some products, and their categories, and…lets say their price… and the current discount i’m giving out.

Product, Category, Price, Discount
iPhone,Phones,300,0
Motorola i231,Phones,300,0
Tshirt,Apparel,12,5
Sweatshirt,Apparel,22,5
etc etc etc.

(I’m having a 5$ sale on apparel.)

Now, I COULD store all that in a single table. But it’s highly wasteful to save the word “Apparel” in the database over and over and over… and that’s assuming of course that you never ever maek a typo, because then you’d break your pretty groupings.

Instead, how about I do this…

Product,Category,Price
iPhone,1,300
Motorola i231,1,300
Tshirt,2,12
Sweatshirt,2,22

Categoryid,Categoryname,discount
1,Phones,0
2,Apparel,5

And furthermore, what if you wanted to have seperate categories for Motorola Apparel, and Apple Apparel, but want to call them both “Apparel” in your navigation? Well a single table, you cant do that, because you couldnt tell the products apart. If they had different CategoryID’s, though, you could tell them apart instantly, even if they had the same name.

Yes, that makes sense now. So i would need to code it so that if the customer selects “iphone 4” from submenu for the “iphone” link the tables are cross referenced to check the product category.

The only problem now, which I mentioned above, is making the clicked link appear at the top of the left navigation bar with its’ sub menu.

For example if I have

Link 1
Link 2
Link 3
Link 4
Link 5
Link 6
Link 7
Link 8

AND CUSTOMER CLICKS LINK 8

they get

Link 8
Product 1
Product 2
Product 3
Product 4
Product 5
Product 6
Product 7
Link 1
Link 2
Link 3
Link 4
Link 5
Link 6
Link 7

Is this possible? Basically I want the clicked link and its’ submenu listed first and then the remaining links in the ‘standard order’. The only link out of its’ order is the one that was clicked.

Matt.

Rule #1: Pretty much anything is possible, if coded right.

Something like…(and i’m just pulling this off the top of my head so dont hold me to this being the best way to do it… and in fact i know it isnt because this isnt sanitized, but it’s a demonstration)


$res = mysql_query("SELECT * FROM categories");
while($row = mysql_fetch_array($res)) {
  $cats[$row['categoryid']] = $row['categoryname'];
}
if(isset($_GET['category'])) {
 $selcat = $_GET['category'];
}
if(isset($_GET['product'])) {
 $prod_info = mysql_fetch_array(mysql_query("SELECT * FROM product WHERE productid = ".$_GET['product']));
 //Prod_Info now gets stored for use in the main display.
 $selcat = $prod_info['categoryid'];
}
if(isset($selcat)) {
  echo "<a href='categorylist.php?category=".$selcat."'>".$cats[$selcat]."</a>";
  unset($cats[$selcat]); //Gets rid of it for later.
  $res = mysql_query("SELECT productid,name FROM products WHERE categoryid = ".$selcat);
  while($row = mysql_fetch_array($res)) {
   echo "&nbsp;<a href='product.php?product=".$row['productid']."'>".$row['name']."</a>";
  }
}
foreach($cats AS $key => $cat)  {
  echo "<a href='categoryview.php?category=".$key."'>$".$cat."</a>";
}

This is exactly what PHP can be used for. It’s dynamic, so one PHP file can output all kinds of different things depending on a whole number of variables including what a user has clicked, where they are in the world, whether they’ve logged in or not, what time of day it is… basically almost anything.

I am trying to understand the code StarLion provided.

I am not sure what the first bit of code does:

$res = mysql_query(“SELECT * FROM categories”);
while($row = mysql_fetch_array($res)) {
$cats[$row[‘categoryid’]] = $row[‘categoryname’];
}

And, secondly if I try using the code below I get a Warning in my browser:

if(isset($_GET[‘product’])) {
$prod_info = mysql_fetch_array(mysql_query("SELECT * FROM product WHERE productid = ".$_GET[‘product’]));
//Prod_Info now gets stored for use in the main display.
$selcat = $prod_info[‘categoryid’];

The Warning says:
Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in /home/content/…etc…

What could be the problem? Is it trying to display an array? And I’m not sure what you meant by “//Prod_Info now gets stored for use in the main display.” - as this is a navigation bar, why do we store info for the main display??

I think, if I can understand the first bit of code and solve the Warning problem, I might be getting somewhere with designing it!

Look forward to your reply,

Matt.

Okay…


$res = mysql_query("SELECT * FROM categories"); //Get everything out of the Categories table.
while($row = mysql_fetch_array($res)) { //For each category...
$cats[$row['categoryid']] = $row['categoryname']; //Put the name of the category into a numeric array, based on the categoryid.
}

So basically, if your category table looked like…

CategoryID, CategoryName, Discount, … (etc etc etc)
1,Phones,0,…
5,Apparel,5,…
6,Accessories,0,…

(I skipped 2-4. Maybe you deleted some rows at some point. Who knows. CategoryID is a PRIMARY KEY.)

Then PHP would hold an array $cats at the end of that code such that:
$cats[1] = “Phones”
$cats[5] = “Apparel”
$cats[6] = “Accessories”

(Note: numeric arrays in PHP dont ‘fill in’ gaps in the numeric structure.)

“Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in /home/content/…etc…”

means that the query returned an error. Try throwing


mysql_error();

on the line above that error.

I’ve tried adding the mysql_error(); but it still comes up with the same warning.

Let me check I understand the code:
You are creating prod_info for a single product? But why are we asking for an array? There will only be one ProductID (taken from the URL using the GET function).

And then you are making sure the chosen product is in its’ correct category, using: $selcat = $prod_info[‘categoryid’];

Is this correct or not?

Matt.

fetch_array() tells PHP “Go get a row from that result, and return it as a formatted array, where the field names = array keys”

So fetch_array()'ing prod_info will mean $prod_info[‘name’] will hold the name of the product, etc etc, based on the field names in your mysql table.

$selcat = $prod_info[‘categoryid’] doesnt do any correcting, all it does is say to PHP ‘this is the category of the product i’m looking at’. I use $selcat because there are three scenarios here:

Scenario 1: No category or product set on the URL. (So i just want a basic list of the categories)
Scenario 2: A category set on the URL (So I can just read the category in from the URL)
Scenario 3: A product set on the URL (So I need to read the category in from the product information)

Then once i deal with reading the category in, I check to see if there is a category (isset($selcat)), and respond accordingly.

Still got the warning message. I was wondering if it was either

  • The quotations are in the wrong place (before the get request)
  • I have 2 tables within one database and I am only accessing the database. I think it is OK to call field names by connecting to the database and not the table names.
  • My database is stored on a separate server to my web site. I am connecting to the database at the top of the page at the other server but perhaps further down the page it has forgotten my connection??

Other than this - I do not know. Any ideas,

Matt.

If you echo mysql_error(); and get nothing out, then something has gone dramatically wrong.

Which line is it that is throwing the error? (Compare line numbers) Because there are multiple fetch_array() calls in there.

PHP is a general-Purpose language development produce web pages. HTML Source and interpreted by a web server PHP processor module. It has evolved to include a command-line interface capability and can be used in standalone graphical applications.

<snip/>

I started again and this time it is working; not sure what I did wrong last time.

The only problem now is the ‘remaining categories’ when loaded in the browser have dollar signs “$” in front of them. How do I get rid of the “$” in front of the category names? Does this have something to do with .$key, as I’m not sure where this comes from.

And my other query is:
In the code we use the get function for: ‘category’ and ‘product’
However, when we write the code in this script we use only ‘productid’ with product.php page and only “.$key.” with categoryview.php page.
If the code asks for both towards the top of the script, why do we only enter one in our fields towards the bottom of the coding??

Look forward to your comments.

Matt.

Following from the previous message I have found and deleted the extra ‘$’ you added in the final line. (Deleted first “$” in “$”.$cat.“</a>”) It was probably a typo you made in the final line.

But I’m still confused about the use of the ‘get’ function. Why we ask for both and then use only one in each URL we create (see last/previous message).

Matt.

Because you only need 1.
Remember the scenarios.

A user could:
Just have clicked on your store (No Category or Product ID’s yet.) [user is now on yourstorename.php, which is loading the navigation script]
Clicked on a category, but hasnt chosen a product (No Product ID, but we have a Category) [user is now on categoryview.php, which is loading the navigation script]
Clicked on a product. (The URL-based category is redundant at this point, because we have a categoryID attached to the product.) [user is now on product.php, which is loading the navigation script]

Now. As to why ‘we only use X with Y’… both product.php and categoryview.php would be including the same navigation.php (or whatever you called it) to generate the navigation window. Thus, we must account for both eventualities. Notice the structure, though; if a user on product.php decided for s***s and giggles to throw &category=1 on the end of the URL, the page wouldnt mess up - it would detect the category on the URL, store it, then immediately override it by noticing there’s a productID on the URL, and use that information instead.

I am going to design an example so that I can see it working before I design it for a web site. I’ll get back to you if I encounter some issues because at the moment I can only get the navigation working when both productid and category are passed through the URL.

At the moment, I have something else I’d like to design but I am not sure it is possible with this navigation code we have here. There will be part of the left navigation bar that needs to change depending on the link clicked: To get the idea across here is an example: They start with…

BMW
Mercedes
Ford
Accessories

User clicks ‘accessories’ and gets:

Accessories
BMW accessories
Mercedes accessories
Ford accessories
BMW
Mercedes
Ford

User clicks ‘BMW accessories’ and gets (category name changes from Accessories to BMW accessories and associated sub menu appears):

BMW accessories
Spare wheel
New Indicator
Rear View Mirror
New Seat
Radio
Accelerator Pedal
BMW
Mercedes
Ford

Notice that the navigation categories change as do the sub menus as the user gets deeper into accessories. I think it would be a compromise too far to not include the individual accessories within the navigation bar and it needs breaking down into manufacturer so I see no way around this and I am trying to work out how the code we have can be modified in this small way? Is this likely to be possible?

All the best,

Matt.

It’s not too hard to modify - you’re simply adding another layer to the structure. Instead of Category->Product, you’re now just making it Category->SubCategory->Product.

Each subcategory belongs to a Category.

There is now an additional scenario:
User has chosen a subcategory, but not a product.