Module: Pagy::Frontend

Overview

Frontend modules are specially optimized for performance. The resulting code may not look very elegant, but produces the best benchmarks

Constant Summary

Constants included from ItemsExtra::Frontend

ItemsExtra::Frontend::ITEMS_PLACEHOLDER

Instance Method Summary collapse

Methods included from UikitExtra

#pagy_uikit_combo_nav_js, #pagy_uikit_nav, #pagy_uikit_nav_js

Methods included from UrlHelpers

#pagy_url_for

Methods included from NavsExtra

#pagy_combo_nav_js, #pagy_nav_js

Methods included from TrimExtra

#pagy_trim

Methods included from BulmaExtra

#pagy_bulma_combo_nav_js, #pagy_bulma_nav, #pagy_bulma_nav_js

Methods included from ItemsExtra::Frontend

#pagy_items_selector_js

Methods included from SupportExtra

#pagy_next_link, #pagy_next_link_tag, #pagy_next_url, #pagy_prev_link, #pagy_prev_link_tag, #pagy_prev_url

Methods included from SemanticExtra

#pagy_semantic_combo_nav_js, #pagy_semantic_nav, #pagy_semantic_nav_js

Methods included from BootstrapExtra

#pagy_bootstrap_combo_nav_js, #pagy_bootstrap_nav, #pagy_bootstrap_nav_js

Methods included from FoundationExtra

#pagy_foundation_combo_nav_js, #pagy_foundation_nav, #pagy_foundation_nav_js

Methods included from StandaloneExtra

#pagy_url_for

Methods included from MaterializeExtra

#pagy_materialize_combo_nav_js, #pagy_materialize_nav, #pagy_materialize_nav_js

Methods included from Pagy::FrontendHelpers::Frontend

#pagy_json_attr, #pagy_marked_link

Instance Method Details

#pagy_info(pagy, pagy_id: nil, item_name: nil, i18n_key: nil) ⇒ Object

Return examples: “Displaying items 41-60 of 324 in total” or “Displaying Products 41-60 of 324 in total”



47
48
49
50
51
52
53
54
55
56
57
58
59
# File 'lib/pagy/frontend.rb', line 47

def pagy_info(pagy, pagy_id: nil, item_name: nil, i18n_key: nil)
  p_id    = %( id="#{pagy_id}") if pagy_id
  p_count = pagy.count
  key     = if    p_count.zero?   then 'pagy.info.no_items'
            elsif pagy.pages == 1 then 'pagy.info.single_page'
            else                       'pagy.info.multiple_pages' # rubocop:disable Lint/ElseLayout
            end

  %(<span#{p_id} class="pagy-info">#{
      pagy_t key, item_name: item_name || pagy_t(i18n_key || pagy.vars[:i18n_key], count: p_count),
                  count: p_count, from: pagy.from, to: pagy.to
    }</span>)
end

Return a performance optimized proc to generate the HTML links Benchmarked on a 20 link nav: it is ~22x faster and uses ~18x less memory than rails’ link_to



63
64
65
66
67
68
69
70
71
72
73
74
75
# File 'lib/pagy/frontend.rb', line 63

def pagy_link_proc(pagy, link_extra: '')
  p_prev      = pagy.prev
  p_next      = pagy.next
  left, right = %(<a href="#{pagy_url_for pagy, PAGE_PLACEHOLDER}" #{
                    pagy.vars[:link_extra]} #{link_extra}).split(PAGE_PLACEHOLDER, 2)
  lambda do |page, text = pagy.label_for(page), extra_attrs = ''|
    %(#{left}#{page}#{right}#{ case page
                               when p_prev then ' rel="prev"'
                               when p_next then ' rel="next"'
                               else             ''
                               end } #{extra_attrs}>#{text}</a>)
  end
end

#pagy_nav(pagy, pagy_id: nil, link_extra: '', **vars) ⇒ Object

Generic pagination: it returns the html with the series of links to the pages



18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
# File 'lib/pagy/frontend.rb', line 18

def pagy_nav(pagy, pagy_id: nil, link_extra: '', **vars)
  p_id   = %( id="#{pagy_id}") if pagy_id
  link   = pagy_link_proc(pagy, link_extra: link_extra)
  p_prev = pagy.prev
  p_next = pagy.next

  html = +%(<nav#{p_id} class="pagy-nav pagination" aria-label="pager">)
  html << if p_prev
            %(<span class="page prev">#{link.call p_prev, pagy_t('pagy.nav.prev'), 'aria-label="previous"'}</span> )
          else
            %(<span class="page prev disabled">#{pagy_t('pagy.nav.prev')}</span> )
          end
  pagy.series(**vars).each do |item| # series example: [1, :gap, 7, 8, "9", 10, 11, :gap, 36]
    html << case item
            when Integer then %(<span class="page">#{link.call item}</span> )
            when String  then %(<span class="page active">#{pagy.label_for(item)}</span> )
            when :gap    then %(<span class="page gap">#{pagy_t('pagy.nav.gap')}</span> )
            else raise InternalError, "expected item types in series to be Integer, String or :gap; got #{item.inspect}"
            end
  end
  html << if p_next
            %(<span class="page next">#{link.call p_next, pagy_t('pagy.nav.next'), 'aria-label="next"'}</span>)
          else
            %(<span class="page next disabled">#{pagy_t('pagy.nav.next')}</span>)
          end
  html << %(</nav>)
end

#pagy_t(key, **opts) ⇒ Object

Similar to I18n.t: just ~18x faster using ~10x less memory (@pagy_locale explicitly initialized in order to avoid warning)



79
80
81
# File 'lib/pagy/frontend.rb', line 79

def pagy_t(key, **opts)
  Pagy::I18n.t(@pagy_locale ||= nil, key, **opts)
end