I have this at the bottom of a form partial, which worked previously when I loaded it through application.html.erb, but have since decided to replace it in application.html.erb with Google Maps.
_new.html.erb (with the field appropriately id'd). straight up doesn't work, can't figure out why.
<script>
$(document).ready(function(){
var autocomplete = new google.maps.places.Autocomplete(document.getElementById("autocomplete"));
});
function initAutocomplete(){
}
</script>
<script src="https://maps.googleapis.com/maps/api/js?key=AIzaSyCFm7OzAKuPbEa48b_aZ4S6JqMGVUCwwFs&libraries=places&callback=initAutocomplete"
async defer></script>
Try moving
<script src="https://maps.googleapis.com/maps/api/js?key=AIzaSyCFm7OzAKuPbEa48b_aZ4S6JqMGVUCwwFs&libraries=places&callback=initAutocomplete"
async defer></script>
to the in application.html.erb head tag
Then put
initAutocomplete = ->
$(document).ready ->
autocomplete = new (google.maps.places.Autocomplete)(document.getElementById('autocomplete'))
return
Into a coffeescript for you front page, or use your existing script inline of the partial to test if you need to.
Related
I have jQuery UI tabs set up, but a problem that I'm having with links to different pages is that they load all contents of the page into the tab. This includes the footer, header, and other navbars that I don't want in the tab. What if I would only like to load a single ID from that page?
My tabs are set up this way:
<div id="mytabs">
<ul>
<li>Awesome page</li>
<li>Foo</li>
</ul>
</div>
Nothing much going on in the jQuery...
$(function() {
$( "#mytabs" ).tabs();
});
Let's say this is the html of "awesomepage" (that the first link targets):
<html>
<head>
<title>awesome page</title>
</head>
<body>
<div id="header">bla</div>
<div id="awesomeness">awesomeness!</div>
<div id="footer">fdsfd</div>
</body>
</html>
...And I only want the tab to load #awesomeness from the page. How would I go about doing this? I've read into some guides that do that by adding a data-target="#youridhere" attribute to the HTML, but I'm still confused on how to implement the javascript. It seems like this is a convenient solution, as I won't be targeting the same ID in every page. Any clues on how to get the javascript working?
Thanks in advance!
The function that allow to load partial code of the response is the $.load() function.
Unfortunately, the tabs() feature does not use this function but use $.ajax instead.
You can try this solution:
You can try to stop the default processing on the beforeLoad callback and manage your ajax call with the $.load() method.
(base on the 1.9 documentation, you may should adapt)
$('#tabs').tabs({
// Callback run when selecting a tab
beforeLoad: function(event, ui) {
// If the panel is already populated do nothing
if (ui.panel.children().size() > 0)
return false;
// Make your own ajax load (with fragment feature)
ui.panel.load(ui.tab.attr('href') + ' #yourFragment');
// stop the default process (default ajax call should not be launched)
return false;
});
NOTICE: I'm not sure about extracting the URL with ui.tab.attr('href'), check before what object is ui.tab, but it should be easy to retrieve the href parameter.
Good luck
Got the solution :) Using one of the answers as a reference point, the tabs can now load a single element specified in the data-target attribute. Here is the modified version:
$(function() {
$('#tabs').tabs(
{
beforeLoad: function(event, ui) {
if (ui.panel.children().size() > 0)
return false;
ui.panel.load($('a', ui.tab).attr('href') + $('a', ui.tab).attr('data-target'));
return false;
}
});
});
So I was using trigger.io to create a page where there's a custom menu at the bottom and each button loads an external HTML page into main container. I had to hack around to make this work so I was wondering if there's a better way of doing it.
I started using the $('.main').load('pages/test.html') and it doesn't work. Instead I had to do:
forge.file.getLocal('pages/test.html', function (file) {
forge.file.string(file, function (str) {
$('.main').html(str);
});
});
which is kinda messy.
Also if the str HTML content as a img tag, the img doesn't show since the src attribute gets messed up. So I had to do another hack:
forge.file.getLocal('pages/test.html', function (file) {
forge.file.string(file, function (str) {
var $main = $('.main');
$main.html(str);
//Hack to resolve img src
var imgPath;
$main.find('img').each(function () {
var $this = $(this);
// First 8 chars is "file:///"
imgPath = $this.prop('src').substr(8);
forge.file.getLocal(imgPath, function (file) {
$this.prop('src', file.uri);
});
});
});
});
Any better way of purely loading an external HTML page without all the hassle?
Thanks!
Testing with forge platform v1.4 (at the time of writing, v1.4.18) on Android 4.1 and iOS (both the iPhone simulator and an iPad), I seem to be able to use jQuery's load method without any extra effort. Here's the structure for my testcase:
src/
index.html
face.png
pages/
hello.html
Here's the contents of index.html
<!DOCTYPE html>
<html>
<head>
<script src="js/jquery-1.7.1.min.js"></script>
<script type="text/javascript">
$(function () {
$('.content').load('pages/hello.html');
});
</script>
</head>
<body>
<div class="content">
</div>
</body>
</html>
And pages/hello.html:
<b>hello world</b><img src="face.png">
Which resulted in this just after app launch:
One gotcha I can see with this approach is that the src attribute for the img tag had to be relative to index.html. If you're still having problems then a more specific testcase and/or details of forge platform version used as well as what devices/simulators you tested on might be useful.
I'm using the "rails-backbone" gem in my Rails 3.2 project. By this design my Backbone Views are loaded in the <head> tag. When using Routes everything works fine, but Views do not render if I try to use them directly without Routes. If I put the Views code in <body> everything works as expected.
Is there a way to make the Views work when defined in <head>?
Update:
in <body>:
<script type="text/javascript">
var lv = new ListView();
</script>
in javascript file included in <head>:
window.ListView = Backbone.View.extend({
el: $("#node"), // This does not work
initialize: function(){
_.bindAll(this, 'render');
this.el = $("#node"); // Works if I add this line
this.render();
},
render: function(){
$(this.el).append("<ul> <li>hello world</li> </ul>");
}
});
As I understand it #node does not exist yet, which is why it is not bound to el. I don't quite understands when happens here: var lv = new ListView(), I thought I was creating an instance from a Class (I guess I'm getting a clone of an Object?). Is there another way of making the code work by modifying the code in <body> instead of the included javascript?
Your problem is caused by using a jQuery selector as the value for el in the view.
Read this:
http://lostechies.com/derickbailey/2011/11/09/backbone-js-object-literals-views-events-jquery-and-el/
if you want something to work in the head, but after the DOM is ready, (And apparently since you're using jQuery) just set up your views in the DOMReady event via:
$(document).ready(function(){
...
//set up view here
...
});
There seems to be some issues when combining MathJax and jQuery Mobile on the same page. Sometimes the MathJax renders correctly and other times it does not - and this can happen to the same page.
The HTML that loads both of them looks like this:
<script type='text/javascript' src='http://code.jquery.com/jquery.min.js'>
</script>
<script type='text/javascript'
src='http://code.jquery.com/mobile/1.0a4.1/jquery.mobile-1.0a4.1.min.js'>
</script>
<link rel='stylesheet' type='text/css'
href='http://code.jquery.com/mobile/1.0a4.1/jquery.mobile-1.0a4.1.min.css' />
<script src='/beta/mathjax/MathJax.js'>
</script>
You can see an example page here: http://stackmobile.com/beta/math.stackexchange.com/questions/view/?id=47772
Edit: It seems to be a problem with MathJax not recognizing a new page being loaded via AJAX - here is an example that doesn't seem to work: http://stackmobile.com/beta/#/beta/physics.stackexchange.com/questions/view/?id=11678
Well I found a solution... and it goes something like this:
First assign unique numbers to the pages. Since these pages are generated in PHP, this can be accomplished by using uniqid().
Assign the following function the the pageshow event:
$('#page_id').live('pageshow', function(event, ui) {
var script = document.createElement('script');
script.type = 'text/javascript';
script.src = 'path_to_mathjax/MathJax.js';
script.onload = callback;
document.getElementsByTagName('head')[0].appendChild(script);
});
This loads MathJax and inserts it into the DOM - this script should be included within the page element. Also note that we mention a 'callback'. This will be called when the script loads.
This function (the callback) needs to go outside of any pages. This will prevent it from being included twice after a new page is loaded.
var mathjax_loaded = false;
function callback()
{
if(mathjax_loaded)
MathJax.Hub.Queue(["Typeset", MathJax.Hub]);
else
{
MathJax.Hub.Startup.onload();
mathjax_loaded = true;
}
}
There's a lot here. First of all, we keep track of whether this callback has been called once before. If not, we tell MathJax to parse the page as if it were invoked from the window.onload event. If this has already happened (and we're on a new page) then we simply need to have MathJax run through the new page.
I'm probably missing something and there may be a better way of doing this. But I haven't found any other way that works.
Not sure if this is easier/better way to add a script but here is what I found:
http://api.jquery.com/jQuery.getScript/
Can't append <script> element
(Untested) Maybe (using your post: Combining jQuery Mobile and MathJax on a mobile site?)
$('#page_id').live('pageshow', function(event, ui) {
$.getScript('http://path_to_mathjax/MathJax.js', function() {
callback();
});
});
var mathjax_loaded = false;
function callback()
{
if(mathjax_loaded)
MathJax.Hub.Queue(["Typeset", MathJax.Hub]);
else
{
MathJax.Hub.Startup.onload();
mathjax_loaded = true;
}
}
There are topics that try to cover this here: Gmaps4rails : map not showing when loaded dynamically and especially here: Rendering google map using gmaps4rails through Ajax, also watched the screencast in which a gmap is dynamically updated but I still don't seem to get it work.
I am trying to load the map in a drop-down tab only if a button is clicked displaying the direction between a user and an offer. In my _location.html.erb partial I have:
<%= gmaps({ "direction" => { "data" => { "from" => current_user.location, "to" => #offer.location } } })%>
(the locations are addresses)
Now this works nicely when the partial is rendered immediately. If I however try to render the partial over an AJAX call later after the whole page has already loaded initially, the gmap is not displayed. Is it possible to initialize and render the gmap through an AJAX call and display directions then?
The reason is quite simple: the partial contains much javascript you can't load and execute this way.
So you can't use RJS there.
The proper way to do is UJS: get data with an AJAX call and render the result. In the following code, I use jQuery.
In your view add:
//include google script
<script type="text/javascript" src='http://maps.google.com/maps/api/js?sensor=false&libraries=geometry'></script>
//include gmaps4rails javascript
<%=javascript_include_tag 'gmaps4rails' %>
<script type="text/javascript" charset="utf-8">
//load map when button click (replace with what you want)
$('#ajax_map').click(function(){
//you have to set a size to the div otherwise the map won't display, that's the purpose of these css classes
$('#map_container').addClass('map_container');
$('#gmaps4rails_map').addClass('gmaps4rails_map');
//create the map object
Gmaps4Rails.initialize();
//of course, replace these two with your dynamic data, you'd have to use some $.ajax jQuery method.
Gmaps4Rails.direction_conf.origin = 'toulon, france';
Gmaps4Rails.direction_conf.destination = 'paris, france';
//read the js file, you can customize much more: https://github.com/apneadiving/Google-Maps-for-Rails/blob/master/public/javascripts/gmaps4rails.js
Gmaps4Rails.create_direction();
});
</script>
<div id="map_container">
<div id="gmaps4rails_map"></div>
</div>
<button type="button" id="ajax_map">Ajax Map</button>
Add the following class in your CSS:
#map-container {
width: 800px;
}
#gmaps4rails_map {
width: 800px;
height: 400px;
}