24

I am trying to use an enum value to set the selected value of an HTML attribute:

export enum MyEnum {
    FirstValue,
    SecondValue
}
export function MyEnumAware(constructor: Function) {
    constructor.prototype.MyEnum = MyEnum;
}

@MyEnumAware
@Component({
    templateUrl: "./lot-edit.component.html",
    styleUrls: ["./lot-edit.component.css"],
})
export class LotEditComponent implements OnInit {
    @Input() myEnumValue: MyEnum ;

}

<td><input name="status" type="radio" [value]="MyEnum.FirstValue" [(ngModel)]="myEnumValue"></td>
<td><input name="status" type="radio" [value]="MyEnum.SecondValue" [(ngModel)]="myEnumValue"></td>

however I get "Cannot read property 'FirstValue' of undefined"

Is there a way to use an enum value as the value of html attributes?

3

3 Answers 3

57

Your template can only access member variables of its component class. So, if you want to use the enum's values, assign it (the Enum) to a member variable.

In your component,

export class MyComp {
  MyEnum = MyEnum;
  .....
}   

Then you're free to access the elements of the enum in your template.

6
  • 3
    Is that a right practise to do? I would not say so. Commented Feb 26, 2017 at 6:28
  • I use a variation of this technique regularly where I have an object whose properties are strings that I treat as constants, and I would attach that object to various components as needed. The most common example is defining project specific names for the material design icons that I want to use in that object literal and then using that object literal wherever I need it
    – snorkpete
    Commented Feb 26, 2017 at 11:53
  • 1
    Well, should a component contain a property containing an enum? Is that right from design? I do not feel so even though I know it is the only way to be able to use enum in templates. The other approach would be methods designed to work with the enum in the component (accessible from the template) and that is the approach I see as correct. Commented Feb 26, 2017 at 20:10
  • 4
    I hear your point about a component not including an enum as a property, especially since the enum doesn't technically belong to the component class from a design perspective. But my view on this specific matter is that for the most part, the role of the component class is to expose data and functionality to the template for its use. Yes, you can wrap the enum in a method to isolate it more but I'm not sure the extra ceremony buys you anything except more boilerplate code. An enum is just a list of constants after all... What's the risk of change?
    – snorkpete
    Commented Feb 26, 2017 at 20:55
  • 10
    you can do MyEnum: typeof MyEnum = MyEnum; to keep it type safe.
    – Mario Eis
    Commented Aug 30, 2017 at 14:21
3

You can use a enum to assign to html element as below

@Component({
  selector: 'my-app',
  template: `
    <div>
      <h2>Hello {{name}}</h2>
      <input type="text" [(ngModel)]="value"/>
    </div>
  `,
})
export class App {
  name:string;
  myValue:any= MyEnum;
  value:string;
  constructor() {
    this.name = 'Angular2';
    this.value=this.myValue[1];
    console.log(this.value);
  }
}

Since you are using [(ngModel)] on input element, you cannot assign to [value] property of input element.

LIVE DEMO

0
-2

With Angular 2 //enum

export enum IType
{
Vegitable=0,
Fruits=1,
Fish=2
}

// angular 2 Component in type script

import {IType} from '/itype';
export class DataComponent
{
getType(id:number):any
{
      return IType[id];
}
}

// in your html file

<div>
{{getType(1)}}
</div>
4
  • 2
    I am not sure this answer the question. You are not using an enum in the html, you are using a function to get the enum value. IMHO it defeats the use of enums as now I have a magic number in the html template I have absolutely no idea where it comes from. Commented Dec 3, 2017 at 19:31
  • I was going to correct your spelling on "Vegitable" (sic), but see you had reverted a previous edit fixing the spelling. The correct spelling would be "Vegetable" - merriam-webster.com/dictionary/vegetable
    – Alan Ball
    Commented Aug 22, 2019 at 11:49
  • @AlbertoL.Bonfiglio The html here seems to be fine. Would you perhaps suggest he puts "{{getType(enum_value)}}"? Personally, I wouldn't write a function to do this, as in this case, the function is specific to the type <MyEnum>. It would be acceptable if it took in a type and dynamically inferred enum type. In the html, I would simply go {{MyEnum[enum_value]}} - keep it simple.
    – Alan Ball
    Commented Aug 22, 2019 at 11:59
  • @AlanBall. IMHO one of the advantages of enums is readability. var myveggie = Vegetables.Celery is more readable than var myveggie = GetType(1) . Additionally, you could add Basil between Arugola and Celery to preserve sort order for example, and the code wouldn't change. The code Muhamed wrote works, it's just not readable and if the value of the enum changes there is a bug. If I am using enums then I would use the angular team suggestion of placing a variable of type enum in the class so that you can reference it from the html model. Just like snorkpete below does. Commented Aug 22, 2019 at 18:22

Not the answer you're looking for? Browse other questions tagged or ask your own question.