1

I would like to dynamically generate a string of classes based on the @Inputs to my Component.

I want these classes to be applied to the element that was selected by the Component, not any child elements of the Component.

Let's say I have a simple Component:

@Component({
    selector:       'responsive-table-column',
    templateUrl:    `<div #responsiveTableCell >
                        <ng-content></ng-content>
                    </div>`
})
export class ResponsiveTableColumn {
    private A:string = "";
    private B:string = "";
    @Input()
    get a(){
        return this.A;
    }
    set a(val:any){
        this.A = val;
    }
    @Input()
    get b(){
        return this.B;
    }
    set b(val:any){
        this.B = val;
    }
    getClassName(){
        //Do something to create class names
        return "classes";
    }
}

I would like to apply the generated class names to my <responsive-table-column> element that has been selected by my component.

How can I access this element? Replace isn't supported, otherwise I would place it on #responsiveTableCell.

Essentially, this is what I would like to see:

<responsive-table-column class="{{getClassName()}}" >
    <div #responsiveTableCell >
        <ng-content></ng-content>
    </div>
</responsive-table-column>

1 Answer 1

1

I think the best way is to use ElementRef.nativeElement.classList to enable/disable various classes:

constructor(private elRef:ElementRef) {}

ngOnChanges() {
  this.elRef.nativeElement.classList.add(this.a); 
}
Sign up to request clarification or add additional context in comments.

4 Comments

I was hoping I wouldn't have to do that (use .nativeElement), but I was thinking the same. Thanks!
You can use Renderer2 instead if using nativeElement directly bothers you. angular.io/docs/ts/latest/api/core/index/…. You can also use @HostBinding('class') classes:String; and create a string that contains the classes and assign it to classes but that doesn't work well together with statically added classes like <my-comp class="c1 c2 c3"> AFAIR.
With Renderer2 being experimental, I'm not sure how supported it will be in future releases. I have not heard anything about @HostBinding() though! That sounds promising! I'm looking at your answer here about @HostBinding. This sounds like the right route. Is there any reason I shouldn't use @HostBinding?
@HostBinding is pergectly fine of course, just usimg it with plain 'class' is a bit problematic, because if there are other ways used to set classes at the same time this doesn't work well together (other classes will be removed) @HostBinding('class.foo') is usually the right way but requires you to know the class names in advance. You can also use Renderer until Renderer2 becomes stable.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.