-
Notifications
You must be signed in to change notification settings - Fork 25.3k
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
feat(content projection): component inputs accepting arrow functions returning ng-templates #56056
Comments
Just a stackblitz to summarise the current possibilities https://stackblitz.com/edit/stackblitz-starters-uoy6sf Note: you might say that the example could be changed by introducing structural directives. This way consumer.tree would look better. But as I see it, it's just a way to rebrande complexity and write more code: tree.component will be packed with directives and consumer.tree will use more advance concepts. IMHO making a closer in tree.component over consumer.tree arrow func inputs is the most natural / easy / elegant way to solve the problem. My 2 cents! |
Umh... I wonder if the "content projection and content queries unification" (see #37319) could be partially rephrased using this proposal: use inputs to pass content to project (in the form of It seems to work for some common problems:
Maybe I'm missing something very important / obvious (ng-content is more performant, CD would be a mess, ...). But the new (typed) signal inputs are pretty powerful / flexible. And reducing complex projection scenarios to "variables to pass as inputs", seems to simplify problems. Anyway, the syntax should be beautified (it's a bit ugly with Ok... just a comment (hopefully useful) for the future! 😅 |
Hey! Thnx for the suggestion - we absolutely feel the pain of working with the current content projection and dynamic template instantiation - especially for more complex cases. We do think of a project proposal / roadmap entry that would significantly improve the situation. I'm going to close this issue as it prescribes a particular solution to one of the use-cases. But we are aware of other pain points so we should look at those more holistically. Also, should not constraint the solution space before we understand all the use-cases that need attention. We do appreciate your input, though - this is one more indicator that we need to dig deeper into those areas. |
Sure np! Perfectly aware that it was a partial solution. Just last personal suggestion considering I often work with "react" guys: do not underestimate the power of changing ng content projection in a way that results familiar for the react community (on top of making it better for the ng one 😃). IMO it can increase the rate of react devs giving angular another successful try... and of course make the creation of "component libs" easier. I'm perfectly aware you're busy with several big tracks... and the ng community is often focus on SFC / classes / decorators while comparing frameworks (myself included 😅). But I think this might be a less mainstream point with a potentially high ROI for angular adoption! Just my 2 cents! And as usual, thanks a lot for your work! |
This issue has been automatically locked due to inactivity. Read more about our automatic conversation locking policy. This action has been performed automatically by a bot. |
Which @angular/* package(s) are relevant/related to the feature request?
compiler, core
Introduction
With the recent
@let
template variables proposal, there is IMO some sort of clashing at the level of names / concepts / notations between@let
template variables and#
template variables.Some similarities are:
On the other hand, they (I guess) react differently to CD and have different scope rules:
#
variables are references to html elements. As such, they play well with (conditional) content-projection:Speaking about content projection (or composition), I have to admit that I've always found angular options not particularly straightforward. In general, mastering content projection in angular requires decent knowledge of:
#
template variables,Proposal
Assuming that
#
template variables cannot be fitted in the@let
one,I'd like to propose the following changes:
#
annotation with@ref
:@ref="varName"
,@ref(ngModel) = "varName"
,@ref
template variables like this@ref temp = {<ng-template>...</ng-template>}
,@ref temp = (...) => {<ng-template>...</ng-template>}
,@ref
template variables defined in 2.Examples
Some refactored examples from the current Understanding template variables and new possibilities for content projection.
DOM element
Component or template
Form
Content projection
Projection variants
Objections
Some reasonable objections:
Why don't leaving
#
variables as they are and simply allow@let temp = (...) => {<ng-template>...</ng-template>}
?Answer: yeah, that would be ideal! The point is: I'm not sure it's possible considering the slightly different mental models and how the compile works. Unfortunately, I have a limited understanding of both concepts... therefore, I went for the
@ref
way (just a#
remapping at compilation time). But of course, defining a@ref
variable after its usage, it's really strange. Moreover it will increase confusion between@let
and@ref
variables.How about viewChild, contentChild, ... ?
Answer: well, for templates like
@ref temp = {<ng-template>...</ng-template>}
I guess it can work as right now (just a different way of definiting an ng-template). Not sure about arrow functions... probably discarded. Problem solved if 1) is applicable. In general, I think templates passed as inputs are more flexible than the current content_projection / content_queries mechanisms .Your new
@ref
definition is not real tsAnswer: that's true... as it's not real ts the following
@let user = user$ | async ?? 'unknonw'
. The idea behind@ref temp = (...) => {<ng-template>...</ng-template>}
is to be familiar, not valid ts. Anyway: the proposal can be adapted if 43485 is strictly required.Why doing things in a different way? You already have all the tools to achieve content projection needs
Answer: true! But on the other hand, I think simple / familiar things are always better. Mastering the current angular content projection (derived from html standards) is not easy... especially if you're coming from other frameworks.
In practice, it's just a parent-child interaction where the parent wants a hook to return a customised template to be used in the child, based on a child-defined object interface (even extendable by the parent). A closure feels very natural and boost components reusability.
Maybe more complicated, but the current angular content projection (see material) is more readable because it's more semanatic and close to html standards
Answer: that's true! Say: I hope there's a way to inline
@ref temp = (...) => {<ng-template>...</ng-template>}
in component inputs. Assuming it's the case, it's mostly a matter of decluttering the examples above (remove<ng-template>
) and the semantic beauty comes back. With just a different taste! I also hope the upcoming DX for components can help fixing this problem. But for now, I guess no solution.Conclusion
The main goal of this issue is to propose an expansion of the current content projection capabilities. But due to the ongoing development of
@let
and my limited understanding of the angular compiler, I might have proposed something very difficult to achieve (or a bit stupid 😅). In case, sorry for this!And yes, the intention is to push angular content projection into react / solid land... which IMO is cool cause it's one of the things these 2 frameworks are shining on (of course easy to achieve when components are just functions 😅).
PS: thanks a lot for the amazing work you're doing!
The text was updated successfully, but these errors were encountered: