Nhibernate 将HQL查询结果绑定到DevExpress GridControl

Nhibernate 将HQL查询结果绑定到DevExpress GridControl,nhibernate,data-binding,devexpress,hql,Nhibernate,Data Binding,Devexpress,Hql,我想用DevExpressGridControl绑定HQL查询结果 无法在编译时预测查询定义。它是基于用户定义的配置设置构建的 var queryResults = GetSession().CreateQuery(PrepereHQLQuery()).List(); gridControl1.DataSource = queryResults; 假设PrepareHQLQuery返回select col1,col2 from MyTable我想得到如下结果: 与此相反: 是否存在将Gri

我想用
DevExpress
GridControl
绑定
HQL
查询结果

无法在编译时预测查询定义。它是基于用户定义的配置设置构建的

var queryResults = GetSession().CreateQuery(PrepereHQLQuery()).List();
gridControl1.DataSource = queryResults;
假设
PrepareHQLQuery
返回
select col1,col2 from MyTable
我想得到如下结果:

与此相反:

是否存在将GridView列配置为直接从
对象[]
列表中显示数据的方法


由于HQL查询的不可预测性,我还希望避免中间对象,例如
DTO

您可以创建一个封装HQL查询结果的包装器类,该查询结果实现IList和ITypedList接口。这种方法允许您将HQL查询结果用作XtraGrid的数据源。
以下是一个您可以调整的小示例:

IList<object[]> queryResult = new List<object[]>{
    new object[]{ "a", 11 },
    new object[]{ "b", 22 }
};
gridControl1.DataSource = new QueryWrapper(queryResult);
//...
public class QueryWrapper : IList, ITypedList {
    class ColumnDescriptor : PropertyDescriptor {
        int index;
        Type elementType;
        public ColumnDescriptor(string name, int index, Type elementType)
            : base(name, null) {
            this.index = index;
            this.elementType = elementType;
        }
        public override Type ComponentType {
            get { return typeof(RowDescriptor); }
        }
        public override bool IsReadOnly {
            get { return false; }
        }
        public override Type PropertyType {
            get { return elementType; }
        }
        public override object GetValue(object component) {
            return ((RowDescriptor)component).GetValue(index);
        }
        public override void SetValue(object component, object value) {
            ((RowDescriptor)component).SetValue(index, value);
        }
        public override bool CanResetValue(object component) { return false; }
        public override void ResetValue(object component) { }
        public override bool ShouldSerializeValue(object component) { return false; }
    }
    class RowDescriptor : CustomTypeDescriptor {
        QueryWrapper owner;
        object[] rowObjects;
        public RowDescriptor(QueryWrapper owner, object[] rowObjects) {
            this.rowObjects = rowObjects;
            this.owner = owner;
        }
        public object GetValue(int index) {
            return rowObjects[index];
        }
        public void SetValue(int index, object value) {
            rowObjects[index] = value;
        }
        public override PropertyDescriptorCollection GetProperties(Attribute[] attributes) {
            return owner.pdc;
        }
    }
    IList<object[]> query;
    List<RowDescriptor> list;
    public QueryWrapper(IList<object[]> query) {
        this.query = query;
        list = new List<RowDescriptor>(query.Count);
        for(int i = 0; i < query.Count; i++)
            list.Add(new RowDescriptor(this, query[i]));
    }
    #region IList Members
    int IList.Add(object value) {
        throw new NotSupportedException();
    }
    void IList.Clear() {
        throw new NotSupportedException();
    }
    bool IList.Contains(object value) {
        return value is RowDescriptor && list.Contains((RowDescriptor)value);
    }
    int IList.IndexOf(object value) {
        return (value is RowDescriptor) ? list.IndexOf((RowDescriptor)value) : -1;
    }
    void IList.Insert(int index, object value) {
        throw new NotSupportedException();
    }
    bool IList.IsFixedSize {
        get { return true; }
    }
    bool IList.IsReadOnly {
        get { return true; }
    }
    void IList.Remove(object value) {
        throw new NotSupportedException();
    }
    void IList.RemoveAt(int index) {
        throw new NotSupportedException();
    }
    object IList.this[int index] {
        get { return list[index]; }
        set { throw new NotSupportedException(); }
    }
    #endregion
    #region ICollection Members
    void ICollection.CopyTo(Array array, int index) {
        if(array is RowDescriptor[]) list.CopyTo((RowDescriptor[])array, index);
    }
    int ICollection.Count {
        get { return list.Count; }
    }
    bool ICollection.IsSynchronized {
        get { return false; }
    }
    object ICollection.SyncRoot {
        get { return this; }
    }
    #endregion
    #region IEnumerable Members
    IEnumerator IEnumerable.GetEnumerator() {
        return list.GetEnumerator();
    }
    #endregion
    #region ITypedList Members
    PropertyDescriptorCollection pdc;
    PropertyDescriptorCollection ITypedList.GetItemProperties(PropertyDescriptor[] listAccessors) {
        if(pdc == null) {
            if(query.Count > 0) {
                PropertyDescriptor[] pd = new PropertyDescriptor[query[0].Length];
                for(int i = 0; i < pd.Length; i++)
                    pd[i] = new ColumnDescriptor("Column" + i, i, query[0][i].GetType());
                pdc = new PropertyDescriptorCollection(pd);
            }
            else pdc = new PropertyDescriptorCollection(new PropertyDescriptor[] { });
        }
        return pdc;
    }
    string ITypedList.GetListName(PropertyDescriptor[] listAccessors) { return string.Empty; }
    #endregion
}
IList queryResult=新列表{
新对象[]{“a”,11},
新对象[]{“b”,22}
};
gridControl1.DataSource=新的queryRapper(queryResult);
//...
公共类查询说话者:IList,ITypedList{
类列描述符:PropertyDescriptor{
整数指数;
类型元素类型;
公共列描述符(字符串名称、整型索引、类型elementType)
:base(名称,null){
这个指数=指数;
this.elementType=elementType;
}
公共重写类型ComponentType{
获取{return typeof(rowsdescriptor);}
}
公共覆盖布尔为只读{
获取{return false;}
}
公共覆盖类型PropertyType{
获取{return elementType;}
}
公共覆盖对象GetValue(对象组件){
返回((行描述符)组件).GetValue(索引);
}
公共覆盖无效设置值(对象组件、对象值){
((行描述符)组件).SetValue(索引,值);
}
公共重写bool CanResetValue(对象组件){return false;}
公共重写无效重置值(对象组件){}
公共重写bool ShouldSerializeValue(对象组件){return false;}
}
类RowDescriptor:CustomTypeDescriptor{
询问者所有者;
对象[]行对象;
公共行描述符(QueryRapper所有者,对象[]行对象){
this.rowObjects=rowObjects;
this.owner=所有者;
}
公共对象GetValue(int索引){
返回行对象[索引];
}
public void SetValue(int索引,对象值){
行对象[索引]=值;
}
公共重写属性DescriptorCollection GetProperties(属性[]属性){
返回owner.pdc;
}
}
IList查询;
名单;
公共查询说话者(IList查询){
this.query=query;
列表=新列表(query.Count);
for(int i=0;i0){
PropertyDescriptor[]pd=新的PropertyDescriptor[查询[0]。长度];
对于(int i=0;i