Source: widget/ModelForm.js

/*
 * redmicro all Copyright (c)

 * Created by seeker910 on 2014/12/29.
 *
 * 对于不要显示但需要保存但数据(如:主键)的数据建议使用隐藏控件,有利于数据专递。
 *
 */
Rsd.define('Rsd.widget.ModelForm', {
    extend: 'Rsd.container.Form',
    requires: [
        'Rsd.container.FieldSet',
        'Rsd.form.Text',
        'Rsd.form.TextArea',
        'Rsd.form.TextFK',
        'Rsd.form.Date',
        'Rsd.form.Time',
        'Rsd.form.Timestamp',
        'Rsd.form.Number',
        'Rsd.form.Hidden',
        'Rsd.form.CheckBox',
        'Rsd.form.ComboBoxEnum',
        'Rsd.form.Picker',
        'Rsd.form.Image',
        'Rsd.form.Images',
        'Rsd.form.Json'
    ],
    xtype: 'model-form',
    layout: 'fit',
    margin: '10 0 10 0',
    height: 'auto',
    //fields 已加载
    //isLoaded:false,
    readOnly: true,
    errorList: [],
    /*
    * 对于不要显示但需要保存但数据(如:主键)的数据建议使用隐藏控件,有利于数据专递。
    * */
    fields: [],
    /**
     * 
     */
    fieldWidth: '45%',
    //最后一次加载的数据对象
    //data:{}, 
    items: [
        {
            xtype: 'fieldset',
            header:null,
            legend: '明 细 信 息',
            height: "100%",
            items: [], 
            layout: { type: 'vbox', align: 'left' }
        }
    ],
    /*
     * */
    constructor: function ModelViewControl(config) {
        config = config || {};
        this.apply(config);

        this.items[0].legend = this.legend; 
    },
    /*
    * */
    onAfterRender: function onAfterRender() {

        var me = this;
        
        setTimeout(function () {
            
            me.loadFields();//render 之后会执行doLayout

            //出现滚动条 重新设置 该控件高度,不让该控件出现滚动条,让滚动条出现在该控件父控件中
           if(me.items[0].body.scrollHeight > me.items[0].body.clientHeight) 
           {
               var _scrollHeight = me.items[0].body.scrollHeight + (me.items[0].legend ? 100 : 45);
          
               me.height = _scrollHeight;
           }
           
       }, 50);

       me.callParent(); 
    },
    /*
    * */
    loadFields: function loadFields() {

        //debugger; 
        var me = this;
        if (me.isLoaded) {
            return;
        }
        //debugger;
        if (me.items[0] == null || me.items[0] == undefined) {

            return;
        }
        var _readOnly = me.readOnly;

        if (_readOnly === undefined || _readOnly==null) {
            _readOnly = false;
        }

        var formfields = me.fields;
        var _w = 0;
        var _width = me.getWidth() || me.parent.getWidth();
       
        if (formfields && formfields.length > 0) {
            var fields = formfields;
            var _field = null; 
            for (var f in fields) {
                //debugger;
              
                try {
                    _field = Rsd.clone(fields[f]);

                    var _dataIndex = _field.dataIndex || _field.dataindex || _field.name;
                    var _defaultXtype = "text";
                    if(!_dataIndex && !_field.xtype)
                    { 
                         _defaultXtype =  "component-x";
                    }

                    if (_field.label) {
                        _field.label.content = _field.label.content || _field.label.text;
                        _field.label.style = Rsd.apply({ lineHeight: _field.height || 40 }, _field.label.style);
                        delete _field.label.text;
                    }
                    if (_field.hasOwnProperty('readOnly')) {
                        _field.readOnly = (_readOnly ? true : _field.readOnly);
                    }
                    else {
                        _field.readOnly = _readOnly;
                    }
                    var _h = 0;
                    if (_field.xtype != 'hidden') {
                        _h = _field.height || 40;
                    }
                    _w += _field.width || 0;
                    if (_field.width && _width && _w < _width) {
                    }
                    else {
                        _w = _field.width || 0; 
                    }
 
                    var _new_field = Rsd.apply(
                        {
                            id: _field.id || _field.name || '',
                            dataIndex: _dataIndex,
                            height: _h,
                            width: me.fieldWidth || '45%',
                            tabIndex: f,
                            margin: '4 0 4 0',
                            xtype: _defaultXtype
                        }, _field);
                    
                    if (me.items[0] instanceof Rsd.container.Component) {
                        me.items[0].add(_new_field);
                    }
                    else {
                        me.items[0].items.push(_new_field);
                    }
                }
                catch (ex) {
                    console.error(ex);
                }
            }
            
            me.isLoaded = true;
        }
 
        //isLoaded == false 时 ,数据不会被加载
        me.loadData();

        return this;
    },
    /**
     * @description 验证控件输入值 是否有效
     *  */
    checkRecord: function checkRecord() {

        var _item = null;
        var _form = this.items[0];
        this.errorList = [];
        for (var i = 0; i < _form.items.length; i++) {
            _item = _form.items[i];

            if (!Rsd.isFunction(_item.checkValue) ) {
                if(_item.xtype !=='component-x'  || _item.xtype !=='container' )
                {
                    continue;
                }
                console.warn('Control [' + _item.$className + '('+_item.xtype+')] has no function \'checkValue\'.');
                continue;
            }

            try {
                if (!_item.checkValue()) {
                    this.errorList.push(_item.getError());
                }
            }
            catch (err) {
                console.error(err);
            }

        }

        return this.errorList.length == 0;
    },
    /**
    * @description 错误消息处理
    * @description handler:方法注入
    * */
    showError: function showError(handler) {

        if (this.errorList.length > 0) {
            if (handler) {
                handler.call(this, [this.errorList]);
            }
            else {
                Rsd.alert('错误提示', this.errorList);
            }
        }

    },
    /** 
    * @description 将控件获取到到数据合并到 参数obj 或data 中返回;
    * @description 在获取前,应先验证form的数据是否全部有效,
    *
    * */
    getRecord: function getRecord(obj) {

        var _obj = obj || this.data || {};
        var me = this;
        var _item = null;
        var _form = me.items[0];

        for (var i = 0; i < _form.items.length; i++) {
            _item = _form.items[i];

            if (_item.readOnly) {
                //continue;
            }
            var _dataIndex = _item.dataIndex || _item.dataindex || _item.name;
            if (Rsd.isEmpty(_dataIndex)) {
                continue;
            }
            _obj[_dataIndex] = _item.getValue();
        }

        return _obj;

    },
    /**
    *
    * @description 获取字段值
    * */
    getFieldValue: function getFieldValue(name) {
        var _obj = this.data || {};
        var me = this;
        var _item = null;
        var _form = me.items[0];

        for (var i = 0; i < _form.items.length; i++) {
            _item = _form.items[i];
            if (_item.readOnly) {
                continue;
            }
            _obj[_item.dataIndex || _item.dataindex] = _item.getValue();
        }

        return _obj[name];
    },

    /**
     *@description 
     * */
    loadData: function loadData(record) {

        var _r = record || this.data || {};
        this.data = _r;
        //fields  暂未加载 不加载数据,更新this.data
        if (this.isLoaded == false) {
            return;
        }
      
        var me = this;
        var _item = null;
        var _dataIndex = null;
        for (var i = 0; i < me.items[0].items.length; i++) {
            _item = me.items[0].items[i];

            try {
                _dataIndex = _item.dataIndex || _item.dataindex || _item.name ||'';
                if(_dataIndex)
                {
                    //console.log(_dataIndex,Rsd.hasProperty(_r, _dataIndex),_r);
                    //_item.setDisabled(!Rsd.hasProperty(_r, _dataIndex));
                    if (_r[_dataIndex] !== undefined) {
                        _item.setValue(_r[_dataIndex]);
                    }
                    else 
                    {
                        var list = _dataIndex.split('.');
                        var j = 0;
                        var _p = _r;
                        while (list.length > 1 && j < list.length && Rsd.hasProperty(_p, list[j])) {
                            _p = _p[list[j]];
                            j++;
                        }
                        if (j == list.length) {
                            _item.setValue(_p);
                        }
                    }
                }
                
            }
            catch (e) {
                console.error(e);
            }

        }
        return this;
    },

    /*
    *@param key:index or name or id  or xtype
    * */
    getFieldControl: function getFieldControl(key) {
        
        if (Rsd.isNumber(key)) {
            //console.log(key,this.items[0].items.length);
            return this.items[0].items[key];
        }
        return this.items[0].getItemByName(key) || this.items[0].getItemById(key) || this.items[0].getItemByXtype(key);
    },
    /**
     * 
     */
    getScrollHeight: function getScrollHeight() {
        return this.items[0].body.scrollHeight;
    }


}, function (type) {

    var _dataGetter = function () {

        if (!this.hasOwnProperty('__data')) {
            this.__data = {};
        }
        return this.__data;
    };
    var _dataSetter = function (value) {

        this.__data = value;
        return;

    };
    this.defineProperty(type, "data", _dataGetter, _dataSetter, true);

    //
    this.defineProperty(type, "isLoaded", function () {

        if (!this.hasOwnProperty('__isLoaded')) {
            this.__isLoaded = false;
        }
        return this.__isLoaded;

    }, function (value) {
        this.__isLoaded = value;
    }, false);

});