JavaScript as a condition to load Rails form? - javascript

I have a form with a Jquery plugin requirement that creates a form input field with a type of Facebook-autocomplete kind of style:
<%= javascript_include_tag "form_prettify_library" %>
<div class="box">
<ul id="first_form" class="tagit">
<li class="prettify-new"></li>
</ul>
<%= form_for #brand do |f| %>
<%= f.hidden_field :tag_list, :value => #brand.tags_from(current_user).join(", "),
:id => "mytaglist" %>
<%= f.submit "Add tags" %>
<%= f.error_messages %>
<% end %>
</div>
It works well, however without JavaScript the form doesn't work because the form above only has a hidden_field and no visible entry field (the entry field is created by the plugin inside of the tags), and I need this to work without JavaScript on mobile devices. Is there any way to show the code above if JavaScript is loaded, otherwise the code below will be displayed if it isn't?
<div class="box">
<%= form_for #brand do |f| %>
<%= f.label :tag_list, "Your tags" %>
<%= f.text_field :tag_list, :value => #brand.all_tags_list %>
<%= f.submit "Add tags" %>
<% end %>
</div>

Yes, use css to hide it by default, and add a class to the site when js is enabled
html
<body class="no_js">
<script type="text/javascript">
(function() {
var body = document.getElementsByTagName("body")[0];
body.className = body.className.replace(/\bno_js\b/, " js ")
}())
</script>
css
.no_js .jsForm,
.js .no_jsForm {
display:none;
}
.js .jsForm,
.no_js .no_jsForm {
display: block;
}

Related

JQuery Input Rails Form

I have a search form on my page with two buttons - "news" and "events".
I can get the Rails search function to work correctly but I don't want a search form, I want the user to press one of the two buttons and the search to be executed.
I figure this probably has to be done with JQuery so when a button is clicked, either "news" or "events" are added to the rails input form and it submits the form. Please appreciate where I'm going wrong here as the form won't submit and the search won't execute.
Application.js
$(document).on('ready page:load', function () {
$(".news-button").click(function(){
$("#search").val("news");
$("#news-search").submit();
});
$(".events-button").click(function(){
$("#search").val("event");
$("#news-search").submit();
});
});
Index.html.erb
<%= form_tag news_index_path, :method => 'get', :id => "news_search" do %>
<p>
<%= text_field_tag :search, params[:search] %>
<%= submit_tag "Search", :name => nil %>
</p>
<% end %>
<div class="col-sm-3 sort-buttons">
<%= link_to "News", "", class: "btn btn-standard news-button" %>
<%= link_to "Events", "", class: "btn btn-standard events-button" %>
</div>
<div class="row">
<% #news.each do |n| %>
<div class="col-sm-4">
<div class="news-wrap">
<%= image_tag("#{n.image}", class: "img-responsive", alt: "Event/News Postings") %>
</div>
</div>
<% end %>
</div>
News.rb
class News < ApplicationRecord
if Rails.env.development?
def self.search(search)
if search
where('category LIKE ?', "%#{search}%")
else
scoped
end
end
end
end
News Controller:
def index
if params[:search]
#news = News.search(params[:search]).page(params[:page]).per_page(10)
else
#news = News.all.page(params[:page]).per_page(10)
end
end

Rails 5: Trying to render divs with a single partial but keep the div class unique so that JQuery doesn't fire on all partials

A bit of a confusing title.
I am trying to implement a bit of a reddit like comment system. So that you can view a Post and add a Comment to it which is polymorphic. Or, comment on another Comment.
My view looks like so:
<h2>Post:</h2>
<div class="well">
<p>
<strong>Title:</strong>
<%= #post.title %>
</p>
<% if #post.description %>
<p>
<strong>Description:</strong>
<%= #post.description %>
</p>
<% end %>
</div>
<% if current_user %>
<%= render "shared/comment_form" %>
<% else %>
<p>Log in to add comments</p>
<% end %>
<% if #post.comments.any? %>
<%= render "shared/comment_list" %> # Another comment_form inside of this partial
<% else %>
<p>No comments yet</p>
<% end %>
Inside of comment_list is another rendering of comment_form so that you can comment on a comment:
<h2>Comments</h2>
<ul>
<% #post.comments.each do |co| %>
<li><%= co.body %></li>
<%= render "shared/comment_form" if current_user %>
<% end %>
</ul>
Finally, my comment form itself:
<div id="comment-form" class="form-group">
<%= form_for #comment, remote: true, url: post_comments_path(#post) do |f| %>
<%= f.text_area :body, required: true, rows: 5, class: "form-control" %>
<%= f.hidden_field :commentable_id, :value => #post.id %>
<%= f.hidden_field :commentable_type, :value => #post.class.name %>
<%= f.hidden_field :user_id, :value => current_user.id %>
<br>
<%= f.submit class: "btn btn-primary" %>
<% end %>
</div>
<span id="add-comment">Add a comment</span>
And the Jquery code that acts on the comment_form:
$(document).on('turbolinks:load', function() {
$("#comment-form").hide();
$('#add-comment').click( function() {
$("#comment-form").fadeToggle("fast");
($("#add-comment").text() === "Cancel") ? $("#add-comment").text("Add comment") : $("#add-comment").text("Hide");
});
});
My question is:
How could I separate these divs so that Jquery doesn't fire on all instances of id="comment-form? I would like to pass in an erb tag like <%= #post.class.name %><%= #post.id %>, but again, keep the variable universal. Then, how could I implement that unique id name in my JQuery code.
Edit: I got one part of my question solved. I left the rest of what I wasn't able to do up for everyone to see.
You could use prev() like this:
$(document).ready(function() {
$('.comment-form').hide();
$('.add-comment').click( function(event) {
// Store the button which has just been clicked on a variable
var eventTarget = $(event.target);
// Find the previous element with the #comment-form and id and toggle it
eventTarget.prev('.comment-form').fadeToggle('fast');
// Use the eventTarget Again
(eventTarget.text() === 'Cancel') ? eventTarget.text('Add comment') : eventTarget.text('Cancel');
});
});
You can see this in action here: http://codepen.io/rebagliatte/pen/MbKNJv

Use Jquery to show form when clicking "Add Object" button in Rails app

I'm trying to make an "Add Car" button that when clicked shows the form that the user uses to add a car to their profile. I think I have the jQuery right, but I'm unsure of how to connect the button id and form to the script to make it work right. I currently have:
home.html.erb
<div class="row">
<aside class="col-md-4">
<section class="user_info" %>
<%= render 'shared/user_info' %>
</section>
<%= link_to "Add Car", shared/car_form, id: "add", class: "btn btn-lg btn-primary" %> //button that I want to hide/show the form
<section class="car_form">
<%= render 'shared/car_form' %> // current version that shows the form without having to click a button
</section>
</aside>
<div class="col-md-8">
<h3>My Cars</h3>
<%= render 'shared/feed' %>
</div>
</div>
<script type="text/javascript">
$(document).ready(function() {
$('shared/car_form').hide(); // inserted form id, hides form
$('add').click(function() { // inserted button id
$('shared/car_form').show(); // inserted form id, shows form
});
});
</script>
And here is the car form, located in the "shared" folder
_car_form.html.erb
<%= form_for(#car, html: {multipart: true}) do |f| %>
<%= render 'shared/error_messages', object: f.object %>
<h3> Add Your Car</h3>
<div class="field">
<%= f.text_area :year, placeholder: "Year i.e. '1993" %>
<%= f.text_area :brand, placeholder: "Brand i.e. 'Ford'"%>
<%= f.text_area :model, placeholder: "Model i.e. 'Mustang'" %>
<%= f.text_area :vin, placeholder: "17 digit VIN number" %>
<%= f.text_area :mileage, placeholder: "Current Car Mileage" %>
</div>
<%= f.submit "Add Car", class: "btn btn-primary" %>
<span class="picture">
<%= f.file_field :picture, accept: 'image/jpeg,image/gif,image/png' %>
</span>
<% end %>
<script type="text/javascript">
$('#car_picture').bind('change', function() {
size_in_megabytes = this.files[0].size/1024/1024;
if (size_in_megabytes > 5) {
alert('Maximum file size is 5MB. Please choose a smaller file.');
}
});
</script>
jQuery has been added to the gem file and installed. Need help implementing it.
$('.btn-primary').on('click',function(evt) {
$('.car_form').show();
});

Rails Tabbed View using Javascript

I'm trying to use tabifier in my rails app so I have:
<%= stylesheet_link_tag "example", "example-print" %>
<%= javascript_include_tag 'tabber.js' %>
<script>
/* Optional: Temporarily hide the "tabber" class so it does not "flash"
on the page as plain HTML. After tabber runs, the class is changed
to "tabberlive" and it will appear. */
document.write('tabber{display:none;}');
</script>
<div class="tabber">
<div class="tabbertab">
<h2>Tab 1</h2>
<%= form_for(resource, :as => resource_name, :url => registration_path(resource_name), :html => { :method => :put }) do |f| %>
<%= devise_error_messages! %>
<div><%= f.label :peeruser %><br />
<%= f.select :peeruser, [['Not yet','not yet'],['Beginner','beginner'],['Intermediate','intermediate'],['Expert','expert']] %></div>
<div><%= f.label :discipline %><br />
<%= f.text_field :discipline %></div>
<div><%= f.label :course %><br />
<%= f.text_field :course %></div>
<div><%= f.label :concept %><br />
<%= f.select :concept, [['Yes','yes'],['No','no']] %></div>
<div><%= f.submit "Continue" %></div>
<% end %>
</div>
<div class="tabbertab">
<h2>Tab 2</h2>
<p>Tab 2 content.</p>
</div>
<div class="tabbertab">
<h2>Tab 3</h2>
<p>Tab 3 content.</p>
</div>
</div>
<%= link_to "Back", :back %>
And I can't figure out why it's not loading correctly like the examples:
http://www.barelyfitz.com/projects/tabber/
I put the javascript if under public->javascripts and the css under public->stylesheets - like it just shows the text, none of it is linkable and it displays all the form information.
not exactly a solution, but why not use a more popular and feature-rich library ?
JqueryUI features a nice and simple way to implement tabs.
Once the lib is loaded, all you will have to do is
<script>
$(function() {
$( ".tabber" ).tabs();
});
</script>
then add some links, reclass all your divs and bam ! instant tabs.
Plus, you have all the Jquery Lib, which is pure awesomeness.
Turns out I had not put the css and js in the assets folder which was causing the problem.

Hiding a div when mouse is clicked on any part of the page, other than the div

Currently, I have a button called 'Comment' that when clicked slides down a comment box. I want the comment box to hide whenever the user clicks on any area of the page other than the comment box itself.
Currently, with my code the button just disappears when it is clicked. Could anyone point me in the right direction? Thanks!
Ruby ERB:
<% #entry.each do |e| %>
<div class="entry">
<p><%= e.entry %></p>
<small>Posted by <%= e.author %> at <%= e.created_at.strftime("%I:%M%p %m/%d/%Y") %></small>
<% if e.comments.nil? %>
<p>No Comments</p>
<% else %>
<% e.comments.each do |c| %>
<div class="comment">
<blockquote><strong><%= c.author %></strong> writes:<%= c.comment %></blockquote>
</div>
<% end %>
<% end %>
<div class="comments">
Comment
<div class="newcomment" id="comment<%= e.id %>">
<%= form_for #comment, :url => entry_comments_path(e, #comment) do |f| %>
<ol>
<li><%= f.label :author %>
<%= f.text_field :author %></li>
<li><%= f.label :comment %>
<%= f.text_area :comment %></li>
<%= f.submit %>
</ol>
<% end %>
</div>
</div>
</div>
<hr />
<% end %>
<%= button_to "Write A Message", new_entry_path, :method => :get %>
Javascript:
// Place your application-specific JavaScript functions and classes here
// This file is automatically included by javascript_include_tag :defaults
$(document).ready(function()
{
$('.newcommentbutton').click(function()
{
var button = $(this);
var comment = button.attr('data-comment');
button.hide();
$('#comment' + comment).slideDown('fast', function() {
$('#comment' + comment + ' input[type=text]').focus();
});
});
$('.newcomment').click(function(event)
{
event.stopPropagation();
});
$('body').click(function()
{
$('.newcomment').hide();
});
});
Your new comment buttons also needs to stop propagation, like this:
$('.newcommentbutton').click(function(e) {
var button = $(this);
var comment = button.attr('data-comment');
button.hide();
$('#comment' + comment).slideDown('fast', function() {
$('#comment' + comment + ' input[type=text]').focus();
});
e.stopPropagation();
});
You have the right idea, just remember that .newcommentbutton is also in <body> so it's opening the comment form, then the click bubbles up and closes it.
If you have a div like that:
<div id="comment"...>
You can put the focus on it, when you show it:
document.getElementById('comment').focus();
You need to set a tabindex attribute to your DIV to make the focus work:
<div id="comment" tabindex="99"...>
Then you set an onblur on it, and it will disappear, when the user click anywhere on the page:
document.getElementById('comment').onblur = function(){
this.parentNode.removeChild(this);
};

Categories