/*
 * SDK Pullenti Lingvo, version 4.33, fabruary 2026. Copyright (c) 2013-2026, Pullenti. All rights reserved. 
 * Non-Commercial Freeware and Commercial Software.
 * This class is generated using the converter Unisharping (www.unisharping.ru) from Pullenti C#.NET project. 
 * The latest version of the code is available on the site www.pullenti.ru
 */

const Utils = require("./../../unisharp/Utils");
const StringBuilder = require("./../../unisharp/StringBuilder");

const ReferentsEqualType = require("./../core/ReferentsEqualType");
const ReferentClass = require("./../metadata/ReferentClass");
const DecreeChangeKind = require("./DecreeChangeKind");
const Referent = require("./../Referent");
const MetaDecreeChange = require("./internal/MetaDecreeChange");

/**
 * Модель изменения структурной части НПА
 */
class DecreeChangeReferent extends Referent {
    
    constructor() {
        super(DecreeChangeReferent.OBJ_TYPENAME);
        this.instanceOf = MetaDecreeChange.GLOBAL_META;
    }
    
    toStringEx(shortVariant, lang = null, lev = 0) {
        let res = new StringBuilder();
        if (this.kind !== DecreeChangeKind.UNDEFINED) 
            res.append(MetaDecreeChange.KIND_FEATURE.convertInnerValueToOuterValue(this.kind.toString(), lang)).append(" ");
        for (const o of this.owners) {
            res.append("'").append(o.toStringEx(true, lang, 0)).append("' ");
        }
        if (this.locValue !== null) 
            res.append("[").append(this.locValue.toStringEx(true, lang, 0)).append("] ");
        if (this.value !== null) 
            res.append(this.value.toStringEx(true, lang, 0)).append(" ");
        if (this.param !== null) {
            if (this.kind === DecreeChangeKind.APPEND) 
                res.append("после ");
            else if (this.kind === DecreeChangeKind.EXCHANGE) 
                res.append("вместо ");
            res.append(this.param.toStringEx(true, lang, 0));
        }
        return res.toString().trim();
    }
    
    get parentReferent() {
        return Utils.as(this.getSlotValue(DecreeChangeReferent.ATTR_OWNER), Referent);
    }
    
    get kind() {
        let s = this.getStringValue(DecreeChangeReferent.ATTR_KIND);
        if (s === null) 
            return DecreeChangeKind.UNDEFINED;
        try {
            if (s === "Add") 
                return DecreeChangeKind.APPEND;
            let res = DecreeChangeKind.of(s);
            if (res instanceof DecreeChangeKind) 
                return DecreeChangeKind.of(res);
        } catch (ex1471) {
        }
        return DecreeChangeKind.UNDEFINED;
    }
    set kind(_value) {
        if (_value !== DecreeChangeKind.UNDEFINED) 
            this.addSlot(DecreeChangeReferent.ATTR_KIND, _value.toString(), true, 0);
        return _value;
    }
    
    get owners() {
        let res = new Array();
        for (const s of this.slots) {
            if (s.typeName === DecreeChangeReferent.ATTR_OWNER && (s.value instanceof Referent)) {
                if (!res.includes(Utils.as(s.value, Referent))) 
                    res.push(Utils.as(s.value, Referent));
            }
        }
        return res;
    }
    
    get children() {
        let res = new Array();
        for (const s of this.slots) {
            if (s.typeName === DecreeChangeReferent.ATTR_CHILD && (s.value instanceof DecreeChangeReferent)) 
                res.push(Utils.as(s.value, DecreeChangeReferent));
        }
        return res;
    }
    
    get value() {
        const DecreeChangeValueReferent = require("./DecreeChangeValueReferent");
        return Utils.as(this.getSlotValue(DecreeChangeReferent.ATTR_VALUE), DecreeChangeValueReferent);
    }
    set value(_value) {
        this.addSlot(DecreeChangeReferent.ATTR_VALUE, _value, true, 0);
        return _value;
    }
    
    get param() {
        const DecreeChangeValueReferent = require("./DecreeChangeValueReferent");
        return Utils.as(this.getSlotValue(DecreeChangeReferent.ATTR_PARAM), DecreeChangeValueReferent);
    }
    set param(_value) {
        this.addSlot(DecreeChangeReferent.ATTR_PARAM, _value, true, 0);
        return _value;
    }
    
    get locValue() {
        const DecreeChangeValueReferent = require("./DecreeChangeValueReferent");
        return Utils.as(this.getSlotValue(DecreeChangeReferent.ATTR_LOCVALUE), DecreeChangeValueReferent);
    }
    set locValue(_value) {
        this.addSlot(DecreeChangeReferent.ATTR_LOCVALUE, _value, true, 0);
        return _value;
    }
    
    canBeEquals(obj, typ = ReferentsEqualType.WITHINONETEXT) {
        return obj === this;
    }
    
    checkCorrect() {
        const DecreePartReferent = require("./DecreePartReferent");
        if (this.kind === DecreeChangeKind.UNDEFINED) 
            return false;
        if (((this.kind === DecreeChangeKind.EXPIRE || this.kind === DecreeChangeKind.EXPIRECHANGES || this.kind === DecreeChangeKind.REMOVE) || this.kind === DecreeChangeKind.SUSPEND || this.kind === DecreeChangeKind.ERROR) || this.kind === DecreeChangeKind.CONFIDENTIAL) 
            return true;
        if (this.value === null) 
            return false;
        if (this.kind === DecreeChangeKind.EXCHANGE) {
            if (this.param === null) {
                let owns = this.owners;
                if (owns.length > 0 && owns[0].findSlot(DecreePartReferent.ATTR_INDENTION, null, true) !== null) 
                    this.kind = DecreeChangeKind.NEW;
                else if (owns.length > 0 && owns[0].findSlot(DecreePartReferent.ATTR_SENTENCE, null, true) !== null) 
                    this.kind = DecreeChangeKind.NEW;
                else 
                    return false;
            }
        }
        return true;
    }
    
    static _new1447(_arg1) {
        let res = new DecreeChangeReferent();
        res.kind = _arg1;
        return res;
    }
    
    static static_constructor() {
        DecreeChangeReferent.OBJ_TYPENAME = "DECREECHANGE";
        DecreeChangeReferent.ATTR_OWNER = "OWNER";
        DecreeChangeReferent.ATTR_KIND = "KIND";
        DecreeChangeReferent.ATTR_CHILD = "CHILD";
        DecreeChangeReferent.ATTR_VALUE = "VALUE";
        DecreeChangeReferent.ATTR_PARAM = "PARAM";
        DecreeChangeReferent.ATTR_LOCVALUE = "LOCVALUE";
        DecreeChangeReferent.ATTR_MISC = "MISC";
    }
}


DecreeChangeReferent.static_constructor();

module.exports = DecreeChangeReferent