I try to add js actions in my ruby app. I read The asset pipeline & Working with JavaScript in Rails guides but I can't reproduce what is described in the second one. I'm a beginner in rails so perhaps I made too much "manipulations" with files, there extensions...
I have
a controller "mycontroller" app/controllers/mycontroller_controller.rb
class mycontrollerController < ApplicationController
def new
end
end
application.js app/assets/javascripts
//= require jquery
//= require jquery_ujs
//= require turbolinks
//= require bootstrap-sprockets
//= require_tree .
mycontroller.coffee app/assets/javascripts
When I load the app in a browser, assets seem to be correctly included
<script src="/assets/mycontroller-d915d2e33a0815bf7b1ac3c478a90599.js?body=1" data-turbolinks-track="true"></script>
<script src="/assets/application-fdae31866ddfa65ac8bed4781fb60a9c.js?body=1" data-turbolinks-track="true"></script>
Question : do I have to rename .coffee files in .js.coffee? I tried but nothing change.
I followed "Working with JavaScript in Rails" and modified my files like that:
new.html.erb app/views/mycontroller
<a href="#" onclick="paintIt(this, '#990000')">Paint it red</a>
mycontroller.coffee app/assets/javascripts
paintIt = (element, backgroundColor, textColor) ->
element.style.backgroundColor = backgroundColor
if textColor?
element.style.color = textColor
I think coffee script is correctly compiled :
(function() {
var paintIt;
paintIt = function(element, backgroundColor, textColor) {
element.style.backgroundColor = backgroundColor;
if (textColor != null) {
return element.style.color = textColor;
}
};
}).call(this);
But nothing happens by clicking... any idea ?
Thanks in advance for our help.
The issue is that CoffeeScripts are intended to communicate with the DOM in an "unobtrusive way", so that you don't see any signs of JS in your HTML. And this happens because your script is compiled as a self-executing anonymous function , that isolates its scope from the global namespace. paintIt
doesn't "leak" outside. It's by design (and here's some explaination on this ). You need to do that differently.
To distinguish attributes' purpose, I personally place any behaviour-related stuff in data-*
attributes and bind events on selectors like [data-paint]
, that indicate presence of such attributes. I suggest you rewrite your HTML like so:
<a href="#" data-paint="#990000">Paint it red</a>
Then handle the click
event for each data-paint
:
$("[data-paint]").on "click", ->
# `@` is basically `this` and `@thing` is `this.thing`
# `@dataset` contains the data attributes of the given element
@style.color = @dataset.paint
Aa-and you're done. See the JSFiddle .
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.