Class: Locomotive::Steam::Liquid::Tags::InheritedBlock

Inherits:
Liquid::Block
  • Object
show all
Includes:
Concerns::Attributes
Defined in:
lib/locomotive/steam/liquid/tags/inherited_block.rb

Overview

Blocks are used with the Extends tag to define the content of blocks. Nested blocks are allowed.

{% extends home %}
{% block content }Hello world{% endblock %}

Options used to generate the UI/UX of the editable element inputs

- short_name (Boolean): use just the name and skip the name of the nested blocks.
- priority (Integer): allow blocks to be displayed before others

Constant Summary collapse

SYNTAX =
/(#{::Liquid::QuotedFragment}+)/o

Instance Attribute Summary collapse

Attributes included from Concerns::Attributes

#attributes, #raw_attributes

Instance Method Summary collapse

Constructor Details

#initialize(tag_name, markup, options) ⇒ InheritedBlock

Returns a new instance of InheritedBlock.



28
29
30
31
32
33
34
35
36
37
38
39
40
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 28

def initialize(tag_name, markup, options)
  super

  if markup =~ SYNTAX
    @name = Regexp.last_match(1).gsub(/["']/o, '').strip
  else
    raise ::Liquid::SyntaxError.new("Syntax Error in 'block' - Valid syntax: block <name>")
  end

  prepare_for_inheritance

  parse_attributes(markup, short_name: false, priority: 0, anchor: true)
end

Instance Attribute Details

#descendantObject

linked chain of inherited blocks included in different templates if multiple extends



26
27
28
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 26

def descendant
  @descendant
end

#nameObject (readonly)

Returns the value of attribute name.



22
23
24
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 22

def name
  @name
end

#parentObject

linked chain of inherited blocks included in different templates if multiple extends



26
27
28
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 26

def parent
  @parent
end

Instance Method Details

#call_super(context) ⇒ Object



107
108
109
110
111
112
113
114
115
116
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 107

def call_super(context)
  if parent
    # remove the block from the linked chain
    parent.descendant = nil

    parent.render(context)
  else
    ''
  end
end

#inherited_blocksObject



118
119
120
121
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 118

def inherited_blocks
  # initialize it in the case the template does not include an extend tag
  options[:inherited_blocks] ||= { all: {}, nested: [] }
end

#parse(tokens) ⇒ Object



66
67
68
69
70
71
72
73
74
75
76
77
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 66

def parse(tokens)
  super

  # when the parsing of the block is done, we can then remove it from the stack
  inherited_blocks[:nested].pop.tap do
    ActiveSupport::Notifications.instrument('steam.parse.inherited_block', {
      page: parse_context[:page],
      name: name,
      found_super: self.contains_super?(nodelist)
    }.merge(attributes))
  end
end

#prepare_for_inheritanceObject



42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 42

def prepare_for_inheritance
  # give a different name if this is a nested block
  if (block = inherited_blocks[:nested].last)
    @name = "#{block.name}/#{@name}"
  end

  # append this block to the stack in order to
  # get a name for the other nested inherited blocks
  inherited_blocks[:nested].push(self)

  # build the linked chain of inherited blocks
  # make a link with the descendant and the parent (chained list)
  if (descendant = inherited_blocks[:all][@name])
    self.descendant   = descendant
    descendant.parent = self

    # get the value of the blank property from the descendant
    @blank = descendant.blank?
  end

  # become the descendant of the inherited block from the parent template
  inherited_blocks[:all][@name] = self
end

#render(context) ⇒ Object



81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 81

def render(context)
  context.stack do
    # look for the very first descendant
    block = self_or_first_descendant

    # the block drop is in charge of rendering "{{ block.super }}"
    context['block'] = Drops::InheritedBlock.new(block)

    anchor_html = if live_editing?(context) && (attributes[:anchor] || attributes[:anchor].nil?)
      %{<span class="locomotive-block-anchor" data-element-id="#{name}" style="visibility: hidden"></span>}
    else
      ''
    end

    anchor_html + block.render_without_inheritance(context)
  end
end

#render_without_inheritanceObject



79
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 79

alias_method :render_without_inheritance, :render

#self_or_first_descendantObject

when we render an inherited block, we need the version of the very first descendant.



101
102
103
104
105
# File 'lib/locomotive/steam/liquid/tags/inherited_block.rb', line 101

def self_or_first_descendant
  block = self
  while block.descendant; block = block.descendant; end
  block
end