I have been re-factoring some of my templates and have put the link to jQuery code at the bottom of my template files to keep page load speeds fast.
I also have some javascript modules that I only use on specific pages so I don't include these in the main template but rather inside the content.
Here is how the templates look....
<html>
<head>
</head>
<body>
<!-- navigation -->
<nav></nav>
<!-- end navigation -->
<!-- main content -->
<?php $this->load->view($module . '/' . $view_file); ?>
<!-- end main content -->
<!-- footer -->
<footer></footer>
<!-- end footer -->
<!-- javascript dependencies -->
<script src="<?php echo base_url('bower_components/jquery/dist/jquery.min.js'); ?>"></script>
</body>
</html>
If I add custom js code to a specific page inside the template like this:
<!DOCTYPE html>
<html>
<head>
</head>
<body>
<!-- navigation -->
<nav></nav>
<!-- end navigation -->
<!-- main content -->
<?php $this->load->view($module . '/' . $view_file); ?>
<!-- end main content -->
<script src="some custom js that uses jQuery"></script>
<!-- footer -->
<footer></footer>
<!-- end footer -->
<!-- javascript dependencies -->
<script src="<?php echo base_url('bower_components/jquery/dist/jquery.min.js'); ?>"></script>
</body>
</html>
I get errors
ReferenceError: $ is not defined
So do I have to put my jQuery and other dependencies in the document head or is there another way?
You get this error because the script is running before jQuery has been loaded, so it is undefined.
To fix this, just place your custom script in the line below the jQuery import and it should work.
Alternatively, put the jQuery import higher in the page so it is always above your custom scripts and it will work.
Related
I'm trying to build a HTML template with a small javascript code. Here is the stuff... At the root, I built two files :
index.html
<!DOCTYPE html>
<html lang="fr">
<head>
<title>HTML Template</title>
<!-- Header initialized with /header-footer.js -->
</head>
<body>
<footer>
<!-- Footer initialized with /header-footer.js -->
<script type="text/javascript" src="/headerfooter.js"></script>
</footer>
</body>
</html>
headerfooter.js
(function () {
/*************** HEADER *****************/
const headerBeforeAppend = document.querySelector('head')
document.querySelector('head').innerHTML = `
${headerBeforeAppend.innerHTML}
<meta charset="UTF-8">
<meta content="width=device-width,initial-scale=1" name="viewport">
<!-- CSS -->
<!-- Google fonts -->
<link href="https://fonts.googleapis.com/css?family=Montserrat:100,400,700" rel="stylesheet">
<!-- Bootstrap, Materialize, etc... you see the idea -->
<!-- Javascript -->
<!-- Fontawesome -->
<script src="https://use.fontawesome.com/45d80bbe59.js"></script>
<!-- jQuery, Bootstrap scripts, etc... you see the idea -->
`
/*************** FOOTER *****************/
const footerBeforeAppend = document.querySelector('footer')
document.querySelector('footer').innerHTML = `
${footerBeforeAppend.innerHTML}
<!-- JQuery (for Bootstrap) -->
<script src="https://code.jquery.com/jquery-3.2.1.slim.min.js" integrity="sha384-KJ3o2DKtIkvYIK3UENzmM7KCkRr/rE9/Qpg6aAZGJwFDMVNA/GpGFF93hXpG5KkN" crossorigin="anonymous"></script>
<!-- Bootstrap CDN v4 alpha-->
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.11.0/umd/popper.min.js" integrity="sha384-b/U6ypiBEHpOf/4+1nzFpr53nxSS+GLCkfwBdFNTxtclqqenISfwAzpKaMNFNmj4" crossorigin="anonymous"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/js/bootstrap.min.js" integrity="sha384-h0AbiXch4ZDo7tp9hKZ4TsHbi047NrKGLO3SEJAg45jXxnGIfYzk4Si90RDIqNm1" crossorigin="anonymous"></script>
`
})()
The idea is, when I load the index.html in a browser, to have the headerfooter.js script to write my <head> section and my <footer> section with the <links> and <script> I need.
It's actually working perfectly when, for the script, the code I write is the relative path to the script : <script type="text/javascript" src="headerfooter.js"></script>, but it's not working with the absolute path to the root: <script type="text/javascript" src="/headerfooter.js"></script>.
This is a problem, because I would like this to be a template, so that I include this script in every html page I will create in my web folder without having to re-write the path everytime. Did I make a mistake somewhere ?
(PS: is it a bad practice trying to build a template like that ?)
How you run your page will matter.
If you're trying to run it with the file:// protocol (by just opening index.html), an absolute path won't resolve correctly. You'll want to somehow run an local server (there are dozens of ways to do this, depending what all you're using, too large a scope for this question).
If you are running some kind of local server (i.e., http://localhost), then try opening the file directly with http://localhost/headerfooter.js. If that doesn't work, your file isn't quite where you think it is.
I have a page where a user can sign in by submitting a basic form, the data is sent to a separate PHP script (for validation, etc). The PHP script ends with the header() function to direct the user to a welcome page:
// form validation above
header(Location: ../welcome.php);
exit();
I would like to be able to run some JavaScript on the welcome page, however I am noticing that even this basic code won't fire:
$(document).ready(function() {
console.log("ready!");
});
I have split the welcome page using PHP include to separate the header, body, and footer:
The Header:
<?php
session_start();
?>
<!DOCTYPE html>
<html>
<head>
<!-- HOSTED ONLINE -->
<!-- Google Fonts: Lato & Pacifio -->
<link href="https://fonts.googleapis.com/css?family=Lato|Pacifico" rel="stylesheet">
<!-- Font Awesome -->
<script src="https://use.fontawesome.com/3d58889dd8.js"></script>
<!-- Bootstrap CSS -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css">
<!-- Bootstrap jQuery -->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<!-- Bootstrap JavaScript -->
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js"></script>
<!-- jQuery -->
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3.2/jquery.min.js"></script>
<!-- jQuery UI -->
<script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>
<!-- LOCAL -->
<!-- CSS -->
<link rel="stylesheet" type="text/css" href="resources/style.css">
<!-- JavaScript -->
<script type="text/javascript" src="resources/script.js"></script>
<!-- Animate.css -->
<link rel="stylesheet" href="resources/animate.css">
<title>Website Title</title>
</head>
<body class="userBody">
<!-- title card -->
<div class="container-fluid titleCard">
<h1 class="pacificoFont mainTitle">Website Title</h1>
</div>
The Body:
<?php
include_once "user_header.php";
?>
<div>
<?php
echo "welcome " . $_SESSION["username"] . "!<br>";
echo "Your email is " . $_SESSION["email"];
echo '<form action="includes/logout_inc.php" method="POST">
<button type="submit" name="submit">Logout</button></form>';
?>
</div>
<div class="test" id="test">
Test
</div>
<?php
include_once "user_footer.php";
?>
The Footer:
</body>
</html>
I do believe the local JavaScript is properly linked, where it's in the same directory as the CSS and the styling is linked and working. I am also running this locally using MAMP (if that info helps).
It's probably quite noticeable that I am very new at PHP/JavaScript. Any help would be deeply appreciated! Thank you for taking the time :)
the javascript reference should be at the bottom of the HTML page before the closing body tag. Just cut the reference of the javascript to the the page bottom below:
<script type="text/javascript" src="resources/script.js"></script>
</body>
</html>
The problem is that jquery got rendered before your page load.
I tried to implement CDN resources with local fallback support for my webpage.
But now I can't get rid of render-blocking JavaScript and CSS CDN resources for jquery and Bootstrap in the "above-the-fold" content.
I tried to stick to Googles Guidelines but it didn't resolve my problem:
Remove Render-Blocking JavaScript
Optimize CSS Delivery
<html>
<head>
</head>
<body>
<div id="wrapper">...</div>
<!-- jQuery CDN -->
<script src="https://code.jquery.com/jquery-2.2.2.min.js"></script>
<!-- jQuery local fallback -->
<script>
window.jQuery || document.write('<script src="./assets/scripts/jquery-2.2.2.min.js"><\/script>')
</script>
<!-- Bootstrap JS CDN -->
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js</script>
<!-- Bootstrap JS local fallback -->
<script>if(typeof($.fn.modal) === 'undefined') {document.write('<script src="./assets/scripts/bootstrap.min.js"><\/script>')}</script>
<!-- Bootstrap CSS local fallback -->
<div id="bootstrapCssTest " class="hide "></div>
<script>
$(document).ready(function() {
if ($('#bootstrapCssTest').is(':visible') === true) {
$("head ").append('<link rel="stylesheet " href="./assets/styles/bootstrap.min.css">');
}
});
</script>
</body>
</html>
<!-- Bootstrap CSS CDN -->
<link rel="stylesheet " href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css ">
UPDATE: I tried to use the "async/defer" attribute for loading my .js CDN scripts. But it didn't work as my local fallback script gives me "Uncaught ReferenceError: $ is not defined" error because they are executed before jquery async loading had been finished.
Using jQuery library include footer section and below custom code start jquery code
40% CSS code in above-the-fold content (head section using internal stylesheet ) <style type="text/css">...</style>
<html>
<head>
</head>
<body>
<div id="wrapper">...</div>
<div id="bootstrapCssTest" class="hide"></div>
<!-- jQuery CDN -->
<script src="https://code.jquery.com/jquery-2.2.2.min.js"></script>
<!-- jQuery local fallback -->
<script src="../scripts/jquery-2.2.2.min.js"></script>
<!-- Bootstrap JS CDN -->
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js">
</script>
<!-- Bootstrap JS local fallback -->
<script src="../scripts/bootstrap.min.js"></script>
<!-- Bootstrap CSS local fallback -->
<script>
$(document).ready(function() {
if ($('#bootstrapCssTest').is(':visible') === true) {
$("head ").append('<link rel="stylesheet " href="./assets/styles/bootstrap.min.css">');
}
});
</script>
<!-- Bootstrap CSS CDN -->
<link rel="stylesheet " href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css ">
</body>
</html>
Apologies if this is an old question. I have spent a few hours searching for an answer but had no luck.
I'm attempting to convert an existing (primarily jQuery) application to use AngularJS. I've hit a problem where a JavaScript file I am including in index.html is being run too early when being included in my AngularJS application. i.e. by using a <script> tag:
<script type="text/javascript" src="/components/js/theme.js"></script>
This file contains a lot of jQuery which needs the rest of the page to have been rendered to have an effect. So is there a way I can include this script and ensure it is only loaded after the rest of the page has finished loading? I have a set of directives on the page and the script is being loaded before these are rendered.
Update:
Here is the structure of my index.html:
<!DOCTYPE html>
<html lang="en">
<head>
<title>App Title</title>
<base href="/">
<!-- icons and CSS -->
<link href="/img/ico/favicon.ico" rel="shortcut icon"
type="image/vnd.microsoft.icon">
<link href="/css/bootstrap.min.css" media="screen" rel="stylesheet"
type="text/css">
<!-- External Libraries -->
<script type="text/javascript" src="/external/jquery/dist/jquery.min.js"></script>
<script type="text/javascript" src="/external/angular/angular.js"></script>
<!-- Angular Components -->
<script type="text/javascript" src="/components/services/ui.js"></script>
<script type="text/javascript"
src="/components/navigation/js/navigation.js"></script>
<!-- App set and config -->
<script type="text/javascript" src="/js/app/app.js"></script>
<script type="text/javascript" src="/js/app/config.js"></script>
<script type="text/javascript" src="/js/app/routes.js"></script>
<!-- endbuild -->
<!-- Precompiled HTML templates -->
<script type="text/javascript" src="/js/templates.module.js"></script>
</head>
<body ng-cloak>
<!-- directive -->
<top-nav-bar></top-nav-bar>
<div class="content">
<div class="container">
<!-- directive -->
<side-nav-bar></side-nav-bar>
<!-- angular view -->
<div ng-view></div>
</div>
</div>
<!-- directive -->
<adysis-footer></adysis-footer>
<!-- Bootstrapper -->
<script src='/js/app.bootstrap.js' type='text/javascript'></script>
<!-- JAVASCRIPT FILE WHICH NEEDS TO RUN AFTER PAGE HAS LOADED! -->
<script type="text/javascript" src="/components/js/theme.js"></script>
</body>
</html>
As you can see, the "theme.js" file is the last item of the <body>. I have stopped in the file to ensure it is being loaded. But this is always done before the rest of the page has rendered. Could some other JavaScript be interfering upsetting things? Note that I have not included all of the JavaScript files that are being included.
Update 2:
I've added further break points in the JavaScript functions for the directives you can see in my index.html. Each of them is stopped in after the theme.js is executed. I don't know why this is, so I'm mentioning this in case it gives more clues as to the problem.
Update 3:
The first line of the "theme.js" file is:
jQuery(document).ready(function($)
And then the function contains a long series of jQuery selectors to setup events and so on. My understanding is the point of this line is to wait until the document has been loaded. But could something in my setup, e.g. Angular, be preventing this from happening?
I've tried changing this line to:
angular.element(document).ready(function($)
and whilst this does lead to the content on the function to be run later, it's still not after the whole document has loaded.
Make sure it's at the end of your HTML Body and not in the header section. If it's in the head section it'll load before the page renders.
I am trying to use share buttons from http://www.shareaholic.com, but I having issues with loading the buttons on elements loading asynchronously.
First of all, the following code works on a static page.
<html>
<head>
<script type='text/javascript'
src='//dsms0mj1bbhn4.cloudfront.net/assets/pub/shareaholic.js'
data-shr-siteid='000000000000000000000000000000000'
data-cfasync='false'
async='async'>
</script>
</head>
<body>
<! -- this loads fine -->
<div class='shareaholic-canvas' data-app='share_buttons' data-app-id='99999999'></div>
</body>
</html>
But if there is an element that loads asynchronously, it doesn't load the share buttons.
##### index.html ######
<html>
<head>
<script type='text/javascript'
src='//dsms0mj1bbhn4.cloudfront.net/assets/pub/shareaholic.js'
data-shr-siteid='000000000000000000000000000000000'
data-cfasync='false'
async='async'>
</script>
</head>
<body>
<!-- this section gets loaded after index.html loaded -->
<blog-content></blog-content>
</body>
</html>
##### blog-content.html #####
<template>
<!-- some blog content here -->
<div class='shareaholic-canvas' data-app='share_buttons' data-app-id='99999999'></div>
</template>
I am guessing that is because section gets executed before section finish loading, but I am not sure what would be the best way to handle this situation. I am using Aurelia.js as a framework.
The script tag that loads shareaholic.js has the async attribute so it will execute asynchronously and won't block the rest of the page load.
While shareaholic.js is loading aurelia has the opportunity to start up and replace the content of the <body> element with the aurelia app.
By the time shareaholic.js has loaded the "shareaholic-canvas" div no longer exists in the dom.
You might try creating a shareaholic custom element like this:
shareaholic.html
<template>
<script type='text/javascript'
src='//dsms0mj1bbhn4.cloudfront.net/assets/pub/shareaholic.js'
data-shr-siteid='000000000000000000000000000000000'
data-cfasync='false'
async='async'>
</script>
<div class='shareaholic-canvas' data-app='share_buttons' data-app-id='99999999'></div>
</template>
And then using the custom attribute like this:
app.html
<template>
<require from="shareaholic.html"></require>
<shareaholic></shareaholic>
</template>
<html>
<head>
<script type='text/javascript'
src='//dsms0mj1bbhn4.cloudfront.net/assets/pub/shareaholic.js'
data-shr-siteid='000000000000000000000000000000000'
data-cfasync='false'
async='async'>
</script>
</head>
<body>
<! -- this loads fine -->
<div class='shareaholic-canvas' data-app='share_buttons' data-app-id='99999999'></div>
</body>
</html>