Table: RailsNotes
User: dreamable
Created at: 2021-02-12 23:24:44 UTC
Updated at: 2021-02-12 23:33:48 UTC
Reference:(Table ID 3, Record ID 22)

标题 :
Rails Load More (2)
笔记 :

Rails Load More

I want to improve it by using multiple tabs in the same page.

  1. improve Javascript to pass both record ID and section ID

    // Improvement: multiple in the same page. The HTML layout must be
    //   <div id="unique_id">
    //     <div class="container">
    //       <div class="record" date-id=object_id>
    //       </div>
    //       <div class="record" date-id=object_id>
    //       </div>
    //     </div>
    //     <div class="load-more-container">
    //       <img class="loading-gif"></img>
    //       <a class="load-more">load more </a>
    //     </div>
    //   </div>
    $(document).on("turbolinks:load", function() {
    // when the load more link is clicked
    $('a.load-more').click(function (e) {
    console.log("Load-more clicked")
    // prevent the default click action
    e.preventDefault();
    // hide load more link
    $(this).siblings('.load-more').hide();
    // show loading gif
    $(this).siblings('.loading-gif').show();
    // Section
    var section = $(this).parent().parent()
    var section = section.attr('id')
    console.log(`Section ID: ${section}`)
    // Container
    var cobj = $(this).parent().siblings(".container") // container object
    // get the last id and save it in a variable 'last-id'
    var last_id = cobj.find('.record').last().attr('data-id');
    console.log(`Last ID: ${last_id}`)
    // make an ajax call passing along our last user id
    $.ajax({
      // make a get request to the server
      type: "GET",
      // get the url from the href attribute of our link
      url: $(this).attr('href'),
      // send the last id to our rails app
      data: {
        record: last_id,
        section: section
      },
      // the response will be a script
      dataType: "script",
      // upon success
      success: function (data,status,xhr) {
        console.log("AJAX done")
        // hide the loading gif. TODO: how about mutliple?
        $('.loading-gif').hide();
        // show our load more link
        $('.load-more').show();
      }
    });
    });
    });
    
  2. Use Record ID and Section ID in controller to get new records

    @limit = params[:limit] || 20;
    @record = params[:record]; @section=params[:section] # operation, also section ID
    cond = {user: current_user};
    cond[:id] = (0..@record.to_i-1) if @record
    if @section
      # List
      cond[:operation] = @section
      @activities = Activity.where(cond).limit(@limit)
    else
      # Hash of activities
      @activities = {}
      Activity.operations.each do |opt, value|
        cond[:operation] = opt
        @activities[opt] = Activity.where(cond).limit(@limit)
      end
    end
    respond_to do |format|
     format.html
     format.js
    end
    
  3. Append result to specified section in js.erb

    <% if @activities.empty? %>
    $('#<%=@section%> .load-more-container').hide()
    <% else %>
    $('#<%=@section%> .container').append('<%= escape_javascript(render(partial: "home/activity",collection: @activities)) %>')
    <% end %>
    
  4. Set multiple tabs by using Bootstrap

    <ul class="nav nav-tabs nav-pills" role="tablist">
    <% Activity.operations.each_with_index do |opt,idx| %>
    <% opt = opt[0]%>
    <% cls = idx==0 ? "active" : "" %>
    <% select = (idx==0)  %>
    <li class="nav-item">
      <a class="nav-link <%=cls%>" id="<%=opt%>-tab" href="#<%=opt%>" data-toggle="tab" role="tab" aria-controls="<%=opt%>" aria-selected="<%= select %>"><%=t("models.activity.operations.#{opt}")%></a>
    </li>
    <% end %>
    </ul>
    <div class="tab-content mt-2">
    <% Activity.operations.each_with_index do |opt,idx| %>
    <% opt = opt[0] %>
    <% cls = (idx==0) ? "active" : "" %>
    <div class="tab-pane fade show <%=cls%>" id="<%=opt%>" role="tabpanel" aria-labelledby="<%=opt%>-tab">
      <div class="container row">
        <%= render partial: "home/activity", collection: @activities[opt] %>
      </div>
      <div class="load-more-container text-center">
        <%= image_tag "ajax-loader.gif", style: "display:none;", class: "loading-gif" %>
        <%= link_to t('views.load_more'), "#", class: "load-more"%>
      </div>
    </div>
    <% end %>
    </div>
    
Tag: