I use the simple-form gem in a rails 3.1 project together with twitter bootstrap. I have several form views which all look fine. But now I like to style the text input field in one of the forms so it gets a bit smaller. The text input field is located in the edit form view of one of my controllers called "roles". The partial for the form looks like this:
= simple_form_for #role, :html => { :class => 'form-horizontal' } do |f|
= f.error_notification
= f.input :name
= f.input :description
.form-actions
= f.button :submit, :class => 'btn-primary'
= link_to t('.cancel', :default => t("helpers.links.cancel")), roles_path, :class => 'btn'
There is a style file under:
app/assets/stylesheets/roles.css.scss
which was created with the scaffold command. I tried to put some styling in here but this results in a change in every form of my application. Is there a good way to change the styling of a text input field only for one special form view with simple form? Where should I put the styling and how would the styling look like if I'd like to have the input text field in the size: width 100px to height 50px?
You need to know that even if you have a special CSS file just for roles. In the end, every CSS file is bundled up and served together. This means, that roles.css will be loaded on every page, which results in the behavior you described.
If you want to style a single form, you can do this by adding a class:
= simple_form_for #role, :html => { :class => 'form-horizontal roles-form' } do |f|
Now you can scope your CSS definitions to .roles-form and they will only apply to this single form.
Related
I've successfully installed the gem 'redactor'rails' and can call it in a form, and update a note successfully.
Problem: When creating a post, the form renders multiple input areas. When I update/edit an existing post, the more times I click "Edit", more input areas are rendered. Why does it render multiple fields?
_form.html.haml
= simple_form_for #note do |f|
= f.input :title
= f.input :content, :input_html => { :class => "redactor" }
= f.button :submit, class: "button"
You should destroy old instances of Redactor for each selector before initializing it.
$('.redactor').redactor('core.destroy');
I'm using simple form for a basic login form for my site within the nav area at the top of the page.
Currently, it's spilling the form fields over two rows and no matter how many display: inline attributes I apply. It still refuses to go back onto one line.
What im trying to do is restrict the number of characters in the form so that the fields fit onto one line.
Here's my current form code..
<%= simple_form_for("user", :url => user_session_path, :html => {:id => "sign_in", :class => 'form-inline' }, :remote => true, :format => :json) do |f| %>
<%= f.input :email %>
<%= f.input :password %>
<%= f.submit 'Login' %>
<%= link_to "Forgot your password?", new_password_path('user') %>
<% end %>
Easy way is to simply use the maxlength html attribute for inputs:
f.input :name, :input_html => { :maxlength => x }
But that will just restrict the number of characters that can be added into a single input. If your problem is with the width of those inputs, just use CSS to specify a custom width per input so the inputs won't overflow into a second line.
I have run into a bit of a problem and a head scratcher, as I'm not sure whether what I want to do is even possible with RoR.
A bit of background info: I have an app with several controllers... and would like to work with 2 of them for this modal example. The first is a users_controller and the other is a recommendations_controller.
Here is what I'm trying to do: In the user index view I have a lists of posts. Each post has a recommend button. If a user clicks it he/she is sent to the recommendation index page, and can search and find a user he/she would like to share the post with. The reason I have it set up this way is because the Recommendation model creates the recommend relationship.
I would like like it so when the user clicks the recommend button on the User index page, a modal appears (one that accesses the recommendation controller) and the user can search for the user he/she would like to share the post with. Basically, I want to know whether it's possible to access the Recommendation controller via the User controller's index view page.
If it's not, is there a work around? I can post the code I have if it's helpful, but I'm not sure that would help in this case--as I'm trying to see whether it's even possible to do what I'm trying to do.
Thank you!
More Details:
recommendations_controller:
def index
#user = Search.find_users(params[:name], current_profile)
respond_to do |format|
format.html
format.js
end
end
index.js.haml (located in the view/recommendations folder)
:plain
$(#my-modal).show();
index.html.haml (located in the view/recommendations folder)
= form_tag post_recommendations_url, :method => "get" do
= text_field_tag :name, '', :class => "span12", :placeholder => "Please enter the name of the users you would like to share this post with."
%center
= submit_tag "Search", :class => "btn btn-primary"
index.html.haml (located in the view/posts folder)
%a{:href => "#{post_recommendations_path(post)}", :remote => true}
%i.icon-share.icon-large
Recommend Post
#my-modal.modal.hide.fade
.modal-header
%a.close{"data-dismiss" => "modal"} ×
%h6 This is a header
.modal-body
%p This is where I would like the contents of the index.html.haml file, located in the view/recommendations folder to appear.
Part 2: Displaying the search results inside the modal/partial
Matzi, at the moment, a user clicks a link near the post they want to recommend. This link renders the modal with a partial (_recommendation.html.haml) inside of it.
This partial (now inside the modal) contains the search form_tag and the code to render all the users that match the search results. Unfortunately, when I try to run a search by entering a name and clicking the search button (again, now located inside of the modal) it takes me to the following url instead of rendering the results inside the modal.
http://localhost:3000/posts/2/recommendations?utf8=%E2%9C%93&name=Test&commit=Search
here is what my updated index.html.haml (located in the view/posts folder) looks like:
= link_to 'Recommend Post', post_recommendations_path(post), :remote => true, "data-toggle" => "modal"
#my-modal.modal.hide
.modal-header
%a.close{"data-dismiss" => "modal"} ×
%h6
%i.icon-share.icon-large
Recommend Post
.modal-body
#modal-rec-body
%p *this is where _recommendation.html.haml is rendered*
updated index.js.haml
:plain
$("#modal-rec-body").html("#{escape_javascript(render('recommendations/recommendation'))}");
$('#my-modal').modal({
keyboard: true,
show: true
});
_recommendation.html.haml
.span12
= form_tag post_recommendations_path, :method => "get" do
= text_field_tag :name, '', :class => "span12", :placeholder => "Please enter the name of the user you would like to share this post with.", :style => "max-width:520px;"
%center
= submit_tag "Search", :class => "btn btn-primary", :remote => "true"
- #user.each do |i|
- unless current_profile == i
.row-fluid
.span6
.row-fluid
.well{:style => "margin-left:0px;"}
.row-fluid
.span2
=image_tag i.avatar(:bio), :class=> "sidebar_avatar"
.span6
%dl{:style => "margin:0px"}
%dt
%i.icon-user
Name
%dd= i.name
%dt
%i.icon-map-marker
Location
%dd= i.location
.span4
- form_for :recommendation do |r|
= r.hidden_field :friend_id, :value => i.account.id
= r.submit "Send Recommendation", :class => "btn btn-primary"
Problem: Unfortunately it seems that when I click the submit (search) button inside the modal instead of rendering the results inside the modal it re-directs the browser to the post_recommendations_path (posts/post.id/recommendations). I would like to display the search results inside the modal without having it redirect to the post recommendations path.
As always, thank you so much! I'm extremely grateful for your help--and I've gotten a much better grasp for AJAX thanks to you. Thank you!
Of course you can do this, but it needs some ajax magic.
First of all, you need to create an action, responding to .js requests, in the recommendation controller. It is done so far in your update. But, your .js is not quite right. The problem is that you render the modal form from the post view, but propably in post controller you dont have the right fields. I recommend the following .js.erb:
$("#modal-body").html(<%= escape_javascript render(:partial => 'recommendations/index')%>);
$("#my-modal").show();
This fills the modal with the form. The next step is to do a remote request from this form. Modify your posts/index the following way:
= form_tag post_recommendations_url, :remote => true, :method => "get" do
= text_field_tag :name, '', :class => "span12", :placeholder => "Please enter the name of the users you would like to share this post with."
%center
= submit_tag "Search", :class => "btn btn-primary"
The difference is the :remote => true tag, this sends an ajax request to your controller, so you must prepare for .js and .html response (in case of no JS on client). The .js should hide the modal form, and may refresh the original page, the html may redirect you back to the post.
Part 2:
The problem is the :remote part. It needs to be part of the form's definition, not the submit button's. My mistake.
I found this guide now, it seems quite good.
I hope it helps! Ask if something is not clear.
In formtastic, when create a semantic form, the layout of the object's attributes are always listed vertically (one attribute label & value occupy one row) by default.
How to customize the layout so that part of the attributes could be in horizental position. For example, I would like to have "body" attribute located on the right side of "title". How to do that?
<% semantic_form_for #post do |form| %>
<% form.inputs do %>
<%= form.input :title %>
<%= form.input :body %>
<%= form.input :section, :as => :radio %>
...
Formtastic provides lots of HTML class and id hooks on the wrapper <li> and elsewhere so that you can style different types of inputs generically (eg li.string) or specific inputs differently (eg li#user_email_input).
You can, as other answers mentioned, add extra classes to the wrapper with :wrapper_html => { :class => 'whatever' } to give yourself new hooks when the options above aren't suitable.
From here, it's purely a style/CSS problem. You probably want to float the <li> wrappers against each other with float:left; and then clear the floats on the containing <ol> with overflow:auto; or any other clearing technique of your preference.
You can use CSS to accomplish this task:
<%= form.input :title, :wrapper_html => {:class => "left"} %>
Then in your stylesheet:
.left
{
float: left;
/* etc. */
}
This will style the container of the form element (li by default)
You'd simple have to change the CSS. However I suggest you just build up the form elements yourself if you need layout customization for specific attributes.
Intro
I have an object #organization that has_many :quick_facts
Basically, I want to produce a _form for each :quick_fact but with one save button, that saves all of the quick_facts.
My two problems:
First Problem:
My quick_facts are not prepopulated with their information. They only appear as blank for each quick_fact I have.
Second Problem
A save button appears on every single form
My sad sad attempt :
- for quick_fact in #organization.quick_facts
- fields_for :quick_facts do |f|
= f.error_messages :header_message => FORM_ERROR_HEADER_MESSAGE, :message => FORM_ERROR_MESSAGE
= f.label :quick_fact, 'QuickFact'
%br/
= f.select :quick_fact, QUICK_FACTS, {}
%br/
= f.submit 'save', :class => 'button'
You really just want one form here, since you want to submit everything at once.
Here is what I would recommend:
Use a partial to render the label and the text option for the quick fact (if you want it to be text). You want this partial to be rendered once per quick fact, so use the :collection option on the render method to specify the collections of quick facts. Each partial will get its own local copy of whatever quickfact you are on, and a variable called quickfact_counter will also be created.
In addition, you will want to use the :locals option to pass the form to the partial as a local variable, so that you can do f.label, f.text_area
So, in conclusion, your new form will be something like this:
<% form_for #organization do |form| %>
<%= render :partial => "partial_name", :collection => #organization.quick_facts, :locals => {:form => form} %>
<%=form.submit 'save', :class => 'button'%>
<% end %>
Then your partial will just have
<%= form.label :quick_fact, 'QuickFact' %>
<%= form.text_field :quick_fact %>
If you wanted to get even fancier you could use a layout to render the form and have it defer to the partial, but this should be enough to get you started. Being able to pass a collection to a partial is one of my favorite Rails features.