I'm trying to trigger an event when the hash changes inside my url using the method onhashchange. I'm calling it, but it doesn't ever seem to get executed.
I've tried the following.
$(function () {
window.addEventListener("onhashchange", function () {
alert("Here");
});
window.onhashchange = function () {
alert("Changed");
}
)};
is there any reason why these functions aren't being called?
You should write 'hashchange' instead of 'onhashchange' in your first example.
This code works fine for me, at least in Chrome:
window.addEventListener('hashchange', function(e){
console.log('changed');
})
Here is short code-snippet:
https://jsfiddle.net/bm8jjwmq/
if ("onhashchange" in window) {
alert("The browser supports the hashchange event!");
}
▲ For Support // ▼ implementation
function locationHashChanged() {
if (location.hash === "#somecoolfeature") {
somecoolfeature();
}
}
window.onhashchange = locationHashChanged;
Source: https://developer.mozilla.org/en-US/docs/Web/API/WindowEventHandlers/onhashchange
Related
I'm sure this is something simple that I am missing but I'm at a loss.
I have this block of jQuery:
jQuery("span.frm_inline_total").digits();
jQuery(".frm_input_group").on("blur", "input", function () {
jQuery("span.frm_inline_total").digits();
});
jQuery(".frm_range_container input").mouseup(function () {
jQuery("span.frm_inline_total").digits();
console.log("mouse up");
});
jQuery(".frm_range_container input").mousedown(function () {
jQuery("span.frm_inline_total").digits();
console.log("mouse down");
});
That calls a function to place commas in some field numbers. I don't think it's relevant, but here is the function:
jQuery.fn.digits = function () {
return this.each(function () {
jQuery(this).text($(this).text().replace(/(\d)(?=(\d\d\d)+(?!\d))/g, "$1,"));
})
}
My issue is this. Everything works except when I try to call digits() using mouseup(). It logs the mouseup() event with 'console.log', and the mousedown() event correctly works, but no mouseup(). ...alert("mouse up") works, just not 'digits'.
For what it's worth, I'm placing this event on a built-in slider in a drag-and-drop website I am editing. My "development" is limited to client side code. There is already an event on it to retrieve the new values that I thought might be interfering, but then I don't understand why it would fire logs or alerts.
Assuming your HTML structure is something like this:
<div class="frm_range_container">
<div class="frm_input_group">
<span class="frm_inline_total">Value to replace</span>
<input value="Click me"></input>
</div>
</div>
and the rest of your code works, changing the code like below should produce desired output.
// added logs to check in console, digits function is the same
$.fn.digits = function () {
console.log('digits'); // test to see if reaches digits() function
return this.each(function () {
// this should be the correct element.
$(this).text(
$(this).text().replace(/(\d)(?=(\d\d\d)+(?!\d))/g, "$1,")
);
})
}
$(".frm_range_container input").on('mouseup mousedown', function (e) {
console.log(e.type);
$("span.frm_inline_total").digits();
});
If you want to only target span.frm_inline_total contained in each frm_range_container, you can use $("span.frm_inline_total", this).digits(); for that
I use the following jQuery code to process keys which are pressed in various input tags:
$(document).ready( function () {
$("input").keydown(function (e) {processKeys(e);});
...
It works great...
In a separate Javascript file I have a function which receives the event call:
function processKeys(e) {
key=e.which;
if (key==27) {
$("#searchCDB").hide();
}
}
So, is there a way for me to identify the <input> tag which caused the event at the event layer... What I mean is here, in some way like:
$("input").keydown(function (e) {processKeys($("#this"),e);});
I know my attempt is absurd, but any suggestion that works will be appreciated.
DK
You can pass in this to your processKeys function:
$(document).ready( function () {
$("input").keydown(function (e) {
processKeys(e, this);
});
});
function processKeys(e, obj) {
console.log(obj.id); //logs ID of keypressed input
key=e.which;
if (key==27) {
$("#searchCDB").hide();
}
}
Demo: http://jsfiddle.net/uE7ZD/
I have a block of code like so:
function doSomething() {
someVar.on("event_name", function() {
$('#elementId').click(function(e) {
doSomething();
});
});
}
// and on document ready
$(function () {
$('#anotherElemId').click(function () {
doSomething();
});
});
The problem that I'm encountering is that when I call doSomething() from anotherElemId click event(that is binded on document ready) it works as expected, but calling it recursively from elementId click doesn't work.
Any ideas? Thinking is something trivial that I'm missing.
Is someVar an actual jQuery reference to a dom element? (e.g. $('#someitem'))
The second problem is you cant put a .click event inside a function that you would like to instantiate later on. If you are trying to only allow #elementId to have a click event AFTER some previous event, try testing if a tester variable is true:
var activated = false;
$(function () {
$('#anotherElemId').click(function () {
activated = true;
});
$('#secondElemId').on("event_name", function() {
if (activated) {
// code that happens only after #anotherElemId was clicked.
}
});
});
I want a mouseover event to be handled after a delay, and then be inactive until a page refresh.
This is my code thus far:
$(function() {
$("#page-flip").mouseover(function() {
$(".box").toggleClass("box-change");
$(".films").toggleClass("films-change");
$(".synopsis").toggleClass("synopsis-change");
});
});
How do I add a time delay to this and than have it inactive after being fully triggered once? Thank you :)
You can use .one() to have an event handler only trigger once:
$(function() {
//bind a mouseover event handler that will fire only once
$("#page-flip").one('mouseover', function() {
//set a timeout so the code runs after half a second
setTimeout(function () {
//run your code here
$(".box").toggleClass("box-change");
$(".films").toggleClass("films-change");
$(".synopsis").toggleClass("synopsis-change");
}, 500);
});
});
Here is a demo: http://jsfiddle.net/jasper/fWakf/3/
Documentation: http://api.jquery.com/one
You could also use .off():
$(function() {
$("#page-flip").on('mouseover', function() {
//remove this event handler so it doesn't fire in the future
$(this).off('mouseover');
setTimeout(function () {
$(".box").toggleClass("box-change");
$(".films").toggleClass("films-change");
$(".synopsis").toggleClass("synopsis-change");
}, 500);
});
});
Here is a demo: http://jsfiddle.net/jasper/fWakf/4/
Note that .on() is new in jQuery 1.7 and in this case is the same .bind(). .off() is also new so if you're using older than 1.7 and .bind(), then use .unbind().
Edit This answer is worse than Jasper's. But the pattern it uses doesn't require jQuery, so I'm leaving it up.
Well, you could go simple and use a global variable, or complicated and remove the event entirely.
the simple one looks like this.
var __GlobalEventFired = false;
$(function() {
$("#page-flip").mouseover(function() {
if(!__GlobalEventFired)
{
__GlobalEventFired = true;
$(".box").toggleClass("box-change");
$(".films").toggleClass("films-change");
$(".synopsis").toggleClass("synopsis-change");
}
});
});
I am trying to ajax load the center content and update the URL without changing the page. This all works fine except until I try to access the history. It seems window.pushState is not recording my URL's properly or popstate event is not working properly. I can successfully ajax load the previous page, but if I press back more than once, it stays on the same page. Any help would be greatly appreciated!
$(document).ready(function() {
$('area, .ajax_link').live('click', function(event) {
change_image(this, event);
});
window.addEventListener('popstate', function(event) {
change_image(window.location, event);
});
});
function change_image(e, event) {
if($(e).attr('target') != '_blank') {
event.preventDefault();
$.post(
base_url+'/kit/ajax_load',
{ url: this_url},
function(return_data) {
$('#content img').attr('src', return_data.image_src);
$('map').html(return_data.imagemap);
},
'json'
);
history.pushState(null, null, this_url);
update_links(this_url);
}
}
Problem Solved
#Oliver Nightingale: I needed to remove history.pushState from my change_image function. You can not call history.pushState during an onpopstate. Here is the entire working code. I shortened it above only to include the necessary parts in question. I will be adding some fallbacks next. This is tested and works in Chrome & Firefox. Tested and does not work in IE.
$(document).ready(function() {
$('area, .ajax_link').live('click', function(event) {
history.pushState(null, null, $(this).attr('href'));
change_image(this, event);
});
window.addEventListener('popstate', function(event) {
change_image(window.location, event);
});
});
function change_image(e, event) {
if(!e instanceof jQuery) {
var this_url = e;
}
else {
var this_url = $(e).attr('href');
}
if($(e).attr('target') != '_blank') {
event.preventDefault();
$.post(
base_url+'/kit/ajax_load',
{ url: this_url},
function(return_data) {
$('#content img').attr('src', return_data.image_src);
$('map').html(return_data.imagemap);
},
'json'
);
update_links(this_url);
}
}
Is the main body of change_image function happening onpopstate? If so it looks like you are pushing a new state everytime you pop a state, this could be causing some issues.
If you are using pushState for routing you could try using a library such as Davis to make things simpler.
How is $(e).attr('target') != '_blank' when e is window.location ?
As you are using the native HTML5 History API, you'll also want to have a check before history.pushState(null, null, this_url); to only call that if we are from a link.
Plus window.addEventListener('popstate', function(event) { the variable event here is actually the state's data.
See the following gists for working examples:
https://gist.github.com/balupton/1145804 - without history.js
https://github.com/browserstate/ajaxify - with history.js