问题
I want to pass in multiple params to a structural directive, but what was working in Angular2 doesn't seem to work in Angular5 anymore
Here's my blah
component which contains an accordion:
@Component(
selector: "blah-scene",
// language=HTML
template: """
<div>
Blah Test Page
<accordion>
<div *accordionItem>
item1
</div>
<div *accordionItem>
item2
</div>
</accordion>
</div>
""",
directives: const [
Accordion,
AccordionItemDirective
]
)
class BlahScene implements AfterContentInit, OnDestroy {
...
}
Accordion is defined as follow:
@Component(
selector: 'accordion',
// language=HTML
template: """
<ul class="accordion"
[id]="id"
[attr.data-slide-speed]="slideSpeed"
[attr.data-multi-expand]="multiExpand"
[attr.data-allow-all-closed]="allowAllClosed">
<ng-content></ng-content>
</ul>
""",
styles: const ["""
.overflow-hidden {
overflow: hidden;
}
"""
],
)
class Accordion implements AfterContentInit, OnDestroy, OnChanges {
@ContentChildren(AccordionItemDirective)
List<AccordionItemDirective> items;
...
}
I'm expecting those two divs marked with *accordionItem
to be rendered as accordion items which it does.
AccordionItem:
@Component(
selector: "li",
template: """
<a
*ngIf="visible"
class="accordion-title"
[attr.did]="title"
(click)='onClickTitle(title)'>
{{title?.toUpperCase()}}
<img
src="{{expandButtonPath()}}"
class="expand-navbar"
[class.disabled]='!allowClose && active'>
</a>
<div
class="accordion-content no-padding"
[class.hidden]='!active'
[class.overflow-hidden]="hideScrollBars"
[class.overflow-auto]="!hideScrollBars"
data-tab-content>
<template
[ngIf]="renderAccordionItemContent && visible"
[ngTemplateOutlet]="template">
</template>
</div>
""",
styles: const ["""
...
"""],
directives: const [
NgTemplateOutlet,
coreDirectives
]
)
class AccordionItem implements AfterContentInit, OnDestroy {
TemplateRef template;
...
}
And then the AccordionItemDirective
which creates the AccordionItem and adds it to the DOM:
@Directive(selector: '[accordionItem]')
class AccordionItemDirective implements AfterContentInit {
final ViewContainerRef vcRef;
final TemplateRef template;
AccordionItemDirective(this.vcRef, this.template);
AccordionItem accordionItem;
ComponentRef componentRef;
String accordionId;
@override
ngAfterContentInit() async {
template.createEmbeddedView();
final ComponentRef<AccordionItem> component =
vcRef.createComponent(accordionItemTemplate.AccordionItemNgFactory);
accordionItem = component.instance;
accordionItem
..template = template
..active = _accordionItemActive
..title = accordionItemTitle
..accordionId = accordionId;
}
...
Up to here, it works fine, the AccordionItems are created and inserted as li
inside the accordion
I now want to pass in params so that i can set the title and id and some other properties of that accordionItem On the accordionItemDirective, i add some inputs:
@Input("accordionItemId") String accordionItemId = "";
bool _accordionItemActive = false;
@Input("accordionItemTitle")
String accordionItemTitle = "Missing Title";
Expecting this to work:
<accordion>
<div *accordionItem [accordionItemTitle]="'Title1'">
item1
</div>
<div *accordionItem>
item2
</div>
</accordion>
i get this error:
lib/component/test/blah-scene.dart: ParseErrorLevel.FATAL: Can't bind to 'accordionItemTitle' since it isn't a known native property or known directive. Please fix typo or add to directives list.
Trying it without the square brackets:
<accordion>
<div *accordionItem accordionItemTitle="'Title1'">
item1
</div>
<div *accordionItem>
item2
</div>
</accordion>
it compiles, but nothing happens.
I try to intercept the input, but my log.fines aren't being printed at all
@Input("accordionItemTitle")
set accordionItemTitle(String title) {
log.fine(title);
}
String get accordionItemTitle {
return "Missing Title [...]";
}
In Angular2, this used to work:
<accordion>
<div *accordionItem="accordionItemTitle: 'Title1' ">
item1
</div>
<div *accordionItem>
item2
</div>
</accordion>
but that too is complaining:
ParseErrorLevel.FATAL: Can't bind to 'accordionItemAccordionItemTitle' since it isn't an input of any bound directive. Please check that the spelling is correct, and that the intended directive is included in the host component's list of directives
What is the correct way to pass in parameters to a structural directive ?
回答1:
Looks like this works for all inputs other than accordionItemId
:
<accordion>
<div *accordionItem="title: 'Title1'; active: true ">
item1
</div>
<div *accordionItem="title: 'Title2'; active: true ">
item2
</div>
</accordion>
来源:https://stackoverflow.com/questions/56791433/passing-multiple-parameters-to-a-structural-directive-in-angulardart-5