Javascript function requiring two clicks - javascript

javascript is completely new to me. I am a relatively inexperienced rails developer. I have implemented something in a rails 3 app called joyride, which is a jquery plugin and pops messages up for users giving them a "tour of the page". This is the script that runs the tour nicely when the page is loaded
:javascript
$(window).load(function() {
$('#joyRideTipContent').joyride({
modal:true,
expose: true
});
});
That works perfectly. My problem is that I need it to run when a button is clicked rather than on loading of the page.
So I started with a simple button on the HAML page
%button#myBtn
Lauch tour
That gives me my button. Then I wrote a function (forgive me its my first) to fire the code when the button is pushed.
:javascript
var myBtn = document.getElementById('myBtn');
myBtn.addEventListener('click', function(event) {
$("#joyRideTipContent").joyride({
modal:true,
expose: true
});
});
This is where it gets strange. The code works - on the SECOND click. Clearly something is being passed in the first time, and then executed the second time, but I am way out of my depth, can anyone help!
thanks
EDIT:
changed the code to this on advice, but same problem exists...
$(function() {
$("#myBtn").click( function()
{
$("#joyRideTipContent").joyride({
modal:true,
expose: true
});
}
);
});
EDIT: added a jsfiddle for anyone with time to have a look at http://jsfiddle.net/garethburrows/beonc06z/

Try
$('#myBtn').on('click', function(event) {
$("#joyRideTipContent").joyride({
modal:true,
expose: true,
autoStart: true
});
});
you're mixing jquery and classic js - not good.

Related

Ajax auto refresh causing my jquery embed script to repeat endlessly

OK, my disclaimer, regarding script, I'm green as a cucumber.
I've recently set up jquery-oembed on my site (phpbb forum), it's a code which auto embeds media content from various sites like youtube, twitter, facebook etc...
It works great, except I'm having trouble integrating it into my chat box. The chat functions through an ajax code which auto refreshes in intervals. Depending on where I put my script, the embed will either show a link and not embed until you manually refresh the page....or....it will embed, but constantly repeat itself over and over every time the ajax refreshes. I've been playing around with this a lot, I try to avoid bothering you guys unless it's absolutely necessary.
Here's the oembed code, which works find on the posts in my site.
(function($) {
$(document).ready(function() {
$(".avatarMessage .postlink").oembed(null, {
embedMethod: "append",
startClosed: true,
maxWidth: 300,
});
});
})
The best I could find through searching was this snippet which I tried. If I change it to add:
(function($) {
$(document).ready(function() {
$(".avatarMessage .postlink").oembed(null, {
embedMethod: "append",
startClosed: true,
maxWidth: 300,
});
while (update.firstChild) {
update.removeChild(update.firstChild);
}
});
})
Then it won't keep repeating it, but it also won't allow for new url's to embed, so I can't use this one.
Is there something I could add for this which would limit the removeChild to just the content of that message, or perhaps another idea that I'm just completely not seeing (don't get frustrated with me, I'm trying, I just don't have much experience outside the basic html and css).
In case anyone is interested, here is the ajax code which fires the auto refresh.
https://raiderforums.com/mchat/mchat_ajax_mini.js
Thanks for putting up with me :)
This is happening because each time you call $(".avatarMessage .postlink").oembed(....) all matched elemenets will be compiled even if they are already compiled. To prevent that you can add a new-post class and remove it after the element is compiled/embeded:
(function($) {
$(document).ready(function() {
$(".avatarMessage .postlink.new-post").oembed(null, {
embedMethod: "append",
startClosed: true,
maxWidth: 300,
}).removeClass('new-post');
});
})
Thus, the elements will not be matched on the next oembed call.
Here is another alternative, it uses a flag instead:
(function($) {
$(document).ready(function() {
$(".avatarMessage .postlink").each(function(index, element) {
var $el = $(element);
//If already embedded just return
if ($el.data('oembedded')) return;
//set the flag
$el.data('oembedded', true);
$el.oembed(null, {
embedMethod: "append",
startClosed: true,
maxWidth: 300,
});
});
});
});
I hope this will help you.

Touchwipe integration - one-page-site script

I have been spending most of the day troubleshooting and searching for an answer to my question regarding TouchWipe (http://www.netcu.de/jquery-touchwipe-iphone-ipad-library) integration on this custom one-page-site script (http://www.joerg-niemann.de/blog/up-down-left-right-scrolling-single-page-website/) based on Parallax, which was exactly what I was searching for for my latest project.
The script itself does everything I want it to, beautiful transitions and keyboard control straight out of the box, but I can't for the life of me, get the hang of how to integrate TouchWipe.
The idea is, that visiting iOS user should be able to wipe/swipe/slide between the pages with their finger with the same ease, as clicking the navigation arrows, or using a keyboard currently does.
My problem is failing at trying to call the same functions for TouchWipe gestures as clicking the arrows, or using the keyboard. The on-click function calling part of the script looks as follows:
function setRight(page, text) {
$("#rightText").text(text);
$("#rightControl").show().unbind('click').click(function () {
parallax[page].right();
});
rightKey = function () {
parallax[page].right();
};
}
I'm by no means a JavaScript developer, and since I haven't been able to find a decent answer anywhere (shame on me for using a custom script without a FAQ) on how to integrate touch with this lovely script, I'm reaching out to you.
I've tried numerous different variations of calling the necessary functions on wipe/swipe/touch, but all have failed to function. I can't for the life of me figure out why this isn't working:
<script>
$(document).ready(function(){
$('body').touchwipe({
wipeLeft: function(){ parallax[page].left(); },
wipeRight: function(){ parallax[page].right(); },
wipeUp: function(){ parallax[page].top(); },
wipeDown: function(){ parallax[page].bottom(); }
})
})
</script>
I hope I've made myself clear, otherwise feel free to take a jab at me, and I will supply further information if requested. I'm sure there is a simple explanation to why it isn't functioning the way I'd like it to, but I just can't seem to figure it out.
I finally figured out how to implement the TouchWipe script with Parallax.js.
Here's the answer for anyone experiencing the issue as myself in the future:
<script>
$(document).ready(function(){
$('#index').touchwipe({
wipeLeft: function(){ $(".control").hide(); parallax.right.right(); },
wipeRight: function(){ $(".control").hide(); parallax.left.left(); },
wipeUp: function(){ $(".control").hide(); parallax.top.top(); },
preventDefaultEvents: true
});
$('#right').touchwipe({
wipeRight: function(){ $(".control").hide(); parallax.index.left(); },
preventDefaultEvents: true
})
$('#left').touchwipe({
wipeLeft: function(){ $(".control").hide(); parallax.index.right(); },
preventDefaultEvents: true
})
$('#top').touchwipe({
wipeDown: function(){ $(".control").hide(); parallax.index.bottom(); },
preventDefaultEvents: true
})
});
</script>
Turns out I had to call each function seperatly, why, I do not know, but for some reason it wouldn't accept calling both functions in the combined function.
So first, call the functions that hide the controls like so (seperate by semicolon, so you can add another function):
$(".control").hide();
Then you have to call the transition and page change like so (the last ID (parallax.xxxx.ID is used to call from which side you want the new page to slide in from - as I was using TouchWipe to set up the site as a webapp, I would of course slide the page in from the opposite site: wipeUp triggers parallax.top, wipeLeft triggers parallax.right etc.):
parallax.index.bottom();
Here is the new, improved and kickass jsfiddle:
http://jsfiddle.net/Q96uH/2/
Code on my fellow stackers!

pjax losing the rails javascript

I have some javascript below which loads upon first page load, but then get lost by pjax.
Any way to solve this pls? I just have pjax running on the in application.html file so should i make it less aggressive or is there some js magic that will hold my js code.
$(document).ready(function() {
$("#note_label_tokens").tokenInput("/labels.json", {
crossDomain: false,
prePopulate: $("#note_label_tokens").data("pre"),
theme: "facebook"
});
});
Make the JS into a function, and then call it on document.ready and when the end.pjax event is fired.

jQuery UI DatePicker Hangs on second call

I'm creating an ASP.NET MVC3 app that uses jQuery Datepicker and Timepicker inside a dialog. The code is pretty simple, just localization:
$(document).ready(function () {
$('.datepicker').datepicker({
dateFormat: "dd/mm/yy",
monthNames: ['Janeiro', 'Fevereiro', 'Março', 'Abril', 'Maio', 'Junho', 'Julho', 'Agosto', 'Setembro', 'Outubro', 'Novembro', 'Dezembro'],
dayNames: ['Domingo', 'Segunda', 'Terça', 'Quarta', 'Quinta', 'Sexta', 'Sábado'],
dayNamesMin:['Dom', 'Seg', 'Ter', 'Qua', 'Qui', 'Sex', 'Sáb'],
});
$('.timepicker').timepicker({
timeOnlyTitle: 'Titulo',
timeText: 'Tempo',
hourText: 'Hora',
minuteText: 'Minuto',
secondText: 'Segundo',
currentText: 'Atual',
closeText: 'Fechar'
});
});
No secret here.
The datepicker works fine when used for the first time. When I used a second time, the browser (any browser) hangs and offers me to stop script execution of jquery-1.6.4.min.js. To reproduce the error, I just reload the whole page.
What am I missing here?
Update
Adding code for the modal:
First, I configure that everything with class='modal' will have some basic parameters:
$('.modal').dialog({
resizable: false,
draggable: false,
modal: true,
position: 'center',
autoOpen: false
});
Then, I extend jQuery with some functions. One of them sets the buttons and submits:
$.extend({
modalPopup: function (modal) {
var $modal = $('#' + modal);
var $form = $modal.find('form').first();
$modal.dialog({
buttons: {
"OK": function (e) {
$.validator.unobtrusive.parse($form);
if ($form.valid()) {
$('.ui-dialog button:contains("OK")').button('disable');
$.post($form.attr('action'),
$form.serialize(),
function (data) {
$modal.dialog('close');
$('#maindiv').load(telaAtual);
});
}
},
"Cancelar": function () { $(this).dialog("close"); }
},
open: function () {
$modal.unbind('submit');
$modal.submit(function () {
$modal.parents('.ui-dialog').first().find('.ui-button').first().click();
return false;
});
$(this).find('.ui-dialog :input').first().blur();
}
})
.dialog('open');
}
})
UPDATE
I did some research and found that the problem is with DatePicker and Ajax. Everytime Maybe the Datepicker is "double called" everytime an ajax call is made. Something very similar to this question. But the Datepicker hangs even if I just close the dialog, meaning that the problem starts when the first ajax call is made.
Anyone can help me to fix this? Maybe returning false somewhere or destroying the datepicker before creating a new one.
UPDATE 01/12/2012
Sorry for the delay, guys and thanks for the help.
None of the solutions posted here worked. But, again, I thank you all for the help.
I found a boolean property $.datepicker.initialized that returns false on the first time I load the dialog, and returns true the second time. Now I can avoid the crash the second time. First problem solved.
But I still don't know how to "reinitialize" the datepicker so it can be shown when the textbox is clicked.
Still looking for a way to reinitialize it.
Also, changed the OK button code to this and works fine:
"OK": function (e) {
$.validator.unobtrusive.parse($form);
if ($form.valid()) {
$modal.parents('.ui-dialog').find('button:contains("OK")').button('disable');
$.post($form.attr('action'),
$form.serialize(),
function (data) {
if (submodal) {
carregaParcial(titulo, id);
}
else {
$('#maindiv').html(data);
}
removeModal($modal);
});
}
The $form.serialize() function already returns the html in the data variable, so, I just need to get its content and set as HTML of the maindiv.
Try this jquery datetimepicker function when submit the dialog or cancel the dialog.
$('.datepicker').datepicker("destroy");
You are using the "load" method incorrectly for your purposes. jQuery default behavior for load method when no selector is passed is to go to the URL specified, execute the JavaScript that exists on that page then load in the DOM into the jQuery object calling it.
If you pass a selector into your load method, the jQuery load method will not execute the script and will only load the dom in you jQuery object.
Change it to:
$('#maindiv').load(telaAtual + ' #maindiv > *')
This assumes your "telaAtual" URL has #maindiv on the page and then gets all of its children and loads them into "#maindiv" jQuery object.
We can go further and find out the particulars of the hanging but solving the load issue will be the first thing to consider. If it continues hanging it is worth further investigation.
Just a guess, not an answer:
Try to remove the dialog, not just close it.
...
$modal.dialog('close');
$modal.remove();
...
Maybe that helps?
BTW: With this you are clicking on the "OK" button by opening the dialog, don't you?
$modal.parents('.ui-dialog').first().find('.ui-button').first().click();
And then you load some content, so that happens when the dialog is opening?
$('#maindiv').load(telaAtual);
And if the telaAtual returns content which will open the dialog again, you are maybe stucked in an endless loop?
In this code the only very minor syntax issue might be the last unnecessary comma after the dayNamesMin. Shouldn't cause any hanging, but remove it and give it a try. Other than that this code looks fine, so the issue is somewhere else.
I've the same issue here, and in my case, that solution worked:
http://forum.jquery.com/topic/datepicker-in-modal-dialog-problem-with-populating-a-date-field
I just assign a random string to datepicker's input ID.

Jquery Fancybox not working after postback

I have a Fancybox (or more accurately) a number of fancy boxes on an asp.net page.
My Fancybox (jquery plugin) works fine until a postback occurs on the page then it refuses to work.
Any thoughts? Anyone experienced similar behaviour?
UPDATE : Some Code..
I have a databound repeater with a fancybox on each repeating item.
They are instanciated by (outside the repeater)
$(document).ready(function() {
$("a.watchvideo").fancybox({
'overlayShow': false,
'frameWidth' : 480,
'frameHeight' : 400
});
});
The anchor tag is repeated..
href="#watchvideo_<%#Eval("VideoId")%>"
As is a div with
id="watchvideo_<%#Eval("VideoId") %>
As is a script element that instanciates the flash movies
Yes the VideoIds are being output the the page.
UPDATE : It's not a problem with the flash..
It is not a problem with the flash as i've tried it without the flash, it wont even pop a window with a simple message in.
UPDATE : I wonder if it is the updatepanel.
Rebinding events in jQuery after Ajax update (updatepanel)
-- lee
The problem is in using $(document).ready() to bind the fancybox. This code is only executed once, when the page is originally loaded. If you want the fancybox functionality on every postback, synchronous or asynchronous, replace the $(document).ready() with pageLoad(sender, args). i.e.
function pageLoad(sender, args) {
$("a.watchvideo").fancybox({
'overlayShow': false,
'frameWidth' : 480,
'frameHeight' : 400
});
}
see this answer for more info
Could it be that the instantiating code is being inserted at a piece of code which is not run after a postback?
It was the Update panel as described
here.. Rebinding events in jQuery after Ajax update (updatepanel)
As suggested I simply replaced
$(document).ready(function() {
$("a.watchvideo").fancybox({
'overlayShow': false,
'frameWidth' : 480,
'frameHeight' : 400
});
});
with
function pageLoad(sender, args)
{
if(args.get_isPartialLoad())
{
$("a.watchvideo").fancybox({
'overlayShow': false,
'frameWidth' : 480,
'frameHeight' : 400
});
}
}
and it worked!
-- Lee
This might help someone else, but FancyBox appends it's code to the <body> element... which is all fine and well, but resides OUTSIDE the asp.net <form> element. My postback problems went away when I modified FancyBox to append its dom objects to the <form> element:
$('body form:first').append( ... );
I had a similar problem with a paged grid-view. The first page of the grid was launching the fancybox while the remaing did not.
I thought it could be an issue related to the UpdatePanel which refreshes only a portion of the screen.
I solved the issue replacing this:
<script>
$(document).ready(function () {
$("a.small").fancybox();
});
</script>
with this:
<script>
function pageLoad(sender, args) {
$("a.small").fancybox();
};
</script>

Categories