I would like to rank the memo apps that I am developing. This time, I will evaluate it in three stages. Along with that, you will learn about inputting, saving, and displaying evaluations by stars.
Add star rating function with Rails
Save the evaluation value in the rate column (type: float) of the notes table (memo table) We will assume that the tables and columns have already been created.
The column should be float type because it will store values such as "0.5" and "1.5" when evaluating with half a star.
If you have created it as an integer or string type, you will need to change the type, although the change method differs depending on the database. The article below describes a solution when you're addicted to this type of change swamp.
class CreateNotes < ActiveRecord::Migration[5.2]
def change
create_table :notes do |t|
t.text :title
t.integer :user_id
t.integer :category_id
t.text :explanation
t.float :rate
t.timestamps
end
end
end
rails db:migrate:reset
While checking the above reference link, load javascript and load the star image.
Method (2 types)
① To use jQuery Raty, download jquery.raty.js from https://github.com/wbotelhos/raty.
Place the downloaded script anywhere on your website.
Place the downloaded jquery.raty.js file in the app / javascripts folder
(2) Load JavaScript in HTML that uses jQuery Raty. Since Raty is a jQuery plugin, you also need a jQuery script.
<script src="/js/jquery.min.js"></script>
<script src="/js/jquery.raty.js"></script>
This time, we will implement it by the method of ①.
javascripts / application.js
file//= require rails-ujs
//= require activestorage
//= require turbolinks
//= require jquery #add to
//= require jquery_ujs #add to
//= require_tree .
Add Gem file
gem 'jquery-rails'
budle install
note.rb
class Note < ApplicationRecord
#Linking with users
belongs_to :user,optional: true
#Validation
validates :title, presence: true
validates :explanation, presence: true
#Link with category
belongs_to :category
validates :rate, presence: true
validates :rate, numericality: {
# only_integer: true,
less_than_or_equal_to: 3,
greater_than_or_equal_to: 1,
}
# Numericality = allow the sky
numericality also allows decimals by default. I only want to allow integers in the rate column, so only_integer.
Example
validates :param3, :numericality => { :less_than_or_equal_to => 3}
#Is the number 3 or less?
validates :param3, :numericality => { :greater_than_or_equal_to => 1 }
#Is the number 1 or more?
end
notes_controller.rb
class NotesController < ApplicationController
before_action :authenticate_user!
def new
@note = Note.new
end
def create
# @note = Note.new(note_params)
@note = current_user.notes.build(note_params)
@note.save
redirect_to notes_path
end
def index
# is_Get all records that valid matches
@categorys = Category.where(is_valid: true)
@q = Note.all.ransack(params[:q])
@notes = @q.result(distinct: true)
end
def show
@note = Note.find(params[:id])
end
def edit
@note = Note.find(params[:id])
end
def update
@note = Note.find(params[:id])
@note.update(note_params)
redirect_to note_path
end
def destroy
@note = Note.find(params[:id])
@note.destroy
redirect_to notes_path
end
def search
@categorys = Category.where(is_valid: true)
@category = Category.find(params[:id])
@q = @category.notes.all.ransack(params[:q])
@notes = @q.result(distinct: true).page(params[:page])
@title = @category.name
render 'notes/index'
end
private
def note_params
params.require(:note).permit(:title, :category_id, :explanation,:user_id,:rate)
end
end
Here we add a rate
column to the note_params
method.
_form.html.erb
<%= form_with model:note, local: true do |f| %>
<div class='form-group'>
<%= f.label :title%>
<%= f.text_field :title, class: 'form-control', id: 'note_title' %>
</div>
<div class='form-group'>
<%= f.label :Category%>
<%= f.collection_select :category_id, Category.all, :id, :name %>
</div>
<!--Evaluation-->
<div class="form-group row" id="star">
<%= f.label :rate,'importance', class:'col-md-1 col-form-label' %>
<%= f.hidden_field :rate, id: :review_star %>
</div>
<div class='form-group'>
<div id='editor'>
<%= f.label :Contents%>
<%= f.text_area :explanation, rows: 10, class: 'form-control', id: 'note_explanation', "v-model" => "input", name: "note[explanation]" %>
<h2><i class="fas fa-eye"></i> Preview</h2>
<div id="preview-field" v-html='input | marked'>
</div>
<div ></div>
</div>
<%= f.submit 'Registration', class: 'btn btn-success' %>
</div>
<% end %>
<!--Real-time preview-->
<script type="text/javascript">
window.onload = function() {
new Vue({
el: '#editor',
data: {
input: '<%== j @note.explanation %>',
},
filters: {
marked: marked,
},
});
};
<!--Evaluation-->
$('#star').raty({
size : 36,
starOff: '<%= asset_path('star-off.png') %>',
starOn : '<%= asset_path('star-on.png') %>',
starHalf: '<%= asset_path('star-half.png') %>',
scoreName: 'note[rate]',
half: true,
});
</script>
To be able to input half of # ★ half: true,
I want to display ★ in the memo list. The difference from the above "Enter and save ★" is that 1. Display without input, 2. Repeat processing.
_notes_index.html.erb
<div class='row'>
<table class='table'>
<thead>
<tr>
<th>title</th>
<th>Category</th>
<th>importance</th>
</tr>
</thead>
<tbody>
<% @notes.each do |note| %>
<% if user_signed_in? && current_user.id == note.user_id %>
<tr>
<td>
<%= link_to note_path(note) do %>
<%= note.title %>
<% end %>
</td>
<td><%= note.category.name %></td>
<!--Evaluation-->
<td>
<div id="star-rate-<%= note.id %>"></div>
<script>
//Note so that id can be unique even in iterative processing_enter id
$('#star-rate-<%= note.id %>').raty({
size: 36,
starOff: '<%= asset_path('star-off.png') %>',
starOn : '<%= asset_path('star-on.png') %>',
starHalf: '<%= asset_path('star-half.png') %>',
half: true,
//I can't input just by reading
readOnly: true,
score: <%= note.rate %>,
});
</script>
</td>
</tr>
<% end %>
<% end %>
</tbody>
</table>
</div>
<div id="note-rate-<%= note.id %>"></div>
readOnly: true,
score: <%= note.rate %>,
This completes!
Please note that the explanation may be difficult to understand. Also, if there are any mistakes, I would appreciate it if you could teach me.
Recommended Posts