Foundation 6 top-bar dropdown won't close - ruby-on-rails

I added a dropdown menu to my top-bar, all the submenus appear when I hover the mouse over it.
The problem is after starting the server then when I click any link in my application then the whole submenu aligns vertically in the topbar and won't go away. When I refresh the page with F5 then the submenu items disappear but when I click any other link then they appear again in fixed position, aligned under the dropdown menu link.
Before hover:
On hover:
After clicking whatever link in the app:
To be sure I'm not messing it up myself while describing the front end, I copy-pasted example from Foundation page directly:
.top-bar
.top-bar-left
ul.dropdown.menu data-dropdown-menu=''
li.menu-text Site Title
li
a href="#" One
ul.menu.vertical
li
a href="#" One
li
a href="#" Two
li
a href="#" Three
li
a href="#" Two
li
a href="#" Three
I'm using slim for syntax and:
foundation-rails 6.4.3.0
rails 5.1.6
ruby 2.5.1
I checked the javascript console with broswer inspection tools and no errors there (also no errors in server log). I even tested with removing turbolinks in main-layout head but of course it didn't affect. I'm running out of thoughts how to debug further.
My application layout (the top-bar resides in _navbar partial which gets rendered in body):
doctype html
html lang= I18n.locale.to_s
head
meta charset='utf-8'
meta name='viewport' content='width=device-width, initial-scale=1.0'
title == content_for?(:title) ? yield(:title) : t('general.home')
= stylesheet_link_tag 'application', media: 'all', 'data-turbolinks-track': 'reload'
= include_gon(init: true)
= javascript_include_tag 'application'
= javascript_include_tag 'https://www.gstatic.com/charts/loader.js'
= csrf_meta_tag
= favicon_link_tag 'favicon.ico'
body
.main
= render 'layouts/navbar'
= render 'layouts/title', title: #title
= render 'layouts/messages'
= yield
And my application javascript (if somehow the order of reloading libaries should matter):
//= require jquery
//= require rails-ujs
//= require turbolinks
//= require rails.validations
//= require rails.validations.simple_form
//= require foundation
//= require chartkick
//= require ckeditor/init
//= require_tree .
$(function(){ $(document).foundation() })
Similar problem described here, but the solution isn't working for me: https://foundation.zurb.com/forum/posts/38667-foundation-62-topbar-dropdown-issue

I'ts a turbolinks issue: inside your application javascript you should load foundation on turbolinks:load like this:
$(document).on('turbolinks:load', function() {
$(function(){ $(document).foundation() })
})
Have a look at here for more information.

Related

Excel Add In - Javascript only working after reload

I am developing an Excel Add-In using the Office-JS Library.
When some pages are loaded, the JS is not loaded properly.
The Javascript only works after reloading the page.
I disabled turbolink as suggested in another question.
But my problem still appears.
My office_connect.js contains the following:
//= require jquery3
//= require jquery_ujs
//= require_self
//= require select2-full
//= require select2_locale_de
And the head of my layout file:
<%= yield :head_top %>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=Edge" />
<%= stylesheet_link_tag "office_connect"%>
<%= javascript_include_tag "office_connect_app"%>
<script src="https://appsforoffice.microsoft.com/lib/1/hosted/office.js" type="text/javascript"></script>
<%= javascript_include_tag "oc_function"%>
<%= javascript_include_tag "office_excel"%>
<title><%=t('layouts.head.text_immodatacockpit')%></title>
<%= csrf_meta_tag %>
<%= yield :head %>
The oc_function file starts Office JS:
// The initialize function must be run each time a new page is loaded.
(function () {
Office.initialize = function (reason) {
// If you need to initialize something you can do so here.
};
})();
A shortened version of my excel.js:
(function () {
"use strict";
var cellToHighlight;
var messageBanner;
var config;
var sheetData;
let housing_output_template_new;
let housing_output_template_edit;
// The initialize function must be run each time a new page is loaded.
Office.initialize = function (reason) {
$(document).ready(function () {
$(".spinner").hide();
// If not using Excel 2016, use fallback logic.
if (!Office.context.requirements.isSetSupported('ExcelApi', '1.1')) {
$('#subtitle').text("Opps!");
$("#template-description").text("Sorry, this sample requires Word 2016 or later. The button will not open a dialog.");
$('#button-text').text("Button");
$('#button-desc').text("Button that opens dialog only on Word 2016 or later.");
return;
}
$("#select1").select2({placeholder: 'Please choose' , language:'<%= I18n.locale %>',dropdownAutoWidth:true});
$(".select4").select2({placeholder: 'Please choose' , language:'<%= I18n.locale %>',dropdownAutoWidth:true});
});
}
})();
I think it has something to do with the order I load the JS libraries.
Could you point me in the direction of what I am missing?
It looks like you are assigning Office.initialize in two places. If these calls are on two different pages, then that's OK. But you shouldn't be doing this twice on the same page.

Uncaught ReferenceError: require is not defined using AngularJS, Rails 4 and Browserify

I am using AngularJS and Rails, and followed http://start.jcolemorrison.com/setting-up-an-angularjs-and-rails-4-1-project/ and several other tutorials to get a very simple "Hello World" example up and running on my desktop. The problem is, when I deploy it to a server, none of my code based on Angular works anymore. Instead, I get a Uncaught ReferenceError: require is not defined error in my console.
I realized that part of my problem is that the browser doesn't know what to do with the 'require' function calls, which makes sense so I installed Browserify using browserify-rails. However, it still does not work on the server like I would expect and I get the same error.
Link to the live site: Link
Here's my application.html.erb (simplified):
<!DOCTYPE html>
<html>
<head>
<base href="/" />
<title>ShibaInu</title>
<%= stylesheet_link_tag 'application', media: 'all', 'data-turbolinks-track' => false %>
<%= javascript_include_tag 'application', 'data-turbolinks-track' => false %>
<%= csrf_meta_tags %>
</head>
<body ng-app="shibaInu">
<div class="container">1 + 2 = {{ 1 + 2 }}</div>
<div class="container">
<%= yield %>
</div>
</body>
</html>
index.html.erb:
<div ng-view=""></div>
home.html.erb (rendered inside the container):
<h1>The Home View!</h1>
<ul>
<li ng-repeat="thing in things">
{{thing}}
</li>
</ul>
home.js:
angular.module('shibaInu')
.controller('HomeCtrl', function ($scope) {
$scope.things = ['Angular', 'Rails 4.1', 'Working', 'Together!!'];
});
app.js:
angular
.module('shibaInu', [
'ngRoute',
'templates'
]).config(function ($routeProvider, $locationProvider) {
$routeProvider
.when('/', {
templateUrl: 'home.html',
controller: 'HomeCtrl'
});
$locationProvider.html5Mode(true);
});
application.js
//= require jquery
//= require jquery_ujs
//= require angular
//= require angular-route
//= require angular-resource
//= require angular-rails-templates
//= require bootstrap-sprockets
//= require ng-app/app.js
//= require_tree ../templates
//= require_tree .
I was doing several things wrong, but I'll try to summarize:
I am minifying JS on my server deployment like a good boy, but I was not writing minification-safe JS. See below for my fixed JS.
This wasn't specified in my original post, but I was not using the angularjs-rails gem like I thought I was. I added this to my project.
Related to 2 above, in my initial post I had used bower to install angularjs like the documentation recommends. For my solution, I took this out because it was just making things messy for my purposes.
New home.js:
angular.module('shibaInu')
.controller('HomeCtrl', ['$scope', function ($scope) {
$scope.things = ['Angular', 'Rails 4.1', 'Working', 'Together!!'];
}]);
New app.js:
angular
.module('shibaInu', [
'ngRoute',
'templates'
]).config(['$routeProvider', '$locationProvider', function ($routeProvider, $locationProvider) {
$routeProvider
.when('/', {
templateUrl: 'home.html',
controller: 'HomeCtrl'
});
$locationProvider.html5Mode(true);
}]);

Getting Dojo to Work with Ruby on Rails 4

I'm porting my symfony app to Ruby on Rails 4.2.0. My setup works fine in symfony. There is this old post on how to use dojo with RoR, but it uses deprecated code.
In my application.html.erb I have
<script>dojoConfig = {async: true}</script>
<%= javascript_include_tag 'http://ajax.googleapis.com/ajax/libs/dojo/1.10.3/dojo/dojo.js'%>
I replaced the symfony wrappers with Rails ones. I also changed the dojo version. I was using 1.9.1. Rails generates this html:
<script>
dojoConfig = {async: true}
</script>
<script src="http://ajax.googleapis.com/ajax/libs/dojo/1.10.3/dojo/dojo.js">
The last line is followed by a bunch of compressed javascript and the close script tag in Firebug.
I didn't make any changes in my home/index.html.erb where I'm testing this code. In app/assets/javaascipts/home.js, I have:
//require(["dojo/dom", "dojo/ready", "dijit/Tooltip"], function(dom, ready, Tooltip)
define(["dojo/dom", "dojo/ready", "dijit/Tooltip"], function(dom, ready, Tooltip)
{
ready(function()
{
var head = "<div class='footnote-text'>";
var tail = "</div>";
var fnt1 = head + dom.byId("fnb1").innerHTML + tail;
var fnt2 = head + dom.byId("fnb2").innerHTML + tail;
var fnt4 = head + dom.byId("fnb4").innerHTML + tail;
new Tooltip({ connectId: ["footnote1"],position:["after","above","below"],label: fnt1 });
new Tooltip({ connectId: ["footnote2"],position:["after","above","below"],label: fnt2 });
new Tooltip({ connectId: ["footnote4"],position:["after","above","below"],label: fnt4 });
new Tooltip({ connectId: ["footnote5"],position:["after","above","below"],label: fnt4 });
});
});
//require(["dojo/dom", "dojo/ready", "dijit/Dialog"], function(dom, ready, Dialog){
define(["dojo/dom", "dojo/ready", "dijit/Dialog"], function(dom, ready, Dialog){
ready(function(){
var fnt3 = dom.byId("fnb3").innerHTML;
myDialog = new Dialog({
title: "Contact Me",
content: fnt3,
style: "width: 300px"
});
});
});
The commented out require lines are what I use in my symfony app. As you can see, I replaced them with define as described on the dojo site. When I run it, I get the following error on the Firebug console:
ReferenceError: define is not defined
...define(["dojo/dom", "dojo/ready", "dijit/Tooltip"], function(dom, ready, Tooltip
If I used require instead of define, I get require is not defined.
Update
I tried installing dojo into the app and made some progress. I copied the download from dojo to vendor/assets/javascript/dojo. The dojo directory contains the subdirectories dojo, dojox, and digit
I then added
//= require dojo/dojo/dojo.js
to app/assets/javascript/application.js. I also changed the define back to require in the home.js file. When I reloaded the page, I got an error complaining that it couldn't find Tooltip. I then added:
//= require dojo/dijit/Tooltip.js
On reload it complained about a bunch of other missing js files. This is the same problem I had using symfony, which is why I went to the google image. How can I get to rails to search for the files in the vendor directories? This is one of the errors:
"NetworkError: 404 Not Found - http://amcolan.loc/dijit/_base/manager.js"
Update 2
Since require_tree worked for app assets, I thought it might work to vendor as well. I added
//= require_tree ../../../vendor/assets/javascripts/dojo
to my application.js file. When I reloaded the page, it took about a minute. My guess is that it's loading everything in the dojo directory tree, which is not surprising. The page load completed without any errors. When I hovered over a tooltip item (the purpose of the code is to show tooltips), Firebug cranked out about two thousand errors and quit. All the errors appear to be "ReferenceError: define is not defined"
Update 3
I went back to using the googleapi. My application.html.erb header looks like this
<head>
<meta charset="UTF-8">
<title><%= content_for?(:title) ? yield(:title) : "American Colonial Ancestors" %></title>
<%= stylesheet_link_tag 'application', media: 'all', 'data-turbolinks-track' => true %>
<script>dojoConfig = {async: true}</script>
<%= javascript_include_tag 'http://ajax.googleapis.com/ajax/libs/dojo/1.10.3/dojo/dojo.js'%>
<%= javascript_include_tag 'application', 'data-turbolinks-track' => true %>
<%= csrf_meta_tags %>
</head>
I reversed the order of the javascript includes. The page reloaded without errors. The tooltip doesn't work, but it doesn't generate any errors when I hover over an item. I put a bad statement in the home.js code and it came up on the console so I know the code is being parsed. I may just have a bug in my page setup.
There may be more than one way to get Dojo toolkit to work with Ruby on Rails. This is the easiest if not the most efficient way. This works in Rails 4.2.0. I would imagine it would work in other versions as well.
In views/layouts/application.html.erb add the following prior to the inclusion of the site scripts:
<script>dojoConfig = {async: true}</script>
<%= javascript_include_tag 'http://ajax.googleapis.com/ajax/libs/dojo/1.10.3/dojo/dojo.js'%>
Change the version to the latest or to which ever one you want to use. Here I'm using version 1.10.3. The dojo site says there are other CDN's (Content Delivery Network) for the source code. I'm using google as it was in their example. Here are the pertinent parts of my head section:
<head>
<meta charset="UTF-8">
<%= stylesheet_link_tag 'application', media: 'all', 'data-turbolinks-track' => true %>
<%= stylesheet_link_tag "http://ajax.googleapis.com/ajax/libs/dojo/1.10.3/dijit/themes/claro/claro.css" %>
<script>dojoConfig = {async: true}</script>
<%= javascript_include_tag 'http://ajax.googleapis.com/ajax/libs/dojo/1.10.3/dojo/dojo.js'%>
<%= javascript_include_tag 'application', 'data-turbolinks-track' => true %>
<%= content_for :page_script %>
<%= csrf_meta_tags %>
</head>
If you are going to use any of the toolkit's dialog boxes, tooltips, etc, you will need to include a stytlesheet by adding something like this:
<%= stylesheet_link_tag "http://ajax.googleapis.com/ajax/libs/dojo/1.10.3/dijit/themes/claro/claro.css" %>
Change the version and the theme to your own requirements. Here I'm using the claro theme. You can see it in my head section above. I don't think placement is critical. You also need to declare your theme class in the body statement. Here's mine:
<body class="claro">
An older post on the subject had different javascript formatting. I don't think anything special is needed. Here's an example of a working script:
require(["dojo/dom", "dojo/ready", "dijit/Tooltip"], function(dom, ready, Tooltip)
{
ready(function()
{
var head = "<div class='footnote-text'>";
var tail = "</div>";
var fnt1 = head + dom.byId("fnb1").innerHTML + tail;
var fnt2 = head + dom.byId("fnb2").innerHTML + tail;
new Tooltip({connectId: ["footnote1"], position:["after","above","below"], label: fnt1 });
new Tooltip({connectId: ["footnote2"], position:["after","above","below"], label: fnt2 });
});
});
As mentioned in my question, I tried placing the Dojo Toolkit source in vendor/assets/javascript. Starting with with version 1.7, dojo started using Asynchronous Module Definition (AMD). It may be the case that the AMD loader is incompatible with the Rails pre-compile feature. I don't know enough about it to say for sure.

Include all javascript files from application except a specific folder in Rails 3.2.11

I would like to exclude a specific folder from assets/javascripts in my application.html.haml
The folder that I do not want to be included in my layout is mobile folder
Here's my layout:
%html(lang="en")
%head
%meta(charset="utf-8")
%meta(http-equiv="X-UA-Compatible" content="IE=Edge,chrome=1")
%meta(name="viewport" content="width=device-width, initial-scale=1.0")
%title= content_for?(:title) ? yield(:title) : #user.name ? 'Niche | ' + #user.name : 'Niche'
= csrf_meta_tags
= analytics_init if Rails.env.production?
/ Le HTML5 shim, for IE6-8 support of HTML elements
/[if lt IE 9]
= javascript_include_tag "//cdnjs.cloudflare.com/ajax/libs/html5shiv/3.6.1/html5shiv.js"
= stylesheet_link_tag "application", :media => "all"
%body#profile
%section.persist-area
%header.global.profile
%div.container
%a.brand.pull-left{ :href => root_path }
.logo-niche
%nav.pull-right
= render 'layouts/menu'
.container-fluid#main
= yield :profile
/
Javascripts
\==================================================
/ Placed at the end of the document so the pages load faster
= javascript_include_tag "application"
= yield :javascript
In this snippet, I am getting all JS:
= javascript_include_tag "application"
But I want to get all JS except the folder named mobile
I tried the following workaround but did not work:
= javascript_include_tag "application", except: "mobile"
Sorry that was just a wild guess. There's no javascript_exclude_tag too as per the docs.
Any ideas? Thanks.
PS: I have a different layout for mobile, so that's why I really want to exclude that folder in desktop view. It's conflicting a lot of conflicts in my desktop view.
Change in application.js
//= require_tree
to
//= require_directory .
or
//= require_tree ./useful
So that, app/assets/javascripts/* files will be included and app/assets/javascripts/mobile/* wont be included.

Using jquery-ui-rails datepicker in an Ruby on Rails website. datepicker method not defined

I got this problem writing the website with Ruby on Rails.
bundle show
* jquery-ui-rails (4.0.1)
In app/assets/javascripts/application.js
//= require jquery.ui.datepicker
In app/assets/stylesheets/application.css
*= require jquery.ui.datepicker
In app/views/layouts/application.html.erb
<%= stylesheet_link_tag "application", :media => "all" %>
<%= javascript_include_tag "application" %>
And then in somepage.html.erb, I got
<script type="text/javascript">
$(function(){
$("#startdate").datepicker();
$("#enddate").datepicker();
});
</script>
When running it, Chrome says that
Uncaught TypeError: Object [object Object] has no method 'datepicker'
I suppose that resource not being referred properly is the cause because the problem could be fixed by adding the follows into app/views/layouts/application.html.erb
<link rel="stylesheet" href="http://code.jquery.com/ui/1.10.1/themes/base/jquery-ui.css" />
<script src="http://code.jquery.com/jquery-1.9.1.js"></script>
<script src="http://code.jquery.com/ui/1.10.1/jquery-ui.js"></script>
<link rel="stylesheet" href="/resources/demos/style.css" />
These could be found at http://jqueryui.com/datepicker/. I saw demos having working datepickers without these codes. But I do not understand why it is not working in mine. Anyone got any suggestions? like something to add other than those I mentioned above?
It probably because of either of the following:
1) You are including multiple javascript files in your application.html.erb which is leading to havoc when put altogether.
2) You are using some other javascript file that also using $ just like jquery is using.
Having two same symbols is the possible cause of getting no method 'datepicker' for the jquery.
The alternative is to replace all the occurences of $ with jQuery
OR
Just wrap your jquery code insode a block like the following:
jQuery(function($){
//all jQuery code which uses $ should be here.
});

Resources