I have made function to get multidemnsional menu from database.
public function get_menu($parent=0,$vis=1) {
$categories = array();
$this->db->from('ci_categories');
$this->db->where('cat_child',$parent);
$this->db->where('cat_vis',1);
$this->db->order_by('cat_order');
$q = $this->db->get();
$result = $q->result();
$i=0;
foreach($result as $mainCategory) {
$mainCategory->cat_subcategories = $this->get_menu($mainCategory->cat_id);
$categories[$i] = $mainCategory;
$i++;
}
return $categories;
}
It is working but I would like to print out the menus. For now I can print main menu and one child with this code:
if (count($menu) > 0) {
foreach($menu as $menu_item) {
$link = anchor("category/".$menu_item->cat_url, $menu_item->cat_name);
echo "<li>$link";
if (!empty($menu_item->cat_subcategories)) {
echo "<ul>";
foreach($menu_item->cat_subcategories as $subcat) {
$sub_link = anchor("category/".$subcat->cat_url, $subcat->cat_name);
echo "<li>$sub_link</li>";
}
echo "</ul>";
}
echo "</li>";
}
}
It is working too but how could I print out even 3rd or 4th submenu without manualy writing those foreach and ifs ? Thanks
You can try a recursive function...
Something like:
function showMenu($menu) {
echo "<ul>";
foreach ($menu as $menu_item) {
$link = anchor("category/".$menu_item->cat_url, $menu_item->cat_name);
echo "<li>$link";
if (!empty($menu_item->cat_subcategories)) showMenu($menu_item->cat_subcategories);
echo "</li>";
}
echo "</ul>";
}
That's an idea ;)
Related
I'm trying to list sport league offerings for intramurals. My current php foreach spits out all the leagues and offerings. Great.
Now I want to only show 1 instance of the sport (course), like "Basketball" and then list the multiple league offerings (offering) in columns.
I can't do another loop based on
if $nt['course'] == "Basketball" because these will change
Not sure if my mssql query needs to change or if I can use another foreach loop?
query
$sql2 = SELECT category
,course
,offering
,Semester
,spots
,registerLink from dbtable WHERE semester like "%Fall 2016%" and category like "%Leagues%" ORDER BY course
$rs= mssql_query ($sql2, $con)
or die("Error!");
$result = array();
if (mssql_num_rows($rs)) {
while ($row = mssql_fetch_assoc($rs)) {
$result[] = $row;
}
}
return $result;
exit();
my foreach loop in view:
<?php
foreach ($data as $nt) {
echo "<div class='col-md-2'>";
echo "<h2><a href='#'>".$nt['course']."</a></h2>";
echo "<h3>".$nt['offering']."</h3>";
echo "<h4>".$nt['Semester']."</h4>";
echo "<p>".$nt['spots']."</p>";
echo "<button>".$nt['registerLink']."</button>";
echo "</div>";
}
So just to clarify:
category = "Leagues" which is in my query
course = Basketball and Flag Football, etc
It's very simple:-
instead of
$result[] = $row;
do
$result[ $row['course']][] = $row;
Simple solution:
$result = array();
if (mssql_num_rows($rs)) {
while ($row = mssql_fetch_assoc($rs)) {
if(!in_array($row["course"], $result))
{
array_push($result, $row["course"]);
}
array_push($result[$row["course"]], $row);
}
}
return $result;
And loop in view:
foreach($data as $key => $value)
{
echo "<h1>".$key."</h1>";
foreach($value as $nt)
{
echo "<div class='col-md-2'>";
echo "<h3>".$nt['offering']."</h3>";
echo "<h4>".$nt['Semester']."</h4>";
echo "<p>".$nt['spots']."</p>";
echo "<button>".$nt['registerLink']."</button>";
echo "</div>";
}
}
Here I have my database table and my table name is category where I store my data category and subcategory in category column
i want to fetch this data like this format in ul li for this code i have trying to arrange but i am not fetch data perfectly like this please help me to arrange my code this format.
You can try like this
//to select categories
$this ->db-> select();
$this->db->from('category');
$this->db->where('pid',0);
$query = $this->db->get();
$categories = array();
$i=0;
foreach ($query->result_array() as $row) {
//put all category names to $categories array
$categories[$i] =$row['category'];
$i++;
}
//to select relevant sub categories
$sub_categories=array();
foreach ($categories as $category) {
$this ->db-> select();
$this->db->from('category');
$this->db->like('category', $category, 'after');
$query = $this->db->get();
$j=0;
foreach ($query->result_array() as $row) {
//put all sub categories names to $sub_categories array
$sub_categories[$category][$j] =$row['category'];
$j++;
}
}
$return_data['categories']=$categories;
$return_data['sub_categories']=$sub_categories;
return $return_data;
This code is useful for get nth level of category,subcategory array
controller:
$this->load->model('getmenu_model');
function get_menu() {
$ci = & get_instance();
$ci->load->model("getmenu_model");
$menu['menu'] = $ci->getmenu_model->get_menu();
$echo = echoMenu($menu['menu']);
//$echo.= "<li>Loose Diamonds</li>";
$menu['print_menu']=$echo;
print_r($menu);
//return $menu;
}
function echoMenu($arr) {
$ci = & get_instance();
$echo = "";
//$echo.="<ul>";
foreach ($arr as $subArr) {
if (!empty($subArr['sub_menu'])) {
$echo.= "<li>";
$echo.= "" . $subArr['name'] . "";
if ($subArr['sub_menu']) {
$echo.= "<ul>";
$echo .=echoMenu($subArr['sub_menu']);
$echo.= "</ul>";
}
$echo.= "</li>";
} else {
$echo.= "<li>" . $subArr['name'] . "</li>";
}
}
//$echo.= "</ul>";
return $echo;
}
model:
public function get_menu() {
$this->db->select('id,name,parent_id');
$menu = $this->db->get('category')->result_array();
$data=$this->menu_child($menu);
//print_r($data);
return $data;
}
function menu_child($menu, $parent = NULL) {
// echo $parent."---";
$main_menu = array_filter($menu, function($a)use($parent) {
return $a['parent_id'] == $parent;
});
// print_r($main_menu);
if ($main_menu) {
foreach ($main_menu as $key => $value) {
$main_menu[$key]['sub_menu'] = $this->menu_child($menu, $value['id']);
}
}
// print_r($main_menu);
return $main_menu;
}
public function getCats($model){
$levels = array();
$tree = array();
$cur = array();
foreach($model as $rows){
$cur = &$levels[$rows['id']];
$cur['parent_id'] = $rows['parent_id'];
$cur['title'] = $rows['title'];
if($rows['parent_id'] == 0){
$tree[$rows['id']] = &$cur;
}
else{
$levels[$rows['parent_id']]['children'][$rows['id']] = &$cur;
}
}
return $tree;
}
public function getTree($arr){
echo '<ul>';
foreach($arr as $k=>$v){
echo '<li>';
echo ''.$v['title'].'';
if(!empty($v['children'])){
echo getTree($v['children']);
}
echo '</li>';
}
echo '</ul>';
}
public function allCats($pos) {
$model = Category::model()->findallBySql('SELECT id, parent_id, title FROM {{category}} WHERE position="'.$pos.'"');
$cats = getCats($model);
echo getTree($cats);
}
I wonder, why these functions don`t work in model file(inside class)?
If i use them inside controllers, they work fine, and if i paste them inside model(class) file, they stop working(as if they are becoming invisible). The last function causing the above two functions.
You are calling getCats($model) which would be a global function. But it's defined as a class function/method. Call it $this->getCats($model) and $this->getTree($cats) and it should work.
please, I have this code to import data from XML to database:
$a = glob('data/*/*.xml');
echo "import kategorie ...... ";
foreach ($a as $i) {
$xml = simplexml_load_file("$i") or die ("Chyba: Nemuzu nacist soubor");
foreach($xml->DocumentElement as $entry) {
foreach ($entry->hotel as $dataHotel) {
addCategory("$dataHotel->country", "$dataHotel->location", "$dataHotel->location2");
}
foreach ($entry->Popisy as $dataPopisy) {
addHotel("$dataHotel->hotel", "$dataPopisy->doporuc");
}
}
}
echo "OK\n"
I can not figure out how to do it - I need in function "addHotel" get data from "hotel" array and from "Popisy" array.
So, I need to get from two at once.
Here is XML structure: http://pastebin.com/TNTpBijg and here http://fmnet.cz/HLS240.xml
Is this possilbe? Thank you very much!
Now I tried this:
$a = glob('data/*/*.xml');
echo "import kategorie ...... ";
foreach ($a as $i) {
$xml = simplexml_load_file("$i") or die ("Chyba: Nemuzu nacist soubor");
foreach($xml->DocumentElement as $entry) {
foreach ($entry->hotel as $dataHotel) {
//addCategory("$dataHotel->country", "$dataHotel->location", "$dataHotel->location2");
foreach ($entry->Popisy as $dataPopisy) {
//addHotel("$dataHotel->hotel", "$dataPopisy->doporuc");
echo "$dataHotel->hotel";
echo "\n";
echo "$dataPopisy->doporuc";
echo "\n";
}
}
}
}
echo "OK\n";
but output is only:
import kategorie ...... OK
Yes, it is possible. You can do it by embedding the popisy loop inside the hotel loop or the other way round. Check the code below:
$a = glob('data/*/*.xml');
echo "import kategorie ...... ";
foreach ($a as $i) {
$xml = simplexml_load_file("$i") or die ("Chyba: Nemuzu nacist soubor");
foreach($xml->DocumentElement as $entry) {
foreach ($entry->hotel as $dataHotel) {
addCategory("$dataHotel->country", "$dataHotel->location", "$dataHotel->location2");
foreach ($entry->Popisy as $dataPopisy) {
addHotel("$dataHotel->hotel", "$dataPopisy->doporuc");
}
}
}
}
echo "OK\n"
I keep getting the following warning listed below on line 3.
Warning: Invalid argument supplied for foreach()
Here is the php code.
function dyn_menu($parent_array, $sub_array, $qs_val = "menu", $main_id = "nav", $sub_id = "subnav", $extra_style = "foldout") {
$menu = "<ul id=\"".$main_id."\">\n";
foreach ($parent_array as $pkey => $pval) {
if (!empty($pval['count'])) {
$menu .= " <li><a class=\"".$extra_style."\" href=\"".$pval['link']."?".$qs_val."=".$pkey."\">".$pval['label']."</a></li>\n";
} else {
$menu .= " <li>".$pval['label']."</li>\n";
}
if (!empty($_REQUEST[$qs_val])) {
$menu .= "<ul id=\"".$sub_id."\">\n";
foreach ($sub_array as $sval) {
if ($pkey == $_REQUEST[$qs_val] && $pkey == $sval['parent']) {
$menu .= "<li>".$sval['label']."</li>\n";
}
}
$menu .= "</ul>\n";
}
}
$menu .= "</ul>\n";
return $menu;
}
Here is the whole code I'm working on.
$mysqli = new mysqli("localhost", "root", "", "sitename");
$dbc = mysqli_query($mysqli,"SELECT id, label, link_url, parent_id FROM dyn_menu ORDER BY parent_id, id ASC");
if (!$dbc) {
// There was an error...do something about it here...
print mysqli_error();
}
while ($obj = mysqli_fetch_assoc($dbc)) {
if (empty($obj['parent_id'])) {
echo $parent_menu . $obj['id']['label'] = $obj['label'];
echo $parent_menu . $obj['id']['link'] = $obj['link_url'];
} else {
echo $sub_menu . $obj['id']['parent'] = $obj['parent_id'];
echo $sub_menu . $obj['id']['label'] = $obj['label'];
echo $sub_menu . $obj['id']['link'] = $obj['link_url'];
echo $parent_menu . $obj['parent_id']++;
}
}
mysqli_free_result($dbc);
function dyn_menu($parent_array, $sub_array, $qs_val = "menu", $main_id = "nav", $sub_id = "subnav", $extra_style = "foldout") {
$menu = "<ul id=\"".$main_id."\">\n";
foreach ($parent_array as $pkey => $pval) {
if (!empty($pval['count'])) {
$menu .= " <li><a class=\"".$extra_style."\" href=\"".$pval['link']."?".$qs_val."=".$pkey."\">".$pval['label']."</a></li>\n";
} else {
$menu .= " <li>".$pval['label']."</li>\n";
}
if (!empty($_REQUEST[$qs_val])) {
$menu .= "<ul id=\"".$sub_id."\">\n";
foreach ($sub_array as $sval) {
if ($pkey == $_REQUEST[$qs_val] && $pkey == $sval['parent']) {
$menu .= "<li>".$sval['label']."</li>\n";
}
}
$menu .= "</ul>\n";
}
}
$menu .= "</ul>\n";
return $menu;
}
function rebuild_link($link, $parent_var, $parent_val) {
$link_parts = explode("?", $link);
$base_var = "?".$parent_var."=".$parent_val;
if (!empty($link_parts[1])) {
$link_parts[1] = str_replace("&", "##", $link_parts[1]);
$parts = explode("##", $link_parts[1]);
$newParts = array();
foreach ($parts as $val) {
$val_parts = explode("=", $val);
if ($val_parts[0] != $parent_var) {
array_push($newParts, $val);
}
}
if (count($newParts) != 0) {
$qs = "&".implode("&", $newParts);
}
return $link_parts[0].$base_var.$qs;
} else {
return $link_parts[0].$base_var;
}
}
echo dyn_menu($parent_menu, $sub_menu, "menu", "nav", "subnav");
It's telling you that $parent_array isn't an array.
If you post the code that calls this function, we can tell you more.
Are you sure $parent_array is actually an array? Try checking it with is_array first (perhaps returning an empty string to represent the menu or whatever - adapt to your needs):
if (!is_array($parent_array)) {
return "";
}
This error happens when you supply not an array into forearch. Try print_r() first argument of every foreach
If you change your function signature to include type hinting (only works for arrays and objects), you'll be sure that your function gets what it needs:
function dyn_menu(array $parent_array, array $sub_array, //etc.)
And you should get an error message that pinpoints the caller of the function, which is where the problem really is.
It looks like you were expecting to build $parent_array in that while loop at the beginning. Instead it's just echoing stuff.
The lines like:
echo $parent_menu . $obj['id']['label'] = $obj['label'];
Should probably be like:
$menu['label'] = $obj['label'];
Then at the end (inside) of the loop add something like:
$parent_menu[$obj['id']] = $menu;
So you build the array you're using in dyn_menu.
In any case, the while loop looks like your problem. It's not building $parent_menu from the data.