Xây dựng calendar trong Ruby on Rails với simple calendar gem

Simple Calendar là thư viện được thiết kế lên để giúp các developer xây dựng calendar một cách nhanh chống và dễ dàng. Thư viện này có thể render calendar rất linh hoạt như render calendar với day view, week view, month view, .... Hơn nữa nó cũng có thể dùng để render các events vào trên calendar đó.

Cài đặt

Add vào Gemfile:

gem "simple_calendar", "~> 2.0"

=> bundle install

Add vào file app/assets/stylesheets/application.css

*= require simple_calendar

Cách sử dụng

Month Calendar

Bạn có thể generate calendar hiển thị theo tháng sử dụng method sau:

<%= month_calendar do |date| %>
  <%= date %>
<% end %>

params start_date default sẽ là current date.

Week Calendar

Bạn có thể generate calendar hiển thị theo tuần sử dụng method sau:

<%= week_calendar number_of_weeks: 2 do |date| %>
  <%= date %>
<% end %>

Trong đó number_of_weeks là số lượng tuần để hiển thị, default sẽ là 1.

Calendar với số lượng ngày bất kỳ

<%= calendar number_of_days: 4 do |date| %>
  <%= date %>
<% end %>

Trong đó number_of_days là số lượng ngày để hiển thị, default là 4.

Custom tên params

Default params start_date sẽ được dùng và hiển thị trên URL. Để customize params này thành tên khác, bạn có thể truyền start_date_param trong hàm calendar như sau:

<%= calendar start_date_param: :my_date do |date| %>
  <%= date %>
<% end %>

Rendering Events

Các method trên bạn có thể dùng nó để render thành các calendar theo tháng, tuần, ngày, ... Ở đây chúng ta sẽ dùng nó để render các sự kiện trên nó.

  • Step 1:

Create model với 2 attributes cần thiết là: start_timeend_time. Nếu model đó chỉ có attribute start_time, có nghĩa là nó là sự kiện chỉ xảy ra trong ngày. Nếu có cả end_time có nghĩa là sự kiện đó xảy ra trong vòng nhiều ngày.

# single day events
$ rails g model Meeting name start_time:datetime

# multi-day events
$ rails g model Meeting name start_time:datetime end_time:datetime

Mình sẽ create data cho event này như sau:

Meeting.create start_time: Time.current, name: "Current" 

Meeting.create start_time: Time.current + 1.day, name: "Tomorrow" 

Meeting.create start_time: Time.current, end_time: Time.current + 1.days, name: "Multi 2 days"
  • Step 2

Từ model trên, mình có thể query để lấy event đó để hiện thị trên calendar như sau:

def index
  @meetings = Meeting.all
end

Tiếp theo trong view, bạn chỉ cần truyền option events vào. Nó sẽ tự động render ngày mà sự kiện đó xảy ra với từng ngày trên calendar.

<%= month_calendar events: @meetings do |date, meetings| %>
  <%= date %>

  <% meetings.each do |meeting| %>
    <div>
      <%= meeting.name %>
    </div>
  <% end %>
<% end %

Kết quả sẽ như sau:

Đến đây mình đã xây dựng được calendar đơn giản theo yêu cầu mình muốn. Hơn nữa, mình cũng có thể customize View của calendar đó được, chị tiết hãy xem tài liệu của nó Customizing The Calendar

References

https://github.com/excid3/simple_calendar