-
-
Notifications
You must be signed in to change notification settings - Fork 356
[Twig] Add (alternate) attribute rendering system #1442
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
{# This is doing the same thing too, right ? #}
data-foo="{{ attributes.get('data-foo') ?? 'replaced-default' }}" {# Could we do this ? #}
data-foo="{{ attributes.get('data-foo', 'replaced-default') }}" {# Or even better... ? #}
data-foo="{{ attributes.dataFoo ?? 'replaced-default' }}" |
@@ -31,7 +34,10 @@ public function __construct(private array $attributes) | |||
public function __toString(): string | |||
{ | |||
return array_reduce( | |||
array_keys($this->attributes), | |||
array_filter( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
array_filter + \ ARRAY_FILTER_USE_KEY ?
{ | ||
$value = $this->attributes[$attribute] ?? ''; | ||
|
||
if (!\is_string($value)) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
- Stringable ?
Those are interesting suggestions @smnandre ... |
What about killing <div
class="{{ attributes.class }} appended-default"
style="prepended-default {{ attributes.style }}"
data-foo="{{ attributes.get('data-foo')|default('replaced-default') }}"
{{ attributes }}
> BTW, the only real reason I added that class was to make using a filter (like <div
class="{{ attributes.class.append('appended-default')|tailwind_merge }}"
{{ attributes }}
>
{# vs #}
<div
class="{{ (attributes.class ~ ' appended-default')|tailwind_merge }} appended-default"
{{ attributes }}
> I should note that if we choose not to include this class, adding it in the future would be a bc break I think. |
I like the fact this class exists, and i like the idea of "consuming" some attributes. I think we can improve the DX a bit more with utilities And the fact this could be forwared to a filter is a really valid point, pushing more the need to a short simple call chain. Lastely, i would really hate we suggest people to use any " ~ " :) But i would like to avoid this syntax, as it can be hard to dynamise (values and modes can depend on other things)
-- When we say "default preprended" in fact the "default" notion has no meaning, right ? It's something prepended in every case. Same for append. Then again, i see not a lot of real life usage for "append" (there probably are, but prefxing CSS or data value feels a lot more common need than adding something) That gives us two main calls to consider: default value, and prepend one. I still think default value can follow standard twig usages, but i'm eager to add a getter with default too. <div class="{{ attributes.class|default('alert') }}" >
<div class="{{ attributes.class ?? 'alert' }}" >
<div class="{{ attributes.get('class', 'alert') }}" > There we have only one problem, by doing so we forbid any usage of 'get' as attribute. Not a big problem, but something to keep in mind We can add a second method, like prepend() or prependValue or getPrepend('class', 'alert') ... But then, why not use the 'get' method ? If we agree the prepend is the default behaviour, why not .... {# Prepend #}
<div class="{{ attributes.get('class', 'alert', true) }}" >
<div class="{{ attributes.get('class', 'alert', 'prepend') }}" >
{# Append #}
<div class="{{ attributes.get('class', 'alert', false) }}" >
<div class="{{ attributes.get('class', 'alert', 'append') }}" > Lastly, if we want something even shorter / sweeter So my suggestion is : {# jQuery mood (not sure i like that ^^, but really front-end-like #}
<div class="{{ attributes.class('alert', true) }}" > |
Taking all of this into account, how about this: A) I think we more or less agree on this syntax. I did tweak how the last looks - I don't think this is a code change, but using <div
class="{{ attributes.class }} appended-default"
style="prepended-default {{ attributes.style }}"
data-foo="{{ attributes.get('data-foo') ?? 'replaced-default' }}"
{{ attributes }}
> The B) Then, for the question of prepending vs replacing vs default values. I like Simon's idea of something like Given this @kbond - are there any tweaks this PR needs to match before review? |
This actually won't be possible, |
Ah, ok. I see it now. This feels like a reason to NOT have <div
class="{{ attributes.prepend('class', 'prepended-stuff') }}"
or="this-idea"
class="{{ attributes.get('class', 'prepended-stuff', true) }}"
> |
I think so. What about, for this PR, we keep it simple and just have |
That sounds reasonable - then we can add args to |
b73e1b9
to
0d027d5
Compare
Thanks Kevin! |
This is an alternate to #1404 as suggested by Ryan here.
This PR allows the following:
When calling
attributes.render('name')
(or magically via, the attribute is marked as rendered. Later when calling justattributes.name
){{ attributes }}
, the attributes marked as already rendered are excluded. Whether or not an attribute is considered rendered is only evaluated when convertingComponentAttributes
to a string.TODO: