ExtJS 5:父模型转换对子关联的依赖

时间:2016-02-12 23:07:34

标签: javascript extjs extjs5

我有2个模型......父母和孩子......父母有很多儿童模特。在Child中,我有一个通过使用其数据创建的字段(在此示例中,它只是转换并返回1)。在Parent中,我进行了两次转换...一次使用其数据,第二次转换取决于Child的数据。但是,在创建父模型时,看起来Child关联尚未完全烘焙,但是当我使用新值更新Parent模型时,Child关联就在那里。

基本上,我想知道的是,当你看到Total2控制台触发时,我希望填充Test。如何在父级中使用转换函数之前强制读取关联?理想情况下,如果Child中的变化,Parent中的依赖转换函数将自动触发......我意识到最有可能是不可能的,但这将是一个令人难以置信的额外奖励。

这是我的example

app.js

Ext.application({
    name : 'Fiddle',

    launch : function() {
        var store = Ext.create('Ext.data.Store', {
            model: 'Namespace.model.Parent',
            autoLoad: true,
            listeners: {
                load: onLoadStore
            }
        });
        var grid = Ext.create('Ext.grid.Panel', {
            title: 'associations',
            store: store,
            renderTo: Ext.getBody(),
            columns: [{
                text: 'Primary Key',
                dataIndex: 'PrimaryKey'
            }]
        });
        function onLoadStore(store, records, successful, eOpts) {
            var firstGroups = store.first().getGroupsStore();
            console.log('before', firstGroups.getCount(), firstGroups.isLoaded());
            firstGroups.first().set('GroupName', 'blah');
            store.first().set('blank', 1)
        }
    }
});

Ext.define('Namespace.model.Parent', {
  extend: 'Ext.data.Model',
  alias: 'model.parent',
  requires: [
    'Ext.data.field.Integer',
    'Ext.data.field.String',
    'Namespace.model.Child'
  ],

  idProperty: "PrimaryKey",
  fields: [{
    type: 'string',
    name: 'PrimaryKey',
    critical: true
  }, {
    type: 'string',
    name: 'Title'
  }, {
      type: 'int',
      name: 'Rating',
      defaultValue: 2
  }, {
      type: 'int',
      name: 'Total',
      depends: ['Rating'],
      convert: function(value, record) {
          console.log('Total', record)
          return record.get('Rating') * 2;
      }
  }, {
      name: 'Total2',
      type: 'int',
      depends: ['groupsMapping', 'blank'],
      // depends on child's Test property
      convert: function(value, record) {
          var groupsMapping = record.get('groupsMapping');
          if (groupsMapping) {
              for (var i = 0; i < groupsMapping.length; i++) {
                  console.log('Total2', groupsMapping[i].GroupName, groupsMapping[i].Test);
              }
          }
          return 0;
      }
  }, {
      name: 'groupsMapping',
      type: 'auto',
      mapping: 'Groups'
  }, {
      name: 'blank',
      type: 'int'
  }],

    hasMany: [{
        model: 'Namespace.model.Child',
        associationKey: 'Groups',
        name: 'getGroupsStore'
    }],

  proxy: {
    type: 'ajax',
    url: 'data1.json'
  }
});

儿童

Ext.define('Namespace.model.Child', {
    extend: 'Ext.data.Model',
    alias: 'model.child',

    fields: [{
        type: 'int',
        name: 'GroupInt',
        critical: true
    }, {
        type: 'string',
        name: 'GroupName'
    }, {
        name: 'Test',
        type: 'int',
        depends: ['GroupName'],
        convert: function() {
            console.log('Test, parent depends on this')
            return 1;
        }
    }],
    proxy: {
        type: 'memory'
    }
});

2 个答案:

答案 0 :(得分:1)

我遇到了同样的问题并花了一些时间才意识到转换时间无关联

在您的示例中,我将子记录与父记录(嵌套)一起发送,并使用子模型&amp;'手动'构建假存储。父字段子数据,以便为转换/计算做数学运算,这就是诀窍:

document.getElementById("7").onclick = function() { alert(this.id); }

但是现在我的“新”挑战是找出一个(好的)解决方案来更新子记录更改时的转换值...

答案 1 :(得分:0)

我做了类似于qdev的事情,除了我听了实际的关联商店。虽然有一些关于构造函数的问题......如果我没有把那个超时放在那里,那么我会在尝试访问商店加载中的第一条记录时出错...可能是一个框架错误,或者我做了一件可怕的事情。重要的代码是构造函数和计算方法......在应用程序中,我只更改了子数据的1秒超时...您可以看到网格的行数据从3更改为102.这里&# 39;更新了example

constructor: function(config) {
    this.callParent(arguments);
    var me = this;
    setTimeout(function() {
        var groupsStore = me.getGroupsStore();
        if (groupsStore) {
            groupsStore.on('update', me.calculateChanges, me);
            groupsStore.on('datachanged', me.calculateChanges, me);
        }
        me.calculateChanges();
    }, 1);
},

calculateChanges: function() {
    console.log('calculating');
    var groupsStore = this.getGroupsStore();
    if (groupsStore) {
        var total2 = 0;
        groupsStore.each(function(group) {
            total2 += group.get('Test');
        });
        this.set('Total2', total2);
    }
},