"use strict";
/*---------------------------------------------------------------------------------------------
 *  Copyright (c) Microsoft Corporation. All rights reserved.
 *  Licensed under the MIT License. See License.txt in the project root for license information.
 *--------------------------------------------------------------------------------------------*/
Object.defineProperty(exports, "__esModule", { value: true });
exports.EnumClass = void 0;
const codegen_csharp_1 = require("@azure-tools/codegen-csharp");
const codegen_csharp_2 = require("@azure-tools/codegen-csharp");
const codegen_csharp_3 = require("@azure-tools/codegen-csharp");
const codegen_csharp_4 = require("@azure-tools/codegen-csharp");
const codegen_csharp_5 = require("@azure-tools/codegen-csharp");
const codegen_csharp_6 = require("@azure-tools/codegen-csharp");
const codegen_csharp_7 = require("@azure-tools/codegen-csharp");
const codegen_csharp_8 = require("@azure-tools/codegen-csharp");
const codegen_csharp_9 = require("@azure-tools/codegen-csharp");
const codegen_csharp_10 = require("@azure-tools/codegen-csharp");
const codegen_csharp_11 = require("@azure-tools/codegen-csharp");
const codegen_csharp_12 = require("@azure-tools/codegen-csharp");
class EnumClass extends codegen_csharp_12.Struct {
    get schema() {
        return this.implementation.schema;
    }
    get convertObjectMethod() {
        return this.implementation.convertObjectMethod;
    }
    get defaultOfType() {
        return (0, codegen_csharp_1.toExpression)('null /* enum value */');
    }
    deserializeFromContainerMember(mediaType, container, serializedName, defaultValue) {
        return this.implementation.deserializeFromContainerMember(mediaType, container, serializedName, defaultValue);
    }
    deserializeFromNode(mediaType, node, defaultValue) {
        return this.implementation.deserializeFromNode(mediaType, node, defaultValue);
    }
    /** emits an expression to deserialize content from a string */
    deserializeFromString(mediaType, content, defaultValue) {
        return this.implementation.deserializeFromString(mediaType, content, defaultValue);
    }
    /** emits an expression to deserialize content from a content/response */
    deserializeFromResponse(mediaType, content, defaultValue) {
        return this.implementation.deserializeFromResponse(mediaType, content, defaultValue);
    }
    serializeToNode(mediaType, value, serializedName, mode) {
        return this.implementation.serializeToNode(mediaType, value, serializedName, mode);
    }
    /** emits an expression serialize this to a HttpContent */
    serializeToContent(mediaType, value, mode) {
        return this.implementation.serializeToContent(mediaType, value, mode);
    }
    serializeToContainerMember(mediaType, value, container, serializedName, mode) {
        return this.implementation.serializeToContainerMember(mediaType, value, container, serializedName, mode);
    }
    get isXmlAttribute() {
        return this.implementation.isXmlAttribute;
    }
    get isNullable() {
        return this.implementation.isNullable;
    }
    get isRequired() {
        return this.implementation.isRequired;
    }
    constructor(schemaWithFeatures, state, objectInitializer) {
        var _a, _b, _c, _d, _e, _f;
        if (!((_a = schemaWithFeatures.schema.language.csharp) === null || _a === void 0 ? void 0 : _a.enum)) {
            throw new Error(`ENUM AINT XMSENUM: ${(_b = schemaWithFeatures.schema.language.csharp) === null || _b === void 0 ? void 0 : _b.name}`);
        }
        super(state.project.supportNamespace, (_c = schemaWithFeatures.schema.language.csharp) === null || _c === void 0 ? void 0 : _c.enum.name, undefined, {
            interfaces: [new codegen_csharp_5.Interface(new codegen_csharp_8.Namespace('System'), 'IEquatable', {
                    genericParameters: [`${(_d = schemaWithFeatures.schema.language.csharp) === null || _d === void 0 ? void 0 : _d.enum.name}`]
                })],
        });
        this.description = (_e = schemaWithFeatures.schema.language.csharp) === null || _e === void 0 ? void 0 : _e.description;
        this.implementation = schemaWithFeatures;
        this.partial = true;
        this.apply(objectInitializer);
        // add known enum values
        for (const evalue of ((_f = schemaWithFeatures.schema.language.csharp) === null || _f === void 0 ? void 0 : _f.enum.values) || []) {
            this.addField(new codegen_csharp_4.Field(evalue.name, this, { initialValue: new codegen_csharp_3.StringExpression(evalue.value), static: codegen_csharp_1.Modifier.Static, description: evalue.description }));
        }
        // add backingField
        const backingField = this.add(new codegen_csharp_11.Property('_value', codegen_csharp_7.dotnet.String, {
            getAccess: codegen_csharp_1.Access.Private,
            setAccess: codegen_csharp_1.Access.Private,
            description: `the value for an instance of the <see cref="${this.name}" /> Enum.`
        }));
        // add private constructor
        const p = new codegen_csharp_10.Parameter('underlyingValue', codegen_csharp_7.dotnet.String, { description: 'the value to create an instance for.' });
        const ctor = this.addMethod(new codegen_csharp_2.Constructor(this, {
            access: codegen_csharp_1.Access.Private,
            parameters: [p],
            description: `Creates an instance of the <see cref="${this.name}"/> Enum class.`
        })).add(`this.${backingField.value} = ${p.value};`);
        // add toString Method
        this.addMethod(new codegen_csharp_6.Method('ToString', codegen_csharp_7.dotnet.String, {
            override: codegen_csharp_1.Modifier.Override,
            description: `Returns string representation for ${this.name}`,
            returnsDescription: 'A string for this value.'
        })).add(`return this.${backingField.value};`);
        // add Equals Method(thistype)
        this.addMethod(new codegen_csharp_6.Method('Equals', codegen_csharp_7.dotnet.Bool, {
            description: `Compares values of enum type ${this.name}`,
            parameters: [new codegen_csharp_10.Parameter('e', this, { description: 'the value to compare against this instance.' })],
            returnsDescription: '<c>true</c> if the two instances are equal to the same value'
        })).add(`return ${backingField.value}.Equals(e.${backingField.value});`);
        // add Equals Method(object)
        this.addMethod(new codegen_csharp_6.Method('Equals', codegen_csharp_7.dotnet.Bool, {
            override: codegen_csharp_1.Modifier.Override,
            description: `Compares values of enum type ${this.name} (override for Object)`,
            parameters: [new codegen_csharp_10.Parameter('obj', codegen_csharp_7.dotnet.Object, { description: 'the value to compare against this instance.' })],
            returnsDescription: '<c>true</c> if the two instances are equal to the same value'
        })).add(`return obj is ${this.name} && Equals((${this.name})obj);`);
        // add implicit operator(string)
        this.addMethod(new codegen_csharp_9.Operator(`implicit operator ${this.name}`, {
            static: codegen_csharp_1.Modifier.Static,
            description: `Implicit operator to convert string to ${this.name}`,
            parameters: [new codegen_csharp_10.Parameter('value', codegen_csharp_7.dotnet.String, { description: `the value to convert to an instance of <see cref="${this.name}" />.` })]
        })).add(`return new ${this.name}(value);`);
        // add static creation 
        this.addMethod(new codegen_csharp_6.Method('CreateFrom', codegen_csharp_7.dotnet.Object, {
            static: codegen_csharp_1.Modifier.Static,
            access: codegen_csharp_1.Access.Internal,
            description: `Conversion from arbitrary object to ${this.name}`,
            parameters: [new codegen_csharp_10.Parameter('value', codegen_csharp_7.dotnet.Object, { description: `the value to convert to an instance of <see cref="${this.name}" />.` })]
        })).add(`return new ${this.name}(global::System.Convert.ToString(value));`);
        // add implicit operator(thistype)
        this.addMethod(new codegen_csharp_9.Operator('implicit operator string', {
            static: codegen_csharp_1.Modifier.Static,
            description: `Implicit operator to convert ${this.name} to string`,
            parameters: [new codegen_csharp_10.Parameter('e', this, { description: `the value to convert to an instance of <see cref="${this.name}" />.` })]
        })).add(`return e.${backingField.value};`);
        // add operator ==
        this.addMethod(new codegen_csharp_6.Method('operator ==', codegen_csharp_7.dotnet.Bool, {
            static: codegen_csharp_1.Modifier.Static,
            description: `Overriding == operator for enum ${this.name}`,
            parameters: [new codegen_csharp_10.Parameter('e1', this, { description: 'the value to compare against <paramref name="e2" />' }), new codegen_csharp_10.Parameter('e2', this, { description: 'the value to compare against <paramref name="e1" />' })],
            returnsDescription: '<c>true</c> if the two instances are equal to the same value'
        })).add('return e2.Equals(e1);');
        // add opeator !=
        this.addMethod(new codegen_csharp_6.Method('operator !=', codegen_csharp_7.dotnet.Bool, {
            static: codegen_csharp_1.Modifier.Static,
            description: `Overriding != operator for enum ${this.name}`,
            parameters: [new codegen_csharp_10.Parameter('e1', this, { description: 'the value to compare against <paramref name="e2" />' }), new codegen_csharp_10.Parameter('e2', this, { description: 'the value to compare against <paramref name="e1" />' })],
            returnsDescription: '<c>true</c> if the two instances are not equal to the same value'
        })).add('return !e2.Equals(e1);');
        // add getHashCode
        this.addMethod(new codegen_csharp_6.Method('GetHashCode', codegen_csharp_7.dotnet.Int, {
            override: codegen_csharp_1.Modifier.Override,
            description: `Returns hashCode for enum ${this.name}`,
            returnsDescription: 'The hashCode of the value'
        })).add(`return this.${backingField.value}.GetHashCode();`);
    }
    validateValue(eventListener, property) {
        return this.implementation.validateValue(eventListener, property);
    }
    validatePresence(eventListener, property) {
        return this.implementation.validatePresence(eventListener, property);
    }
}
exports.EnumClass = EnumClass;
//# sourceMappingURL=enum.js.map