markawesome 0.4.0 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 8a3394f03fff9ca20290650589ba70022b2f8ca71b5581f5d06cb4e06ac83f3f
4
- data.tar.gz: d5af8667249a450c3119641dc38a9f148bbb2b30a1f8c76eae138c3765617fd5
3
+ metadata.gz: c1a813451ca32ebe286489c510fd9ebc0f161877d6e20bdc50c390c8e54669c8
4
+ data.tar.gz: fe1f091910a15ebf1f825769266fdaa1ff776e1ceace7a041e0fe71370b42817
5
5
  SHA512:
6
- metadata.gz: c29d6692c8cd45f5f2a6a544de3505ff3a9af50a0d36468385f71b38daac30465ff23d15b5d94648f48690fae43d652cf495a4c7ea8d282bc96127a7376e22a3
7
- data.tar.gz: c8134fa3a4a9344efe72ffa5d4a6504763ba9ebce4a4a9c6f7d8b0907de48506ebb9a7ae843bffd0898da5379ba2ebdf9bc100978f2b86add9cec722c4e3281e
6
+ metadata.gz: 1ddf1bc53111ca053bd5fe82040ee9387783dd95f0892658697a2f38f0b7a11ebd8fa1517df4e990fbda8aaa90f465f27bb1a6f46d673b8f6fc31a24acab5070
7
+ data.tar.gz: 83ac02b6ca5cb7744579661c068511c53666bf4ec8b550a6170050ab04f8911c053db46f1b87122b91aec2024b3a564f4e21d1a34e49189fdbb0e5152df99e49
data/CHANGELOG.md CHANGED
@@ -4,6 +4,22 @@ All notable changes to this project will be documented in this file.
4
4
 
5
5
  The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
6
6
 
7
+ ## [0.5.0] - 2026-02-10
8
+
9
+ ### Added
10
+
11
+ - **LayoutTransformer**: New `::::` (quadruple colon) syntax for wrapping content in Web Awesome CSS layout containers
12
+ - Supports 6 layout types: `grid`, `stack`, `cluster`, `split`, `flank`, `frame`
13
+ - Common attributes: `gap:SIZE`, `align:VALUE`, `justify:VALUE` for all layouts
14
+ - Grid-specific: `min:CSS_VALUE` for custom minimum column size (`--min-column-size`)
15
+ - Split-specific: `row` and `column` direction modifiers
16
+ - Flank-specific: `start`/`end` position modifiers, `size:CSS_VALUE`, `content:PCT`
17
+ - Frame-specific: `landscape`/`portrait`/`square` aspect ratios, `radius:SIZE`
18
+ - Dual syntax: both `::::grid` and `::::wa-grid` work identically
19
+ - CSS value sanitization for user-provided values (strips quotes, angle brackets, semicolons)
20
+ - Inner content is not markdown-converted, allowing component `:::` syntax to be processed by subsequent transformers
21
+ - Runs first in the pipeline so layout containers wrap around component output
22
+
7
23
  ## [0.4.0] - 2026-02-09
8
24
 
9
25
  ### Added
@@ -7,6 +7,7 @@ module Markawesome
7
7
  # Main transformer that orchestrates all component transformers
8
8
  class Transformer
9
9
  def self.process(content, options = {})
10
+ content = LayoutTransformer.transform(content)
10
11
  content = BadgeTransformer.transform(content)
11
12
  content = ButtonTransformer.transform(content)
12
13
  content = CalloutTransformer.transform(content)
@@ -0,0 +1,121 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'base_transformer'
4
+
5
+ module Markawesome
6
+ # Transforms layout syntax into CSS layout utility containers
7
+ # Primary syntax: ::::type params?\ncontent\n::::
8
+ # Alternative syntax: ::::wa-type params?\ncontent\n::::
9
+ # Supported types: grid, stack, cluster, split, flank, frame
10
+ #
11
+ # Common attributes (all layouts):
12
+ # gap:SIZE - wa-gap-{SIZE} class (0, 3xs, 2xs, xs, s, m, l, xl, 2xl, 3xl)
13
+ # align:VALUE - wa-align-items-{VALUE} class (start, end, center, stretch, baseline)
14
+ # justify:VALUE - wa-justify-content-{VALUE} class (start, end, center, space-between, space-around, space-evenly)
15
+ #
16
+ # Grid-specific: min:CSS_VALUE - sets --min-column-size style
17
+ # Split-specific: row, column modifiers
18
+ # Flank-specific: start, end modifiers; size:CSS_VALUE, content:PCT
19
+ # Frame-specific: landscape, portrait, square modifiers; radius:SIZE
20
+ class LayoutTransformer < BaseTransformer
21
+ VALID_GAPS = %w[0 3xs 2xs xs s m l xl 2xl 3xl].freeze
22
+ VALID_ALIGNS = %w[start end center stretch baseline].freeze
23
+ VALID_JUSTIFIES = %w[start end center space-between space-around space-evenly].freeze
24
+ VALID_RADII = %w[s m l pill circle square].freeze
25
+
26
+ KEYWORD_MODIFIERS = {
27
+ split: %w[row column],
28
+ flank: %w[start end],
29
+ frame: %w[landscape portrait square]
30
+ }.freeze
31
+
32
+ COMMON_KEY_CLASS_MAP = {
33
+ 'gap' => ->(v) { "wa-gap-#{v}" if VALID_GAPS.include?(v) },
34
+ 'align' => ->(v) { "wa-align-items-#{v}" if VALID_ALIGNS.include?(v) },
35
+ 'justify' => ->(v) { "wa-justify-content-#{v}" if VALID_JUSTIFIES.include?(v) }
36
+ }.freeze
37
+
38
+ def self.transform(content)
39
+ primary_regex = /^::::(grid|stack|cluster|split|flank|frame)[ \t]*([^\n]*)\n(.*?)\n::::/m
40
+ alternative_regex = /^::::wa-(grid|stack|cluster|split|flank|frame)[ \t]*([^\n]*)\n(.*?)\n::::/m
41
+
42
+ transform_proc = proc do |type, params_string, inner_content|
43
+ classes, styles = build_attributes(type, params_string)
44
+ build_html(classes, styles, inner_content)
45
+ end
46
+
47
+ patterns = dual_syntax_patterns(primary_regex, alternative_regex, transform_proc)
48
+ apply_multiple_patterns(content, patterns)
49
+ end
50
+
51
+ class << self
52
+ private
53
+
54
+ def build_attributes(type, params_string)
55
+ classes = ["wa-#{type}"]
56
+ styles = []
57
+
58
+ return [classes, styles] if params_string.nil? || params_string.strip.empty?
59
+
60
+ tokens = params_string.strip.split(/\s+/)
61
+
62
+ tokens.each do |token|
63
+ process_token(type, token, classes, styles)
64
+ end
65
+
66
+ [classes, styles]
67
+ end
68
+
69
+ def process_token(type, token, classes, styles)
70
+ if token.include?(':')
71
+ process_key_value(type, token, classes, styles)
72
+ else
73
+ process_keyword(type, token, classes)
74
+ end
75
+ end
76
+
77
+ def process_key_value(type, token, classes, styles)
78
+ key, value = token.split(':', 2)
79
+ return if value.nil? || value.empty?
80
+
81
+ if COMMON_KEY_CLASS_MAP.key?(key)
82
+ css_class = COMMON_KEY_CLASS_MAP[key].call(value)
83
+ classes << css_class if css_class
84
+ else
85
+ process_type_specific_key_value(type, key, value, classes, styles)
86
+ end
87
+ end
88
+
89
+ def process_type_specific_key_value(type, key, value, classes, styles)
90
+ case key
91
+ when 'min'
92
+ styles << "--min-column-size: #{sanitize_css(value)}" if type == 'grid'
93
+ when 'size'
94
+ styles << "--flank-size: #{sanitize_css(value)}" if type == 'flank'
95
+ when 'content'
96
+ styles << "--content-percentage: #{sanitize_css(value)}" if type == 'flank'
97
+ when 'radius'
98
+ classes << "wa-border-radius-#{value}" if type == 'frame' && VALID_RADII.include?(value)
99
+ end
100
+ end
101
+
102
+ def process_keyword(type, token, classes)
103
+ modifiers = KEYWORD_MODIFIERS[type.to_sym]
104
+ return unless modifiers&.include?(token)
105
+
106
+ classes[0] = "wa-#{type}:#{token}"
107
+ end
108
+
109
+ def sanitize_css(value)
110
+ value.gsub(/["'<>;]/, '')
111
+ end
112
+
113
+ def build_html(classes, styles, inner_content)
114
+ attr_parts = ["class=\"#{classes.join(' ')}\""]
115
+ attr_parts << "style=\"#{styles.join('; ')}\"" unless styles.empty?
116
+
117
+ "<div #{attr_parts.join(' ')}>\n#{inner_content}\n</div>"
118
+ end
119
+ end
120
+ end
121
+ end
@@ -15,5 +15,6 @@ require_relative 'transformers/details_transformer'
15
15
  require_relative 'transformers/dialog_transformer'
16
16
  require_relative 'transformers/icon_transformer'
17
17
  require_relative 'transformers/image_dialog_transformer'
18
+ require_relative 'transformers/layout_transformer'
18
19
  require_relative 'transformers/tabs_transformer'
19
20
  require_relative 'transformers/tag_transformer'
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Markawesome
4
- VERSION = '0.4.0'
4
+ VERSION = '0.5.0'
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: markawesome
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.0
4
+ version: 0.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Janne Waren
@@ -107,6 +107,7 @@ files:
107
107
  - lib/markawesome/transformers/dialog_transformer.rb
108
108
  - lib/markawesome/transformers/icon_transformer.rb
109
109
  - lib/markawesome/transformers/image_dialog_transformer.rb
110
+ - lib/markawesome/transformers/layout_transformer.rb
110
111
  - lib/markawesome/transformers/tabs_transformer.rb
111
112
  - lib/markawesome/transformers/tag_transformer.rb
112
113
  - lib/markawesome/version.rb