How to invoke javascript function when # is present in URL - javascript

I am trying to call JavaScript function when # is present in URL. I know normal behavior is to navigate / scroll to the specific tag. But could not find how to invoke a JavaScript function.
The below example is close but not solving my problem.
What is the meaning of # in URL and how can I use that?

You might be able to leverage the hashchange event to trigger the function, assuming you don't just want to keep polling the location to see if it changes.
DOCS: https://developer.mozilla.org/en-US/docs/Web/API/Window/hashchange_event
This code snippet will add the listener to the current page, then manipulate the hash and fire the function, displaying the new hash value. You could call any function here.
window.addEventListener('hashchange', function() {
alert(location.hash);
});
window.location += "#test";

var hash = window.location.hash;
if(hash){
// do something
}

<script>
if (window.location.href.includes('#')) {
// run your code here
}
</script>

use a location.hash function will solve your problem
var hash = window.location.hash.replace(/#/g, '');
if(hash){
// found a hash
console.log("heyy I found a hash")'
}
else{
// did not find a hash
console.log("Uh oh")
/*
try using :
window.location = window.location + '#' + "some random variable"
to create a new URL and every time the page loads find the hash and
display the wanted data.
*/
}
PS: this only works if your URL is like example.com/#xyz
then it will give you xyz as a console output. This may sound
vague but if you do this you may get a Idea

Related

Where does window.location.reload() get its value from?

Trying reload the current page without the fragment identifier (i.e. hash symbol #) and using the following bit of code to do so which functions correctly:
var path = window.location.href.replace(/(\#.*)/,'');
window.location = path;
I'm also aware that the above second line could read window.location.href = path; which brings me to the next part.
Before arriving at the above code we tried:
var path = window.location.href.replace(/(\#.*)/,'');
window.location.href = path;
window.location.reload();
However that didn't work for us as the href value wasn't seeming to be set and I feel that reload() was calling before or instead of the href = path bit.
This got me curious, where does the reload() function for window.location get its value from to reload the page?
If I click around a page jumping between fragment identifiers (perhaps a table of contents) then the address bar updates accordingly and when called, window.location.reload() will do so with the correct fragment. Yet if I manually type something in the address bar and then call the reload() function it will not load with my manual entry but rather the last 'computer defined' value.
My guess is the user agent (in this particular case Chrome 44) is listening and updating the value which each interaction with the DOM or within the window. I checked out the HTML5 spec and the MDN Location.reload() docs for information and either it wasn't there or I'm too dense to find/understand it.
Can anyone explain to me where reload() gets it's value and how it is updated through a users interaction with a page?
What is the exact difference between using window.location = path and window.location.href = path in this scenario?
The location (value) only changes after a successful navigation! In other words, the location instance represents the currently loaded page (including the fragment).
Assigning a new value to window.location.href (re)loads a page.
So when you call window.location.href = path; the browser wants to load the new URL (the one without the #). But if you immediately call window.location.reload(); it's like saying "No, wait! Reload the current page (the one with the #)".
If you want to remove the "#" part of the url you have to explicitly set:
window.location.hash = ""
and then call window.location.reload().
window.location = path is nothing more than syntactic sugar for window.location.href = path.

issue in IE browser while opening a new window

i have this small piece of code
$("a").live("click",function(event) {
<% String lifeCare=LifeEventProperties.getInstance().getProperty("lifeCare");%>
var s="<%=lifeCare%>";
var href = $(this).attr('href');
if (href.indexOf(s) != -1) {
loadLifeCare(href) ;
event.preventDefault();
}
});
function loadLifeCare(href)
{
var wnd=window.open('/NASApp/benemain/LifeCareSite');
setTimeout(function() {
wnd.location.href = href;
}, 6000);
}
here in my jsp page i have checked for a particular word in url's using jquery and that word is like "something.com" which i am fetching from property file ,now if this something.com is found in the url which a user has clicked then i am calling a javascript function which then opens a new window with an internal site url which is taking care of user's session for that page which has this something.com and then i reload the page with "href" that user actually clicked .
the problem is its working good in all browser's other IE and my client loves IE,
IE is directly going to the link which bypassing loadLifeCare method and giving me this error on console
The value of the property 'loadLifeCare' is null or undefined, not a Function object
can any suggest something why it is happening ?is there anything in this code that IE don't understand ,i am getting a feeling that issue is with window.open() maybe but i am not sure and i don't even know any alternative if that's the case.
please help me and tell me if you need any clarification on anything..
Try this
fixed the deprecated live
used a better method to open windows (yours may very likely give access denied;
moved the function to before it is used and wrapped the click event handler in a a load handler
function loadLifeCare(href) {
var wnd=window.open('/NASApp/benemain/LifeCareSite',"lifeCareWin");
if (wnd) setTimeout(function() {
window.open(href,"lifeCareWin");
}, 6000);
}
$(function() {
$("a").on("click",function(event) {
<% String lifeCare=LifeEventProperties.getInstance().getProperty("lifeCare");%>
var s="<%=lifeCare%>";
var href = $(this).attr("href"); // this.href might be useful too
if (href.indexOf(s) != -1) {
loadLifeCare(href) ;
event.preventDefault();
}
});
});

Button onClick event and Href-Location

I used a solution given by "Chrules" found in this discussion:buttons with no href, onclick etc
like this :
<button id="clickable" >Click Me!!</button>
......
$("#clickable").click(function(){
// Send user to this link
insertRecord(); //SQLite Code
location.href = "game.html";
// location.href = "http://www.takemehere.com"; });
So When i used the location.href like he putted it (= "http://www.takemehere.com";) The insertRecord() method is done with success (the object is added to the database)
But when I use the location.href = "game.html"; the game.html page is opened but the insertRecord() method is not done i tried to put the full path of game.html but the same problem persist Have you any idea please ? Thank u in advance
I think insertMethod() calls some async functions to do database updating. So you should use a callback before doing anything else.
Something like this (i don't know what is inside of insertRecord method);
function insertRecord(callback) {
// do all sorts of database job
// when it's finished
// fire your callback
callback();
}
insertRecord(function() {
location.href = "page.html";
});
EDIT: After your comment, i see you already have defined a function to run after sql which is loadAndReset(). So simply put location.href = "page.html" in that function, and it should work.

How to run a javascript function using the # in the url?

hi this all started when i ran a function (lets call it loadround) that altered the innerHTML of an iframe. now once loadframe was loaded there were links in the iframe that once clicked would change the iframe page. the only problem is when i click the back button the loadround page was gone. i've thought about this numerous times to no avail. so i tried this code.
loadround
then
function loadround(a,b){
window.location.hash = "#loadround('"+a+"','"+b+"')";
var code = "<(h2)>"+a+"</(h2)><(h2)>"+b+"</(h2)>"
var iFrame = document.getElementById('iframe');
var iFrameBody;
iFrameBody = iFrame.contentDocument.getElementsByTagName('body')[0]
iFrameBody.innerHTML = code;
}
(the brackets in the h2 are intentional)
then i would try to reload the function by possibly an onload function but for now i was testing with a simple href as followed.
function check(){
var func = location.hash.replace(/#/, '')
void(func);
}
check
unfortunately the check code doesn't work and im almost certain there is an easier way of doing this. i tried changing the src of the iframe instead of the innerhtml and there was the same problem. thanks in advance
The modern browsers are starting to support the event window.onhashchange
In the meantime you can use the workaround proposed by Lekensteyn or maybe you can find something useful here: JavaScript/jQuery - onhashchange event workaround
You are misunderstanding the function void, which just make sure the return value is undefined. That prevents the browser from navigating away when you put it in a link. You can test that yourself by pasting the next addresses in your browser:
javascript:1 // note: return value 1, browser will print "1" on screen
javascript:void(1) // note: undefined return value, browser won't navigate away
It's strongly discouraged to execute the hash part as Javascript, as it's vulnerable to XSS without proper validating it. You should watch the hash part, and on modification, do something.
An example; watch every 50 milliseconds for modifications in the hash part, and insert in a element with ID targetElement an heading with the hash part. If the hash part is not valid, replace the current entry with home.
var oldHash = '';
function watchHash(){
// strip the first character (#) from location.hash
var newHash = location.hash.substr(1);
if (oldHash != newHash) {
// assume that the parameter are alphanumeric characters or digits
var validated = newHash.match(/^(\w+)$/);
// make sure the hash is valid
if (validated) {
// usually, you would do a HTTP request and use the parameter
var code = "<h1>" + validated[1] + "</h1>";
var element = document.getElementById("targetElement");
element.innerHTML = code;
} else {
// invalid hash, redirect to #home, without creating a new history entry
location.replace("#home");
}
// and set the new state
oldHash = newHash;
}
}
// periodically (every 50 ms) watch for modification in the hash part
setInterval(watchHash, 50);
HTML code:
Home
About Me
Contact
<div id="targetElement">
<!-- HTML will be inserted here -->
</div>

Change hash without triggering a hashchange event

I'm using the hash to load content dynamically. To make the back button work I am capturing hash changes. However sometimes I need to change the hash without triggering the hash changed function (eg, when the page was redirected server side and I need to update the hash once the content has returned.)
The best solution I have come up with is to unbind the hashchange event, make the change and then rebind it. However, as this happens asynchronously, I am finding that it rebinds too quickly and still catches the hash change.
My solution at the moment is very poor: Rebinding in a setTimeout. Does anyone have a better idea?
$(window).unbind( 'hashchange', hashChanged);
window.location.hash = "!" + url;
setTimeout(function(){
$(window).bind( 'hashchange', hashChanged);
}, 100);
Edit:
Amir Raminfar's suggestion prompted me to a solution that does not require a timeout.
I added a class variable
_ignoreHashChange = false;
When I want to change the hash silently I do this:
_ignoreHashChange = true;
window.location.hash = "!" + url;
and the hash changed event does this :
function hashChanged(event){
if(_ignoreHashChange === false){
url = window.location.hash.slice(2);
fetchContent(url);
}
_ignoreHashChange = false;
}
You could use history.replaceState and append the hash, to replace the current URI without triggering the hashchange event:
var newHash = 'test';
history.replaceState(null, null, document.location.pathname + '#' + newHash);
JSFiddle example
You can have a function like this:
function updateHash(newHash){
...
oldHash = newHash
}
then in your setTimeOut you need to do
function(){
if(oldHash != currenHash){
updateHash(currenHash);
}
}
So now you can call update hash manually and it won't be triggered by the event. You can also have more parameters in updateHash to do other things.
By the way, have you looked at the jquery history plugin? http://tkyk.github.com/jquery-history-plugin/

Categories