Take the 2-minute tour ×
Stack Overflow is a question and answer site for professional and enthusiast programmers. It's 100% free, no registration required.

I have a simple ASP.Net MVC 4 app designed for mobile use. The application uses the in built C# Visual Studio template for Mobile application which comes with Forms Authentication and an Accounts view and controller for handling the login.

The application has the in built login view, a main menu and a Flight view that I have created myself.

I want all html elements with the CSS class of "date" to be date time pickers so via JQuery UI I have placed the following JavaScript into the Shared/_Layout.cshtml view right after the Jquery bundles are loaded:

<script type="text/javascript">
            $(document).ready(function () {
                alert("test");
                $('.date').datepicker({ dateFormat: "dd/mm/yy" });

            });
</script>

This script does exactly what I need when I login into the application and manually change the URL in my browser to the Flight view e.g. manually navigate to http://localhost:63891/Flight

However when I navigate from the link on the main menu it never runs the script. In the main menu view the link is generated with the following:

<ul data-role="listview" data-inset="true">
    <li data-role="list-divider">Navigation</li>
    <li>@Html.ActionLink("Flights", "Index", "Flight")</li>
</ul>

To be clear clicking the link renders the view as expected it just does not run my JavaScript. The only way I can ever get the script to run is manually entering the URL.

I have tried moving the script inside the actual Flight view but JQuery is not loaded at that point because it is loaded in the scripts section of the Shared/_Llayout.cshtml view.

When I hover the link the URL shown is localhost:63891/Flight but when I actually click through the URL changes to localhost:63891/#/Flight. I'm not sure why this is and if it's relevant.

How do I get the script to run when clicking through links?

EDIT: I think I have this issue but no one has answered his/her question How to handle jQuery event on an ASP.net MVC Ajax loaded page?

share|improve this question
1  
Sounds like a weird caching issue. If you hit Ctrl + F5 (hard refresh) after hitting the link, does it work? –  mattytommo May 29 '13 at 8:45
    
Are you sure that Index action is called when the url http://localhost:63891/Flight is entered manually? Might it be the case that another action is called, returning another view? –  Andrei May 29 '13 at 8:56
1  
Are you sure that the Mobile version of the MVC site is not doing some sort of partial loading of the views, if that's the case then the browser might not be actually running the script section you've defined after the initial load? –  Tr1stan May 29 '13 at 9:19
    
@mattytommo yeah hitting reload on the page is indeed running the script but after if I return to the main menu and click again it doesn't run again –  Alan Macdonald May 29 '13 at 9:27
    
@Andrei yes I am sure as there is only one action in the Flight controller –  Alan Macdonald May 29 '13 at 9:28

4 Answers 4

up vote 2 down vote accepted

if the mobile site uses JQM, and it looks from the comments that it does. try using

$(document).bind('pageinit')

instead of

$(document).ready()

more on that

share|improve this answer
    
You sound like you're onto something there. I tried it but it stops firing at all now so I am not sure I am hooking it up right. I have tried, $(document).bind('pageinit', function () { blah }); $(document).bind('pageinit', function (event, data) { blah }); $(document).live('pageinit', function (event) { blah }); Any idea what the correct syntax is? –  Alan Macdonald May 29 '13 at 12:09
1  
@AlanMacdonald $( '#/Flight' ).live( 'pageinit',function(event){ blah; }); that way you get the event handling only when you navigate to the page with the hash tag. –  Igarioshka May 29 '13 at 12:12
    
Thanks but that doesn't work because the script is in the Shared view. Even if I could get this code into the specific view (which would require loading JQuery first in the view) then the idea was by doing it in the shared view then any more views added later can just use the css class and not have to do any other configuration to get a datetimepicker. Do you know if it is possible to do without hardcoding the #/Flight part? –  Alan Macdonald May 29 '13 at 12:21
    
there s a nice discussion on the topic here: link –  Igarioshka May 29 '13 at 13:15
    
I've found the problem. Your's was the closest answer so I'll accept your's but I'll post the full solution. –  Alan Macdonald May 29 '13 at 13:40

I've accepted @Igarioshka's answer as it will be the normal answer for this problem and gives good information on how you are not meant to use document.ready in a Jquery mobile app.

The actual problem was I created the site from the Mobile template in VS which automatically added JQuery mobile. I then proceeded with development until I needed a calendar popup. From what I have found online this requires JQuery UI and JQuery (full) so I added the render call under the existing call for JQM in the SHared/_layout.cshtml view.

@Scripts.Render("~/bundles/jquery", "~/bundles/jquerymobile")
 @Scripts.Render("~/bundles/jquery")
 @Scripts.Render("~/bundles/jqueryui")

I then added my script for adding the datapicker. This would not fire due to JQuery Mobile using AJAX for everything as detailed by @Igarioshka. However changing my script to $(document).bind('pageinit', function (event, data) {

still wasn't firing. This seems to be because the script was after the full blown JQuery was getting loaded. So changing the order of the code to use the pageinit event before full blown jquery is loaded solves it.

@Scripts.Render("~/bundles/jquery", "~/bundles/jquerymobile")
@RenderSection("scripts", required: false)
        <script type="text/javascript">
            $(document).bind('pageinit', function (event, data) {
                $('.date').datepicker({ dateformat: "dd/mm/yy" });
            });
        </script>
@Scripts.Render("~/bundles/jquery")
@Scripts.Render("~/bundles/jqueryui")

This implies to me that the pageinit event is specific to JQuery Mobile and not available in the full blown JQuery which is a shame when trying to learn a unified approach to web development across platforms.

I'm not sure if this means I should get rid of JQuery Mobile because I have ended up using the full one or if it's still useful because it has optimizations etc.

share|improve this answer

Try a simple tag. Maybe it works:

<a href = "~/Flight/">Flights</a>
share|improve this answer
    
I think you meant <a href = "@Url.Content("~/Flight/")">Flights</a> but this has the same problem –  Alan Macdonald May 29 '13 at 10:46
    
No. I meant what I exactly wrote, it works for me. However, it seems that doesn't solve the problem –  AminSaghi May 29 '13 at 16:46
    
OK well what you wrote will not work in general. You need to use @Url.Content to make sure the virtual path is correctly translated to a physical path. –  Alan Macdonald May 29 '13 at 19:35
3  
In fact you're right. However I use this kind of addressing in my main menu in the _layout.cshtml file and it works in this situation. –  AminSaghi May 29 '13 at 19:40

It sounds more like the 'Flight' page is loaded partially (via ajax for instance).

Before looking for XHR requests you can see if the URL is changing when you click on the 'Flight' link, if it doesn't change it means that your 'Flight' page is loaded partially, the opposite is false (it is possible to load a content in AJAX and change the URL).

You can then look for XHR requests using a developer tool (Chrome for example). Hit F12 (or right click "Inspect Element") and see if you have XHR requests on the Console. XHR request on Chromes' web developer tool

Verify that the "Log XMLHttpRequests" option is enabled (on settings). Settings

Log XMLHttpRequests option

share|improve this answer
    
The URL changes although when I hover the link the URL shown is localhost:63891/Flight but when I actually click through the URL changes to localhost:63891/#/Flight is this relevant? There is nothing showing in the Chrome dev console –  Alan Macdonald May 29 '13 at 10:51
    
It means that the 'Flight' page is not loaded entirely. And if you say that there is not XHR request logged on the dev console, maybe the content of the 'Flight' page is already loaded on the page and shown when you click the link (some js that handles the 'click' event) –  polkduran May 29 '13 at 11:29
    
Sorry I cocked up my Chrome setting. Now I have it set correctly I do see XHR finished loading: "localhost:63891/Flight/";. so for some reason it is using AJAX for a simple anchor tag click. –  Alan Macdonald May 29 '13 at 12:51

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.