primer_view_components 0.0.46 → 0.0.50
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 +4 -4
- data/CHANGELOG.md +144 -0
- data/app/components/primer/base_component.rb +2 -2
- data/app/components/primer/beta/auto_complete.rb +159 -0
- data/app/components/primer/beta/auto_complete/auto_complete.d.ts +1 -0
- data/app/components/primer/{auto_complete → beta/auto_complete}/auto_complete.html.erb +0 -0
- data/app/components/primer/beta/auto_complete/auto_complete.js +1 -0
- data/app/components/primer/{auto_complete → beta/auto_complete}/auto_complete.ts +0 -0
- data/app/components/primer/beta/auto_complete/item.rb +44 -0
- data/app/components/primer/beta/avatar.rb +77 -0
- data/app/components/primer/{avatar_stack_component.html.erb → beta/avatar_stack.html.erb} +0 -0
- data/app/components/primer/beta/avatar_stack.rb +92 -0
- data/app/components/primer/clipboard_copy.html.erb +2 -2
- data/app/components/primer/component.rb +5 -1
- data/app/components/primer/details_component.rb +7 -7
- data/app/components/primer/image_crop.html.erb +4 -4
- data/app/components/primer/label_component.rb +13 -12
- data/app/components/primer/markdown.rb +9 -9
- data/app/components/primer/navigation/tab_component.rb +30 -2
- data/app/components/primer/popover_component.rb +6 -3
- data/app/components/primer/primer.d.ts +1 -1
- data/app/components/primer/primer.js +1 -1
- data/app/components/primer/primer.ts +1 -1
- data/app/components/primer/tab_nav_component.rb +4 -3
- data/app/components/primer/timeline_item_component.rb +2 -2
- data/app/components/primer/truncate.rb +6 -1
- data/app/components/primer/underline_nav_component.rb +4 -3
- data/app/lib/primer/octicon/cache.rb +1 -1
- data/lib/primer/classify.rb +4 -18
- data/lib/primer/classify/cache.rb +0 -5
- data/lib/primer/classify/utilities.rb +54 -22
- data/lib/primer/classify/utilities.yml +16 -0
- data/lib/primer/view_components.rb +34 -6
- data/lib/primer/view_components/constants.rb +55 -0
- data/lib/primer/view_components/linters/argument_mappers/base.rb +74 -0
- data/lib/primer/view_components/linters/argument_mappers/button.rb +32 -44
- data/lib/primer/view_components/linters/argument_mappers/clipboard_copy.rb +20 -0
- data/lib/primer/view_components/linters/argument_mappers/helpers/erb_block.rb +24 -0
- data/lib/primer/view_components/linters/argument_mappers/label.rb +50 -0
- data/lib/primer/view_components/linters/argument_mappers/system_arguments.rb +4 -1
- data/lib/primer/view_components/linters/autocorrectable.rb +30 -0
- data/lib/primer/view_components/linters/button_component_migration_counter.rb +9 -23
- data/lib/primer/view_components/linters/clipboard_copy_component_migration_counter.rb +21 -0
- data/lib/primer/view_components/linters/close_button_component_migration_counter.rb +16 -0
- data/lib/primer/view_components/linters/helpers.rb +56 -38
- data/lib/primer/view_components/linters/label_component_migration_counter.rb +25 -0
- data/lib/primer/view_components/statuses.rb +14 -0
- data/lib/primer/view_components/version.rb +1 -1
- data/lib/rubocop/config/default.yml +12 -0
- data/lib/rubocop/cop/primer.rb +4 -0
- data/lib/rubocop/cop/primer/no_tag_memoize.rb +42 -0
- data/lib/rubocop/cop/primer/system_argument_instead_of_class.rb +75 -0
- data/lib/tasks/constants.rake +12 -0
- data/lib/tasks/docs.rake +87 -32
- data/lib/tasks/utilities.rake +4 -10
- data/lib/yard/docs_helper.rb +12 -3
- data/static/arguments.yml +973 -0
- data/static/assets/view-components.svg +18 -0
- data/static/classes.yml +174 -0
- data/static/constants.json +628 -0
- data/static/statuses.json +5 -5
- metadata +34 -13
- data/app/components/primer/auto_complete.rb +0 -157
- data/app/components/primer/auto_complete/item.rb +0 -42
- data/app/components/primer/avatar_component.rb +0 -75
- data/app/components/primer/avatar_stack_component.rb +0 -90
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 81f226f5fd176e5a1565b2064ba3a85a8af1c11bfd7c3c9503714f3f5cd41dac
|
4
|
+
data.tar.gz: d655dc0cfa7260a09de3f1f662a1317eb2540914407f33cfdbc07b369a6cd5b0
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 07bc38eedefeae46a76d6f7a4b28892a4f01ab0018564c610d8143919c3fed93da3ad91c7970225fdfaac1fd12a294b51e245633f690e87b7392a21d3d3d65f8
|
7
|
+
data.tar.gz: c162cf3fca8accf0a92b9045e9e77bce16d3e646793a3fd479b12efd7e545e0cb9c56cc60884b39965ed7f41baf502d990cee3279170a3b896c845558a3ba714
|
data/CHANGELOG.md
CHANGED
@@ -30,6 +30,150 @@ The category for changes related to documentation, testing and tooling. Also, fo
|
|
30
30
|
|
31
31
|
## main
|
32
32
|
|
33
|
+
## 0.0.50
|
34
|
+
|
35
|
+
### New
|
36
|
+
|
37
|
+
* Add linter suggestions for `CloseButton` component.
|
38
|
+
|
39
|
+
*Manuel Puyol*
|
40
|
+
|
41
|
+
### Breaking changes
|
42
|
+
|
43
|
+
* Update to `octicons` `v15`, removing open-ended dependency. See [https://github.com/primer/octicons/releases/tag/v15.0.0] for icon name changes in release.
|
44
|
+
|
45
|
+
*Joel Hawksley*
|
46
|
+
|
47
|
+
### Updates
|
48
|
+
|
49
|
+
* Don't require `title` for `Label`.
|
50
|
+
|
51
|
+
*Manuel Puyol*
|
52
|
+
|
53
|
+
* Improve autocorrectable linters to convert known SystemArgument classes.
|
54
|
+
|
55
|
+
*Manuel Puyol*
|
56
|
+
|
57
|
+
* Add support for `width: :full` and `height: :full` to System Arguments.
|
58
|
+
|
59
|
+
*Joel Hawksley*
|
60
|
+
|
61
|
+
### Bug fixes
|
62
|
+
|
63
|
+
* Update linters to not autocorrect attributes with ERB blocks.
|
64
|
+
|
65
|
+
*Manuel Puyol*
|
66
|
+
|
67
|
+
* Fix `:height` and `:width` docs to pull from Utilities
|
68
|
+
|
69
|
+
*Jon Rohan*
|
70
|
+
|
71
|
+
## 0.0.49
|
72
|
+
|
73
|
+
### New
|
74
|
+
|
75
|
+
* Add linter suggestions for `Label` component.
|
76
|
+
|
77
|
+
*Manuel Puyol*
|
78
|
+
|
79
|
+
* Add linter suggestions for `ClipboardCopy` component.
|
80
|
+
|
81
|
+
*Manuel Puyol*
|
82
|
+
|
83
|
+
### Updates
|
84
|
+
|
85
|
+
* Update the `Truncate` component to accept `:strong` as a tag.
|
86
|
+
|
87
|
+
*Amélia Chavot*
|
88
|
+
|
89
|
+
* Improve `Primer::Classify::Utilities.classes_to_hash` performance.
|
90
|
+
|
91
|
+
*Manuel Puyol*
|
92
|
+
|
93
|
+
### Breaking changes
|
94
|
+
|
95
|
+
* Require tab with panels to have `panel_id` so `aria-controls` can be set.
|
96
|
+
|
97
|
+
*Kate Higa*
|
98
|
+
|
99
|
+
* Renames:
|
100
|
+
* `Primer::AvatarStackComponent` to `Primer::Beta::AvatarStack`.
|
101
|
+
|
102
|
+
*Manuel Puyol*
|
103
|
+
|
104
|
+
### Misc
|
105
|
+
|
106
|
+
* Extract example tag parsing into helper.
|
107
|
+
|
108
|
+
*Kate Higa*
|
109
|
+
|
110
|
+
* Generate a static constant JSON and use it when defining linters.
|
111
|
+
|
112
|
+
*Manuel Puyol*
|
113
|
+
|
114
|
+
## 0.0.48
|
115
|
+
|
116
|
+
### Breaking changes
|
117
|
+
|
118
|
+
* Ensure panels in `Navigation::Tab` have a label.
|
119
|
+
|
120
|
+
*Kate Higa*
|
121
|
+
|
122
|
+
### Misc
|
123
|
+
|
124
|
+
* Expose custom cops and default config for erblint.
|
125
|
+
|
126
|
+
*Manuel Puyol*
|
127
|
+
|
128
|
+
* Fix double constant assign.
|
129
|
+
|
130
|
+
*Manuel Puyol*
|
131
|
+
|
132
|
+
## 0.0.47
|
133
|
+
|
134
|
+
### Breaking changes
|
135
|
+
|
136
|
+
* Restrict tag for `Popover` to `:div` and `Popover` heading slot to headings.
|
137
|
+
|
138
|
+
*Kate Higa*
|
139
|
+
|
140
|
+
* Renames:
|
141
|
+
* `Primer::AutoComplete` to `Primer::Beta::AutoComplete`
|
142
|
+
* `Primer::AutoComplete::Item` to `Primer::Beta::AutoComplete::Item`
|
143
|
+
* `Primer::AvatarComponent` to `Primer::Beta::Avatar`
|
144
|
+
|
145
|
+
*Manuel Puyol*
|
146
|
+
|
147
|
+
### Misc
|
148
|
+
|
149
|
+
* Update `doc_examples_axe_test` to exclude non-standalone components and fix `Markdown` example.
|
150
|
+
|
151
|
+
*Kate Higa*
|
152
|
+
|
153
|
+
* Update `DetailsComponent` examples.
|
154
|
+
|
155
|
+
*Manuel Puyol*
|
156
|
+
|
157
|
+
* Add linter to suggest system arguments instead of classes.
|
158
|
+
|
159
|
+
*Manuel Puyol*
|
160
|
+
|
161
|
+
* Update component generator to create components in the right status module.
|
162
|
+
|
163
|
+
*Manuel Puyol*
|
164
|
+
|
165
|
+
* Add example for truncating HTML to `Truncate`.
|
166
|
+
|
167
|
+
*Joel Hawksley*
|
168
|
+
|
169
|
+
* Update docs generation to point to the correct file sources.
|
170
|
+
|
171
|
+
*Manuel Puyol*
|
172
|
+
|
173
|
+
* Add ENV flag to dump linter data into a file.
|
174
|
+
|
175
|
+
*Manuel Puyol*
|
176
|
+
|
33
177
|
## 0.0.46
|
34
178
|
|
35
179
|
### Updates
|
@@ -79,7 +79,6 @@ module Primer
|
|
79
79
|
# | `flex_shrink` | Integer | To enable, set to `0`. |
|
80
80
|
# | `flex_wrap` | Symbol | <%= one_of(Primer::Classify::Flex::WRAP_MAPPINGS.keys) %> |
|
81
81
|
# | `justify_content` | Symbol | <%= one_of(Primer::Classify::Flex::JUSTIFY_CONTENT_VALUES) %> |
|
82
|
-
# | `width` | Symbol | <%= one_of([:fit]) %> |
|
83
82
|
#
|
84
83
|
# ## Grid
|
85
84
|
#
|
@@ -94,7 +93,8 @@ module Primer
|
|
94
93
|
# | Name | Type | Description |
|
95
94
|
# | :- | :- | :- |
|
96
95
|
# | `display` | Symbol | <%= one_of(Primer::Classify::Utilities.mappings(:display)) %> |
|
97
|
-
# | `
|
96
|
+
# | `width` | Symbol | <%= one_of(Primer::Classify::Utilities.mappings(:width)) %>. Also supports integer values. |
|
97
|
+
# | `height` | Symbol | <%= one_of(Primer::Classify::Utilities.mappings(:height)) %>. Also supports integer values. |
|
98
98
|
# | `hide` | Symbol | Hide the element at a specific breakpoint. <%= one_of(Primer::Classify::Utilities.mappings(:hide)) %> |
|
99
99
|
# | `visibility` | Symbol | Visibility. <%= one_of(Primer::Classify::Utilities.mappings(:visibility)) %> |
|
100
100
|
# | `vertical_align` | Symbol | <%= one_of(Primer::Classify::Utilities.mappings(:vertical_align)) %> |
|
@@ -0,0 +1,159 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Primer
|
4
|
+
module Beta
|
5
|
+
# Use `AutoComplete` to provide a user with a list of selectable suggestions that appear when they type into the
|
6
|
+
# input field. This list is populated by server search results.
|
7
|
+
# @accessibility
|
8
|
+
# Always set an accessible label to help the user interact with the component.
|
9
|
+
#
|
10
|
+
# * Set the `label` slot to render a visible label. Alternatively, associate an existing visible text element
|
11
|
+
# as a label by setting `aria-labelledby`.
|
12
|
+
# * If you must use a non-visible label, set `:"aria-label"` on `AutoComplete` and Primer
|
13
|
+
# will apply it to the correct elements. However, please note that a visible label should almost
|
14
|
+
# always be used unless there is compelling reason not to. A placeholder is not a label.
|
15
|
+
class AutoComplete < Primer::Component
|
16
|
+
status :beta
|
17
|
+
|
18
|
+
# Optionally render a visible label. See <%= link_to_accessibility %>
|
19
|
+
#
|
20
|
+
# @param system_arguments [Hash] <%= link_to_system_arguments_docs %>
|
21
|
+
renders_one :label, lambda { |**system_arguments|
|
22
|
+
system_arguments[:for] = @input_id
|
23
|
+
system_arguments[:tag] = :label
|
24
|
+
Primer::BaseComponent.new(**system_arguments)
|
25
|
+
}
|
26
|
+
|
27
|
+
# Required input used to search for results
|
28
|
+
#
|
29
|
+
# @param type [Symbol] <%= one_of(Primer::Beta::AutoComplete::Input::TYPE_OPTIONS) %>
|
30
|
+
# @param system_arguments [Hash] <%= link_to_system_arguments_docs %>
|
31
|
+
renders_one :input, lambda { |**system_arguments|
|
32
|
+
aria_label = aria("label", system_arguments) || @aria_label
|
33
|
+
if aria_label.present?
|
34
|
+
system_arguments[:"aria-label"] = aria_label
|
35
|
+
system_arguments[:aria]&.delete(:label)
|
36
|
+
end
|
37
|
+
|
38
|
+
name = system_arguments[:name] || @input_id
|
39
|
+
Input.new(id: @input_id, name: name, **system_arguments)
|
40
|
+
}
|
41
|
+
|
42
|
+
# Optional icon to be rendered before the input. Has the same arguments as <%= link_to_component(Primer::OcticonComponent) %>.
|
43
|
+
#
|
44
|
+
renders_one :icon, Primer::OcticonComponent
|
45
|
+
|
46
|
+
# Customizable results list.
|
47
|
+
#
|
48
|
+
# @param system_arguments [Hash] <%= link_to_system_arguments_docs %>
|
49
|
+
renders_one :results, lambda { |**system_arguments|
|
50
|
+
system_arguments[:tag] = :ul
|
51
|
+
system_arguments[:id] = @list_id
|
52
|
+
system_arguments[:classes] = class_names(
|
53
|
+
"autocomplete-results",
|
54
|
+
system_arguments[:classes]
|
55
|
+
)
|
56
|
+
|
57
|
+
aria_label = system_arguments[:"aria-label"] || system_arguments.dig(:aria, :label) || @aria_label
|
58
|
+
system_arguments[:"aria-label"] = aria_label if aria_label.present?
|
59
|
+
system_arguments[:aria]&.delete(:label)
|
60
|
+
|
61
|
+
Primer::BaseComponent.new(**system_arguments)
|
62
|
+
}
|
63
|
+
|
64
|
+
# @example Default
|
65
|
+
# <%= render(Primer::Beta::AutoComplete.new(src: "/auto_complete", input_id: "fruits-input-1", list_id: "fruits-popup-1", position: :relative)) do |c| %>
|
66
|
+
# <% c.label(classes:"").with_content("Fruits") %>
|
67
|
+
# <% c.input(type: :text) %>
|
68
|
+
# <% end %>
|
69
|
+
#
|
70
|
+
# @example With `aria-label`
|
71
|
+
# <%= render(Primer::Beta::AutoComplete.new("aria-label": "Fruits", src: "/auto_complete", input_id: "fruits-input-2", list_id: "fruits-popup-2", position: :relative)) do |c| %>
|
72
|
+
# <% c.input(type: :text) %>
|
73
|
+
# <% end %>
|
74
|
+
#
|
75
|
+
# @example With `aria-labelledby`
|
76
|
+
# <%= render(Primer::HeadingComponent.new(tag: :h2, id: "search-1")) { "Search" } %>
|
77
|
+
# <%= render(Primer::Beta::AutoComplete.new(src: "/auto_complete", input_id: "fruits-input-3", list_id: "fruits-popup-2", position: :relative)) do |c| %>
|
78
|
+
# <% c.input("aria-labelledby": "search-1") %>
|
79
|
+
# <% end %>
|
80
|
+
#
|
81
|
+
# @example With custom classes for the results
|
82
|
+
# <%= render(Primer::Beta::AutoComplete.new(src: "/auto_complete", input_id: "fruits-input-4", list_id: "fruits-popup-3", position: :relative)) do |c| %>
|
83
|
+
# <% c.label(classes:"").with_content("Fruits") %>
|
84
|
+
# <% c.input(type: :text) %>
|
85
|
+
# <% c.results(classes: "custom-class") do %>
|
86
|
+
# <%= render(Primer::Beta::AutoComplete::Item.new(selected: true, value: "apple")) do |c| %>
|
87
|
+
# Apple
|
88
|
+
# <% end %>
|
89
|
+
# <%= render(Primer::Beta::AutoComplete::Item.new(value: "orange")) do |c| %>
|
90
|
+
# Orange
|
91
|
+
# <% end %>
|
92
|
+
# <% end %>
|
93
|
+
# <% end %>
|
94
|
+
#
|
95
|
+
# @example With Icon
|
96
|
+
# <%= render(Primer::Beta::AutoComplete.new(src: "/auto_complete", list_id: "fruits-popup-4", input_id: "fruits-input-4", position: :relative)) do |c| %>
|
97
|
+
# <% c.label(classes:"").with_content("Fruits") %>
|
98
|
+
# <% c.input(type: :text) %>
|
99
|
+
# <% c.icon(icon: :search) %>
|
100
|
+
# <% end %>
|
101
|
+
#
|
102
|
+
# @param src [String] The route to query.
|
103
|
+
# @param input_id [String] Id of the input element.
|
104
|
+
# @param list_id [String] Id of the list element.
|
105
|
+
# @param system_arguments [Hash] <%= link_to_system_arguments_docs %>
|
106
|
+
def initialize(src:, list_id:, input_id:, **system_arguments)
|
107
|
+
@list_id = list_id
|
108
|
+
@input_id = input_id
|
109
|
+
@aria_label = aria("label", system_arguments)
|
110
|
+
|
111
|
+
system_arguments.delete(:"aria-label") && system_arguments[:aria]&.delete(:label)
|
112
|
+
|
113
|
+
@system_arguments = system_arguments
|
114
|
+
@system_arguments[:tag] = "auto-complete"
|
115
|
+
@system_arguments[:src] = src
|
116
|
+
@system_arguments[:for] = list_id
|
117
|
+
end
|
118
|
+
|
119
|
+
# add `results` without needing to explicitly call it in the view
|
120
|
+
def before_render
|
121
|
+
raise ArgumentError, "Missing `input` slot" if input.blank?
|
122
|
+
raise ArgumentError, "Accessible label is required." if label.blank? && input.missing_label?
|
123
|
+
|
124
|
+
results(classes: "") unless results
|
125
|
+
end
|
126
|
+
|
127
|
+
# This component is part of `Primer::Beta::AutoCompleteComponent` and should not be
|
128
|
+
# used as a standalone component.
|
129
|
+
class Input < Primer::Component
|
130
|
+
DEFAULT_TYPE = :text
|
131
|
+
TYPE_OPTIONS = [DEFAULT_TYPE, :search].freeze
|
132
|
+
|
133
|
+
# @param type [Symbol] <%= one_of(Primer::Beta::AutoComplete::Input::TYPE_OPTIONS) %>
|
134
|
+
# @param system_arguments [Hash] <%= link_to_system_arguments_docs %>
|
135
|
+
def initialize(type: DEFAULT_TYPE, **system_arguments)
|
136
|
+
@system_arguments = system_arguments
|
137
|
+
@system_arguments[:tag] = :input
|
138
|
+
|
139
|
+
@aria_label = system_arguments[:"aria-label"]
|
140
|
+
@aria_labelledby = system_arguments[:"aria-labelledby"] || system_arguments.dig(:aria, :labelledby)
|
141
|
+
|
142
|
+
@system_arguments[:type] = fetch_or_fallback(TYPE_OPTIONS, type, DEFAULT_TYPE)
|
143
|
+
@system_arguments[:classes] = class_names(
|
144
|
+
"form-control",
|
145
|
+
system_arguments[:classes]
|
146
|
+
)
|
147
|
+
end
|
148
|
+
|
149
|
+
def missing_label?
|
150
|
+
@aria_label.blank? && @aria_labelledby.blank?
|
151
|
+
end
|
152
|
+
|
153
|
+
def call
|
154
|
+
render(Primer::BaseComponent.new(**@system_arguments))
|
155
|
+
end
|
156
|
+
end
|
157
|
+
end
|
158
|
+
end
|
159
|
+
end
|
@@ -0,0 +1 @@
|
|
1
|
+
import '@github/auto-complete-element';
|
File without changes
|
@@ -0,0 +1 @@
|
|
1
|
+
import '@github/auto-complete-element';
|
File without changes
|
@@ -0,0 +1,44 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Primer
|
4
|
+
module Beta
|
5
|
+
class AutoComplete
|
6
|
+
# Use `AutoCompleteItem` to list results of an auto-completed search.
|
7
|
+
class Item < Primer::Component
|
8
|
+
status :beta
|
9
|
+
|
10
|
+
# @example Default
|
11
|
+
# <%= render(Primer::Beta::AutoComplete::Item.new(selected: true, value: "value")) do |c| %>
|
12
|
+
# Selected
|
13
|
+
# <% end %>
|
14
|
+
# <%= render(Primer::Beta::AutoComplete::Item.new(value: "value")) do |c| %>
|
15
|
+
# Not selected
|
16
|
+
# <% end %>
|
17
|
+
#
|
18
|
+
# @param value [String] Value of the item.
|
19
|
+
# @param selected [Boolean] Whether the item is selected.
|
20
|
+
# @param disabled [Boolean] Whether the item is disabled.
|
21
|
+
# @param system_arguments [Hash] <%= link_to_system_arguments_docs %>
|
22
|
+
def initialize(value:, selected: false, disabled: false, **system_arguments)
|
23
|
+
@system_arguments = system_arguments
|
24
|
+
@system_arguments[:tag] = :li
|
25
|
+
@system_arguments[:role] = :option
|
26
|
+
@system_arguments[:"data-autocomplete-value"] = value
|
27
|
+
|
28
|
+
@system_arguments[:"aria-selected"] = true if selected
|
29
|
+
@system_arguments[:"aria-disabled"] = true if disabled
|
30
|
+
|
31
|
+
@system_arguments[:classes] = class_names(
|
32
|
+
"autocomplete-item",
|
33
|
+
system_arguments[:classes],
|
34
|
+
"disabled" => disabled
|
35
|
+
)
|
36
|
+
end
|
37
|
+
|
38
|
+
def call
|
39
|
+
render(Primer::BaseComponent.new(**@system_arguments)) { content }
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,77 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Primer
|
4
|
+
module Beta
|
5
|
+
# `Avatar` can be used to represent users and organizations on GitHub.
|
6
|
+
#
|
7
|
+
# - Use the default round avatar for users, and the `square` argument
|
8
|
+
# for organizations or any other non-human avatars.
|
9
|
+
# - By default, `Avatar` will render a static `<img>`. To have `Avatar` function as a link, set the `href` which will wrap the `<img>` in a `<a>`.
|
10
|
+
# - Set `size` to update the height and width of the `Avatar` in pixels.
|
11
|
+
# - To stack multiple avatars together, use <%= link_to_component(Primer::Beta::AvatarStack) %>.
|
12
|
+
#
|
13
|
+
# @accessibility
|
14
|
+
# Images should have text alternatives that describe the information or function represented.
|
15
|
+
# If the avatar functions as a link, provide alt text that helps convey the function. For instance,
|
16
|
+
# if `Avatar` is a link to a user profile, the alt attribute should be `@kittenuser profile`
|
17
|
+
# rather than `@kittenuser`.
|
18
|
+
# [Learn more about best image practices (WAI Images)](https://www.w3.org/WAI/tutorials/images/)
|
19
|
+
class Avatar < Primer::Component
|
20
|
+
status :beta
|
21
|
+
|
22
|
+
SMALL_THRESHOLD = 24
|
23
|
+
|
24
|
+
# @example Default
|
25
|
+
# <%= render(Primer::Beta::Avatar.new(src: "http://placekitten.com/200/200", alt: "@kittenuser")) %>
|
26
|
+
#
|
27
|
+
# @example Square
|
28
|
+
# <%= render(Primer::Beta::Avatar.new(src: "http://placekitten.com/200/200", alt: "@kittenuser", square: true)) %>
|
29
|
+
#
|
30
|
+
# @example Link
|
31
|
+
# <%= render(Primer::Beta::Avatar.new(href: "#", src: "http://placekitten.com/200/200", alt: "@kittenuser profile")) %>
|
32
|
+
#
|
33
|
+
# @example With size
|
34
|
+
# <%= render(Primer::Beta::Avatar.new(src: "http://placekitten.com/200/200", alt: "@kittenuser", size: 16)) %>
|
35
|
+
# <%= render(Primer::Beta::Avatar.new(src: "http://placekitten.com/200/200", alt: "@kittenuser", size: 20)) %>
|
36
|
+
# <%= render(Primer::Beta::Avatar.new(src: "http://placekitten.com/200/200", alt: "@kittenuser", size: 24)) %>
|
37
|
+
# <%= render(Primer::Beta::Avatar.new(src: "http://placekitten.com/200/200", alt: "@kittenuser", size: 28)) %>
|
38
|
+
# <%= render(Primer::Beta::Avatar.new(src: "http://placekitten.com/200/200", alt: "@kittenuser", size: 32)) %>
|
39
|
+
# <%= render(Primer::Beta::Avatar.new(src: "http://placekitten.com/200/200", alt: "@kittenuser", size: 36)) %>
|
40
|
+
#
|
41
|
+
# @param src [String] The source url of the avatar image.
|
42
|
+
# @param alt [String] Passed through to alt on img tag.
|
43
|
+
# @param size [Integer] Adds the avatar-small class if less than 24.
|
44
|
+
# @param square [Boolean] Used to create a square avatar.
|
45
|
+
# @param href [String] The URL to link to. If used, component will be wrapped by an `<a>` tag.
|
46
|
+
# @param system_arguments [Hash] <%= link_to_system_arguments_docs %>
|
47
|
+
def initialize(src:, alt:, size: 20, square: false, href: nil, **system_arguments)
|
48
|
+
@href = href
|
49
|
+
@system_arguments = system_arguments
|
50
|
+
@system_arguments[:tag] = :img
|
51
|
+
@system_arguments[:src] = src
|
52
|
+
@system_arguments[:alt] = alt
|
53
|
+
@system_arguments[:size] = size
|
54
|
+
@system_arguments[:height] = size
|
55
|
+
@system_arguments[:width] = size
|
56
|
+
|
57
|
+
@system_arguments[:classes] = class_names(
|
58
|
+
system_arguments[:classes],
|
59
|
+
"avatar",
|
60
|
+
"avatar-small" => size < SMALL_THRESHOLD,
|
61
|
+
"circle" => !square,
|
62
|
+
"lh-0" => href # Addresses an overflow issue with linked avatars
|
63
|
+
)
|
64
|
+
end
|
65
|
+
|
66
|
+
def call
|
67
|
+
if @href
|
68
|
+
render(Primer::LinkComponent.new(href: @href, classes: @system_arguments[:classes])) do
|
69
|
+
render(Primer::BaseComponent.new(**@system_arguments.except(:classes))) { content }
|
70
|
+
end
|
71
|
+
else
|
72
|
+
render(Primer::BaseComponent.new(**@system_arguments)) { content }
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|