Im developing a website and I am trying to a foreach include for my header which includes my navigation menu (the main topic here).
My code inside the header.php file for the navigation menu is here:
<!-- topmenu -->
<div class="menu-header">
<div class="container">
<ul class="top menu">
<?php
$nav = array("Home","About","Portfolio","Products","Services","Contact");
foreach($nav as $item){
if($item == $title){
echo "<li class='current-menu-ancestor parent'><a href='$item.php'>$item</a></li>";
}else{
echo "<li><a href='$item.php'>$item</a></li>"; }
}
?>
</ul>
</div>
</div>
<!--/ topmenu -->
You may notice that in the code is the condition if($item == $title). In my index.php I have included $title="Home"; which I intended to be taken and used in this if statement.
On my index.php page I have included this with the following code:
<?php
include("header.php");
$title = "Home";
?>
Can anyone tell me where I am going wrong?
Not an answer, but comments aren't suitable for formatted code. You might want to de-duplicate some of your HTML:
$class = '';
if($item == $title) {
$class = ' class"current-menu-ancestor parent"';
}
echo "<li{$class}><a href='$item.php'>$item</a></li>";
Duplicating HTML as you did can lead to maintenance problems later on, if you decide to change something in the menu structure and change only one of the copies of the menu html.
header.php can not look into the future. If you want the variable to be set in the include, you need to set it before:
<?php
$title = "Home";
include("header.php");
?>
So you basically just switched the lines.
Additionally I suggest that you enable error reporting to the highest level when you develop, as it will give you warning on common mistakes that can happen while typing code.
You can do this by adding the following two lines to the top of your script:
error_reporting(~0);
ini_set("display_errors", "1″);
or by changing your PHP configuration.
You need to set $title before including header.php!
i.e.
<?php
$title = "Home";
include("header.php");
?>
Related
I am building a Website using Bootstrap 4. The template that I am using has a carousel at the top of the page. I use my index.php page as a shell for other content which is called using the following code:
<?php
if (!isset($_REQUEST['content']))
include("home.php");
else
{
$content = $_REQUEST['content'];
$nextpage = $content;
include($nextpage);
}
?>
Currently the carousel will show on every page. I would like for it to only show on the home page or index.phpcontent=home.php but I have yet to figure out how to do that without breaking things.
On the index.php page I have set up chunks of code to be called with include statements:
<body>
<header>
<?php include 'navbar.php'; ?>
<?php include 'carousel.php'; ?>
</header>
I have tried to programatically simply call the carousel.php as follows:
<?php
if (!isset($_REQUEST['content']))
include("carousel.php");
else
{
include("");
}
?>
But that did not work. Any help would be greatly appreciated.
So I'm wanting to make a way to display the 2nd newest row from my database. So my example (To help better explain it) If i have 10 rows. I want to display only the second newest one. Not the newest one but the one right after it. Or the maybe even the third one. I have my working code below and i see the for each loop. But I'm not sure how to only display the one I'm wanting it to display. I also don't think how i have it set up is the most efficient way of acomplishing this.
I am using concrete5 for this site and the main idea is for composer so i can post a new post and the pull a recent news feed but showing the second post.
Here is my current code: (This shows the first post)
<?php
defined('C5_EXECUTE') or die("Access Denied.");
?>
<div id="blog-index">
<?php
$isFirst = true; //So first item in list can have a different css class (e.g. no top border)
$excerptBlocks = ($controller->truncateSummaries ? 1 : null); //1 is the number of blocks to include in the excerpt
$truncateChars = ($controller->truncateSummaries ? $controller->truncateChars : 255);
$imgHelper = Loader::Helper('image');
foreach ($cArray as $cobj):
$title = $cobj->getCollectionName();
$date = $cobj->getCollectionDatePublic(DATE_APP_GENERIC_MDY_FULL);
$author = $cobj->getVersionObject()->getVersionAuthorUserName();
$link = $nh->getLinkToCollection($cobj);
$firstClass = $isFirst ? 'first-entry' : '';
$entryController = Loader::controller($cobj);
if(method_exists($entryController,'getCommentCountString')) {
$comments = $entryController->getCommentCountString('%s '.t('Comment'), '%s '.t('Comments'));
}
$isFirst = false;
?>
<div class="entry">
<div class="title">
<h3>
<?php echo $title; ?>
</h3>
<h6 class="post-date">
<?php
echo t('Posted by %s on %s',$author,$date);
?>
</h6>
</div>
<div class="excerpt">
<?php
$a = new Area('Main');
$a->disableControls();
if($truncateChars) {
$th = Loader::helper('text');
ob_start();
$a->display($cobj);
$excerpt = ob_get_clean();
echo $th->entities($th->shorten($excerpt,$truncateChars));
} else {
$a->display($cobj);
}
?>
</div>
<div class="ccm-spacer"></div>
<br />
<div class="meta">
<?php echo $comments; ?> <?php echo t('Read the full post'); ?> <i class="icon-chevron-right"></i>
</div>
</div>
<hr class="blog-entry-divider"/>
<?php endforeach; ?>
</div>
To build upon what the others have written as comments:
What you've pasted is a concrete5 view. You'll notice there's no db querying or PageList building in there. For that, you need to look in the controller. (This looks like a page list block view, so the controller will be in / concrete / core / controllers / blocks / page_list.php (on c5.6+).
The concrete5 api code to do what the others have suggested (let mysql handle the skipping) is done within the ->get() call. So, on about line 135:
$pl->get(1, 1);
Remember not to modify the files directly, but to override them the c5 way. There are plenty of tutorials on this on the c5 website.
I have the following code to include pages dynamically:
<div id="content">
<div id="aside">
...
</div>
<div id="main">
<?php
$page = (isset($_GET['page'])) ? sanitize($_GET['page']) : 'home';
if (!include 'pages/'.$page.'.php') require 'pages/404.php';
?>
</div>
</div>
As you can see, the #aside has static content.
I want to include a specific content for the #aside depending on the page selected. For example, if the user goes to 'Home' and 'About', I want the 'default' aside. But if the user goes to 'Documents' I want a 'Sections' aside.
I know I can just include each aside from every page, but that's not effective. I also don't want the user to be hable to set the aside as the main content, so they have to be in different folders or something.
I'd like to know an effective and not so complicated way to do this.
Thanks for taking your time to read this.
You want to keep which sidebar goes on which page in a database, and then query that database for the correct sidebar to include.
A table structure may look like this:
Table sidebars: ID | path | name | more info on sidebar...
Table pages: ID | path | name | more info on page...
Table sidebars-to-pages: page_ID | sidebar_ID
This approach even allows you to place multiple sidebars on a specific page.
What if you did this?
<?php
ob_start();
$page = (isset($_GET['page'])) ? sanitize($_GET['page']) : 'home';
if (!include 'pages/'.$page.'.php') require 'pages/404.php';
$contents = ob_get_clean();
?>
<div id="content">
<div id="aside">
<?php include($aside); ?>
</div>
<div id="main">
<?php echo $contents; ?>
</div>
</div>
and $page.php would look like:
<?php $aside = "sidebars/default.php"; ?>
<p>HTML for #main<br />
goes here</p>
There are a few different ways to do this that are all more-or-less equal. I almost always use a config.php file for sites to hold whatever global information I want every page to have. At the top of every page, you just call
<?php
require_once('config.php');
?>
In that config.php file, you could have an array listing your page names and the file you want included for each page, as well as a function that returns the content, like so:
// this lets you call includes relative to the site root
set_include_path($_SERVER['DOCUMENT_ROOT']);
$defaultAsideContent = 'includes/default.php';
$asideContent = array(
'index.php' => 'includes/include-1.php',
'document.php' => 'includes/include-2.php'
);
function getAsideContent() {
global $asideContent;
global $defaultAsideContent;
$content = $defaultAsideContent;
// get the requested page
$pageFull = $_SERVER['REQUEST_URI'];
// strip URL variables
$pageParts = explode('?', $pageFull);
$page = $pageParts[0];
// loop throught the array and see if there is specific aside content for the page
foreach($asideContent as $key=>$value) {
if ($page == $key) {
$content = $asideContent[$key]);
}
}
include($content);
}
Lastly, wherever you want your aside content to show up, just do
<?php getAsideContent(); ?>
When you create a new page, if you want specific aside content, just edit your config file. Just FYI, didn't test this at all, probably has bugs, but you get the jist.
Thank you all for your answers and collaboration. Although none of the answers did exactly what I was looking for, they showed me other ways to approach this issue and guided me to decide what method to use.
I came up with what I think is the simpliest way to do this:
I set my folder structure as: pages/aside and pages/main
I set up an array($asides) with the aside files as the keys and the main content files as the values.
Then I check if the requested file exists in the main folder.
If it doesn't exist, I redirect the user to the 404 page. If it does exist, I loop through $asides to see which aside is asigned to that main content page.
If it doesn't belong to any of the establisged asides, then I include the default aside.
$asides = array(
'aside1' => array('page1', 'page2', 'page3', 'page4'),
'aside2' => array('page5', 'page6')
);
$page = (!empty($_GET['p'])) ? sanitize($_GET['p']) : 'page1';
if (file_exists("pages/main/{$page}.php")) {
foreach ($asides as $key => $value) {
if (in_array($page, $asides[$key])) {
$aside = $key;
break;
}
}
if (!isset($aside)) $aside = 'default';
?>
<div id="aside"><?php require "pages/aside/{$aside}.php"; ?></div>
<div id="main"><?php require "pages/main/{$page}.php"; ?></div>
<?php
} else {
header('Location: ?p=404');
}
The bounty goes to Madara Uchiha because in my opinion, his answer is simple an effective. Thanks again to all of you who helped me with this issue.
What I'm trying to do is to add some HTML tags to my Joomla! module titles. I will need something like this
Some <b>Title</b>
but when I save !Joomla trims the titles and remove all HTML tags.
I've check the administrator/com_content, which I think should be responsible for inserting the database data, but I couldn't find the answer there.
Can anyone help me with this headache?
Check out ../templates/system/html/modules.php
You can style your module structure in HTML.
function modChrome_myCustomModule($module, &$params, &$attribs)
{
$doc =& JFactory::getDocument();
$css = ".otherClass {}";
$css .= ".yourClass {}";
$doc->addStyleDeclaration($css);
?>
<div>
<?php if ($module->showtitle != 0) : ?>
<h1><?php echo $module->title; ?></h1>
<?php endif; ?> // post your title
</div>
<div>
<?php echo $module->content; ?> // post your module content
</div>
<?php
}
Then call your styled module in index.php:
<jdoc:include type="modules" name="right" style="myCustomModule" />
So I found the solutions. It includes both of the previous answers, so I'm putting a new one here with the correct code.
First of all I need to say, that this solution works only for a fixed amount of words (last one, two, etc.) I need only to have the last one, so I will post an example code with one word.
First as SMacFadyen sad I needed to create a new module structure in my template html folder: /templates/system/html/modules.php file.
Note: If you don't want to add this new module styling to all templates, but just on one of them you need to put the module.php in your template's html folder.
The provided by SMacFadyen looks like this:
function modChrome_myCustomModule($module, &$params, &$attribs)
{
$doc =& JFactory::getDocument();
$css = ".otherClass {}";
$css .= ".yourClass {}";
$doc->addStyleDeclaration($css);
?>
<div>
<?php if ($module->showtitle != 0) : ?>
<h1><?php echo $module->title; ?></h1>
<?php endif; ?> // post your title
</div>
<div>
<?php echo $module->content; ?> // post your module content
</div>
<?php
}
Then expired by the comments of Hanny I've added some php code to match the last word of the title and to store it in a new varibale.The code looks like this:
$wrap_tag = 'b';
$html_title = preg_replace("~\W\w+\s*$~", '<'.$wrap_tag.'>'.'\\0'.'</'.$wrap_tag.'>', $module->title);
Note: the $wrap_tag variable stores the tag you want. You can put b, em, u and etc. to have different result.
The last thing was to replace the displayed title, so I've replaced this code:
<h1><?php echo $module->title; ?></h1>
with this one:
<h1><?php echo $html_title; ?></h1>
The final result was this:
function modChrome_myCustomModule($module, &$params, &$attribs)
{
$doc =& JFactory::getDocument();
$css = ".otherClass {}";
$css .= ".yourClass {}";
$wrap_tag = 'b';
$html_title = preg_replace("~\W\w+\s*$~", '<'.$wrap_tag.'>'.'\\0'.'</'.$wrap_tag.'>', $module->title);
$doc->addStyleDeclaration($css);
?>
<div>
<?php if ($module->showtitle != 0) : ?>
<h1><?php echo $html_title; ?></h1>
<?php endif; ?> // post your title
</div>
<div>
<?php echo $module->content; ?> // post your module content
</div>
<?php
}
Thanks to everybody for the help.
The Gantry framework can help you accomplish what you want (1st word styled one way, 2nd word styled another) - but it's a lot of overhead just accomplish that one task you're looking for. Ultimately you'll have to create a template override for your template, and then do some creative editing with php in order to get it to display that way.
There's no quick and easy way to get that done. You'll have to do some php coding on the backend and edit the template (use an override so you don't hack core files). Ultimately you'll probably have to code the php to pull apart the title, and apply formatting to each pulled apart word (or string of words as the case may be) using CSS.
Hope that helps.
I can't figure out how to say what I'm talking about which is a big part of why I'm stuck. In PHP I often see code like this
html
<?php
language construct that uses brackets {
some code;
?>
more html
<?php
some more code;
}
?>
rest of html
Is there any name for this? Having seen this lead me to try it out so here is a concrete example whose behavior doesn't make sense to me
<div id="content">
<ul id="nav">
<?php
$path = 'content';
$dir = dir($path);
while(false !== ($file = $dir->read())) {
if(preg_match('/.+\.txt/i', $file)) {
echo "<li class=\"$file\">$file</li>";
?>
</ul>
<?php
echo "<p class=\"$file\">" . file_get_contents($path . '/' . $file) . '</p>';
}
}
?>
</div>
Which outputs roughly <div><ul><li></li></ul><li></li><p></p>...</div> instead of <div><ul><li></li>...</ul><p></p>...</div>, which is what I thought would happen and what I want to happen. To make it clearer I want the <li> inside the <ul> and the <p> inside the <div>. Yes, I know there is an easy solution but I was wondering if there is a way to do it with the technique I am looking for a name for.
Just something to add here:
If you're using a PHP loop for templating, there is another syntax that helps you avoid confusion with indentation and which-braces-match-which:
<?php
foreach($items as $item):
?>
<b>item: </b> <?php echo $item; ?> <br />
<?php
endforeach;
?>
this may be an oversimplification, but really you shouldn't be using anything more complicated than this in a template. Things like the $items variable and anything else you need should be set up by the code which includes the template, and not in the template itself.