This is for someone else. I’m including some comments for explanation, but the target reader(s) will understand. Sorry, folks, it was more readable than email.
from Entries controller – gets appropriate entries, plus start and end date.
1: class EntriesController < ApplicationController
2: before_filter :login_required
3:
4: def index
5:
6: @week_num = 0
7: if !params[:week].blank?
8: @week_num = params[:week].to_i
9: end
10:
11: @entries, @begin_date, @end_date = current_user.entries.find_for_week @week_num
12:
13: respond_to do |format|
14: format.html
15: format.js {render :layout => false, :partial => "list", :locals => { :entries => @entries, :begin_date => @begin_date, :end_date => @end_date }}
16: end
17: end
18:
19: ...
20:
21: end
Entry model method – does the dirty work of getting the records. returns records plus dates.
1: class Entry < ActiveRecord::Base
2: belongs_to :user
3:
4: def self.find_for_week(num)
5: # finds weeks in reverse order. 0 is current week. 1 is last week, 2 is 2 weeks ago. etc.
6: #assume monday is first day of week
7: t_now = Time.now - (7*24*60*60 * num)
8: t_wday = t_now.wday==0 ? 6 : t_now.wday-1
9: t_mon_begin = t_now - (t_wday)*24*60*60 - t_now.hour*60*60 - t_now.min*60 - t_now.sec
10: t_sun_end = t_mon_begin + 7*24*60*60 - 1
11: entries = find_all_by_on_date(t_mon_begin..t_sun_end, :order => 'on_date DESC') # ..finds all within range.
12: return entries, t_mon_begin, t_sun_end
13: end
14:
15: end
index.html.erb – renders the header, new link, and partial with list. update div is for the ajax call.
1:
2: <h2>Time Entries</h2>
3: <p><%= link_to 'new', new_entry_path, :class=>'applink', :id => 'new' %></p>
4:
5: <div id="update">
6: <%= render :partial => "list", :locals => { :entries => @entries } %>
7: </div>
_list.html.erb – renders links for ajax navigation, and list of records.
1: <% if @week_num > 0 %>
2: <%= link_to 'Next Week', '/entries?week=' + (@week_num.to_i - 1).to_s, :class => "get"%>
3: <% end %>
4: <%= link_to 'Prev Week', '/entries?week=' + (@week_num.to_i + 1).to_s, :class => "get"%>
5: <input type='hidden' value='<%= @week_num.to_i + 1 %>' id='weeknumber' />
6:
7: <% if flash[:notice] or flash[:message] or flash[:error] %>
8: <div id="flash" class="flash_html">
9: <%= flash[:notice] unless flash[:notice].blank?%>
10: <%= flash[:error] unless flash[:error].blank?%>
11: <%= flash[:message] unless flash[:message].blank?%>
12: </div>
13: <% end %>
14: <br/>
15:
16: <p> For week starting on: <%= @begin_date.strftime('%a, %b %d %Y') %></p>
17: <table cellpadding='3px' cellspacing='3px' border='0px'>
18: <tr>
19: <th width="30px"></th>
20: <th width="100px">Action</th>
21: <th width="100px">Date</th>
22: <th width="60px">Hours</th>
23: <th width="150px">Project Code</th>
24: <th width="200px">Description</th>
25: </tr>
26: <%= render :partial => "entry_row", :collection => @entries %>
27: </table>
_entry_row.html.erb – renders the actual row data
1: <tr>
2: <td><%= entry_row_counter+1 %></td>
3: <td><%= link_to 'edit', edit_entry_path(entry_row) %> | <%= link_to("delete", {:action => "destroy", :id => entry_row}, :confirm => "Are you sure you want to delete this entry?", :method => :delete) %></td>
4: <td><%=h entry_row.on_date.strftime('%b %d %Y') %></td>
5: <td><%=h entry_row.hours %></td>
6: <td><%=h entry_row.code %></td>
7: <td><%=h entry_row.description %></td>
8: </tr>
from application.js – jquery javascript used for ajax call, updating html, and setting click method on certain links
1: jQuery.fn.getWithAjax = function() {
2: this.unbind('click', false);
3: this.click(function() {
4: //$.get($(this).attr("href"), $(this).serialize(), null, "script");
5: $.ajax({
6: url: $(this).attr("href"),
7: type: 'get',
8: dataType: 'html',
9: success: function(msg){
10: $('#update').html(msg);
11: ajaxLinks();
12: }
13: });
14: return false;
15: })
16: return this;
17: };
18:
19: //This will "ajaxify" the links
20: function ajaxLinks(){
21: $('.ajaxForm').submitWithAjax();
22: $('a.get').getWithAjax();
23: $('a.post').postWithAjax();
24: $('a.put').putWithAjax();
25: $('a.delete').deleteWithAjax();
26: }
27:
28: $(document).ready(function() {
29: //default click event for all links
30: $('#applink').unbind('click', false);
31: $('#applink').click(function() {
32: self.location = $(this).attr("href");
33: return false;
34: })
35:
36: $.ajaxSettings.accepts.html = $.ajaxSettings.accepts.script;
37:
38: $(document).ajaxSend(function(event, request, settings) {
39: if (typeof(window.AUTH_TOKEN) == "undefined") return;
40: // <acronym title="Internet Explorer 6">IE6</acronym> fix for http://dev.jquery.com/ticket/3155
41: if (settings.type == 'GET' || settings.type == 'get') return;
42: settings.data = settings.data || "";
43: settings.data += (settings.data ? "&" : "") + "authenticity_token=" + encodeURIComponent(window.AUTH_TOKEN);
44: });
45:
46: $(document).ajaxSend(function(event, request, settings) {
47: if ( settings.type == 'post' ) {
48: settings.data = (settings.data ? settings.data + "&" : "")
49: + "authenticity_token=" + encodeURIComponent( AUTH_TOKEN );
50: }
51: });
52: ajaxLinks();
53:
54: $(document).bind('keyup', 'Ctrl+l', function(){ self.location = "/login"; } );
55: $(document).bind('keyup', 'Ctrl+r', function(){ self.location = "/register"; } );
56: $(document).bind('keyup', 'Ctrl+e', function(){ self.location = "/entries"; } );
57: $(document).bind('keyup', 'Ctrl+o', function(){ self.location = "/logout"; } );
58: $(document).bind('keyup', 'Ctrl+n', function(){
59: //alert($('a#new').length);
60: if($('a#new').length) {
61: //$('a.new').trigger('click');
62: $('a#new').click();
63: }
64: } );
65: });
screenshot – looks like this because a good css and design haven’t been added. this is after navigating back a couple weeks; notice the url shows it wasn’t just navigating pages.
