Adding custom javascript to device - ruby-on-rails

In my javascripts folder for my rails application, I've added both a device.js file as well as a device/registrations.js file. I was under the impression that when I'm routed to the registration page, rails would automatically pick up the correct javascript files, but for some reason it's not working.
Is there anything that needs to be added so that it can use custom javascript code?

You can include that in your registration view of devise by doing:
<%= javascript_include_tag 'devise/registrations' %>
To generate the views do
rails g devise:views
EDIT
Another way would be in the views/devise folder create a partial _registrations.html.erb
Put your js code in there and then do
<%= render 'registrations' %>

Related

How to customize devise form css in rails

Command rails generate devise:views successfully created folders under \app\views\users
I am looking to customize the devise forms but not sure whether the css to be placed in application.css or i need to separately create user.css.scss. Googled a bit and check git doc for this but none is specifying for CSS handling in devise.
Let me know the correct way of handling it
Devise will use you default layout. So the CSS that you are using in your views/layouts/application.html.erb will be used in your generated devise views.
If you want devise specific layouts, you can create a views/layouts/devise.html.erb file where you can serve devise specific CSS. It will pick it up automatically because of Rails naming conventions.
The above will work for any controller, just add a file in layouts named after the controller eg. views/layouts/reservations.html.erb for ReservationsController
You can also add specific layouts for the Devise::RegistrationsController by making a directory views/layouts/devise and adding views/layouts/devise/registrations.html.erb
If you are doing controller-specific stylesheets, that is, if you switched off automatic compilation of all of your stylesheets into application.css, you should name your stylesheet after a devise controller, e.g.:
registrations.css.scss
and add it to Rails.application.config.assets.precompile list in assets.rb.
The placement of the stylesheet is standard, app/assets/stylesheets/ so watch for name collisions between devise's controllers and yours.
To pick up a controller-specific stylesheet in a layout you need something like this:
Rails up to 4.1
<%= stylesheet_link_tag controller_name, media: 'all' if Rails.application.assets.find_asset("#{controller_name}.css") %>
Rails 4.2+
<%= stylesheet_link_tag controller_name, media: 'all' if asset_present?("#{controller_name}.css") %>
# ...meanwhile, somewhere in the helpers...
def asset_present?(name)
# Rails 4.1 had Rails.application.assets filled out in all environments.
# Rails 4.2 has it filled only when config.assets.compile == true which is only
# in development by default.
if Rails.application.assets.present?
Rails.application.assets.find_asset(name)
else
Rails.application.assets_manifest.files.values.map { |v| v['logical_path'] }.include?(name)
end
end
To generate device view run this line
rails generate devise:views
and do what ever you want with page styling.
to read more Click here

Submit form without using object

It's my first post on stackoverflow! I warn you, I just started learning Ruby on Rails.
Currently, I'm working on a music scanning project in rails. I'm trying to process al the music on the hard disk. To do that, the user can add a folder to scan when he is inside the config part of the app. So I store inside a YAML file all the config of my app.
I create a 'config' controller, that contains 2 view for the moment: "adddir" and "index".
The index view show all parameters, that have been gathered by loading the YAML config file (done by the controller 'config').
Next, I want to give the possibility to the user to add a new folder to scan. So I did a static route to the 'adddir' view:
routes.rb file:
match "/config/adddir" => "config#adddir"
Now, I want to create a form that get the path provided by the user, and add it to the YAML file.
So my question is: How to create a form that be able to use the method config#addfolder I created when the user click on submit button?
I hope this is enough clear.
Best regards
Welcome to SO. Its a very basic question. Just have a look at the screencast. Make a simple project first (with a model), then you will see the ABC of Rails.
http://rubyonrails.org/screencasts/rails3/
Basically:
You generate the controller like:
rails g controller config adddir
This setups the controller, the view and your route.
Then go into your view folder and look inside config. There is adddir.html.erb. This file you need to change in something like a form.
You can open your form:
http://localhost:3000/config/adddir
rake routes
Will print you a list of available routes you can use (inside your form).
Now the magic is that Rails generate your a config_adddir_path (watch the _path). That you can use to hookup the form.
<%= form_tag(config_adddir_path, :method => "get") do %>
<%= label_tag(:q, "Folder:") %>
<%= text_field_tag(:q) %>
<%= submit_tag("index") %>
<% end %>
Inside your controller (def adddir):
You can access the parameters:
def adddir
logger.debug params.inspect
end
Have a look here:
http://guides.rubyonrails.org/form_helpers.html

Can't override default devise gem views

I want to use my devise generated views (with command rails g devise:views users) from app/views/users.
I already have set these options from app/initializers/devise.rb:
config.scoped_views = true
config.default_scope = :user
but it still uses default devise views from /usr/lib/ruby/gems/1.8/gems/devise-2.0.4/app/views/devise/
So what should I do?
Thanks.
I was having this same problem and it took me forever to figure it out. Setting config.scoped_views = true is the first step, but there's another step that's not as clear.
If you look closely at some of the views that get generated by rails g devise:views users you'll see that the templates include <%= render "devise/shared/links" %> at the bottom of the file. Since you have generated these views, the shared links are now located in users/shared/links. Since devise doesn't find anything in devise/shared/links anymore, it uses the default links view instead.
Change <%= render "devise/shared/links" %> to <%= render "users/shared/links" %>and you're set!
For a custom login view, when you're using the default User devise resource, I think all you need is to create app/views/devise/sessions/new.html.erb. And, just for the moment, let's forget about the CRUD interface. And undo those config/initializers/devise.rb settings. Just see if you can get that working.

How to use rails code / pass variables to a .coffee javascript file?

What would be the best way to pass values inside a .coffee script? Renaming the file to .erb breaks my app so what are the alternatives?
checkout this rails guide. this section : 2.3.3 JavaScript/CoffeeScript and ERB
You can use rails code in .coffee-script file. It's built-in feature.
2nd Edit___
If the file is in assets pipeline then you need to add .erb extension at end of coffee file so that the rails tag works otherwise there is no need to add .erb extension if you moves the file in views folder rails tag works there.
You can either (1) move the file into your app/views directory (so it won't be in the asset pipeline), or (2) pass the information via query string.
(1) app/views/users/script.js.coffee.erb
var username = <%= #user.name %>
(2) I'm using this function
<%= link_to "User", user_path(#user, :username => #user.name) %>
...
var username = getParameterByName('username')
Untested but this is the general idea.

how should I include a coffeescript file on only one page?

Edit: a year later if I was going to do this again I'd do it with curl.js instead of Rails asset pipeline.
Related: Best way to add page specific javascript in a Rails 3 app?
I'm writing an app and using coffeescript to generate all of the js. That's why the related question doesn't do what I need.
I'd like to be able to put a coffeescript file in a subfolder of my assets directory and have that .coffee file only get served up on one page. The page is on a named route
match 'myNotifications' => 'user#notifications'
The most obvious thing to do was to put the .coffee file in assets\javascripts\user\index.js.coffee. But after reading the docs about assets I'm unclear.
I read this line (from http://guides.rubyonrails.org/asset_pipeline.html):
You should put any JavaScript or CSS unique to a controller inside
their respective asset files, as these files can then be loaded just
for these controllers with lines such as <%= javascript_include_tag
params[:controller] %> or <%= stylesheet_link_tag params[:controller]
%>.
Ok cool, so I put the page specific js in assets\javascripts\user.js.coffee. Then I reloaded my home page, Ctrl F5. The user.js file is still being loaded on the homepage. Tested with $ -> alert 'ready from users controller'; seeing that alert when I load the homepage.
Does Rails have a way to have a per-page coffeescript file that will only be served up with that page? Am I reading the manual wrong? Is there a place in the assets folder that I can put .coffee files where they won't get loaded with every page?
Update: Looks like I might have an answer:
There are a couple of ways that we can get around this problem. We
could use require_directory instead of require_tree as this will only
load the files in the current directory and not in subdirectories. If
we want more control over the included files we can require them
separately instead of including the whole directory. Alternatively we
could move the JavaScript files that we want to be included on all
pages into a public subdirectory. We can then use require_tree
./public to include just those files.
I'll give that a shot in the AM.
Here's the approach I use to make controller/view specific Coffee:
application.html.haml:
%body{ :data => { :controller => params[:controller], :action => params[:action]} }
alt. application.html.erb
<%= content_tag(:body, :data => { :controller => params[:controller], :action => params[:action] }) do %>
...
<% end %>
application.js.coffee:
$(document).ready ->
load_javascript($("body").data('controller'),$("body").data('action'))
load_javascript = (controller,action) ->
$.event.trigger "#{controller}.load"
$.event.trigger "#{action}_#{controller}.load"
users.js.coffee
$(document).bind 'edit_users.load', (e,obj) =>
# fire on edit users controller action
$(document).bind 'show_users.load', (e,obj) =>
# fire on show users controller action
$(document).bind 'users.load', (e,obj) =>
# fire on all users controller actions
Sidenote:
This works great with PJAX as well as you can pass the controller/action names with the response header on PJAX requests and just fire these js functions based on that.
EDIT (2014/03/04):
This solution still works when using turbolinks.js.
Rather than only including the file on one page, you might want to just use logic that's conditional on the page markup. See my answer to a related question. That way, your users don't have to make an additional <script> request for the particular page.
If there's a lot of logic specific to that page (say, 10K+ minified), then yes, split it out. As you suggested in the edit to your question: Rather than doing require_tree . at the root of your javascripts directory, instead create a sub-directory called global and change the top of application.js from
require_tree .
to
require_tree global
Then put your page-specific CoffeeScript file in the root javascripts directory, and point to it with a javascript_include_tag call in that page's template.
include javascript tag into your view template, like show.html.haml
- content_for :javascripts do
= javascript_include_tag 'folder/coffee_file_name'

Resources