Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/delphi/9.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Delphi 将对象与TListView绑定_Delphi_Data Binding_Livebindings - Fatal编程技术网

Delphi 将对象与TListView绑定

Delphi 将对象与TListView绑定,delphi,data-binding,livebindings,Delphi,Data Binding,Livebindings,我最近发现了数据绑定,并进行了跟踪。我用TEdit实现了它,但现在我有了一个TObjectList,我实现了绑定它们,但它只能以一种方式工作。当我修改TObjectList时,它会更改ListView,但当我修改ListView时:它不会更改TObjectList 这是我的密码: // When I change an Item of my ListView procedure TForm1.ListView1Change(Sender: TObject; Item: TListItem;

我最近发现了
数据绑定
,并进行了跟踪。我用
TEdit
实现了它,但现在我有了一个
TObjectList
,我实现了绑定它们,但它只能以一种方式工作。当我修改
TObjectList
时,它会更改
ListView
,但当我修改
ListView
时:它不会更改
TObjectList

这是我的密码:

// When I change an Item of my ListView
procedure TForm1.ListView1Change(Sender: TObject; Item: TListItem;
  Change: TItemChange);
begin
  TBindings.Notify(Sender, 'Items.Item[' + IntToStr(Item.Index) +   '].Caption');
end;

// When I add a new item to my TListView, and I want that to be bound with my ListView
itemAdd := ListView1.Items.Add;
Item.Bind('id', ListView1, 'Items.Item[' + IntToStr(ListView1.Items.Count-1) + '].Caption');



  // The TBoundObject Class. Every class thatI want to bind with UI, inherits from this class
  unit U_TBoundObject;

  interface

  uses
    Generics.Collections, System.Bindings.Expression, System.Bindings.Helper;

  type
    TBoundObject = class
    protected
      type
        TExpressionList = TObjectList<TBindingExpression>;
    private
      FBindings: TExpressionList;
    protected
      procedure Notify(const APropertyName: string = '');
      property Bindings: TExpressionList read FBindings;
    public
      constructor Create; virtual;
      destructor Destroy; override;
      procedure Bind(const AProperty: string; const ABindToObject: TObject;
          const ABindToProperty: string; const ACreateOptions:
          TBindings.TCreateOptions = [coNotifyOutput, coEvaluate]);
      procedure ClearBindings;
    end;

  implementation

  constructor TBoundObject.Create;
  begin
    inherited;
    FBindings := TExpressionList.Create(false {AOwnsObjects});
  end;

  destructor TBoundObject.Destroy;
  begin
    ClearBindings;
    FBindings.Free;
    inherited;
  end;

  procedure TBoundObject.ClearBindings;
  var
    i: TBindingExpression;
  begin
    for i in FBindings do
      TBindings.RemoveBinding(i);
    FBindings.Clear;
  end;

  procedure TBoundObject.Notify(const APropertyName: string);
  begin
    TBindings.Notify(Self, APropertyName);
  end;

  procedure TBoundObject.Bind(const AProperty: string;
    const ABindToObject: TObject; const ABindToProperty: string;
    const ACreateOptions: TBindings.TCreateOptions);
  begin
    // From source to dest
    FBindings.Add(TBindings.CreateManagedBinding(
        { inputs }
        [TBindings.CreateAssociationScope([Associate(Self, 'src')])],
        'src.' + AProperty,
        { outputs }
        [TBindings.CreateAssociationScope([Associate(ABindToObject, 'dst')])],
        'dst.' + ABindToProperty,
        nil, nil, ACreateOptions));
    // From dest to source
    FBindings.Add(TBindings.CreateManagedBinding(
        { inputs }
        [TBindings.CreateAssociationScope([Associate(ABindToObject, 'src')])],
        'src.' + ABindToProperty,
        { outputs }
        [TBindings.CreateAssociationScope([Associate(Self, 'dst')])],
        'dst.' + AProperty,
        nil, nil, ACreateOptions));
  end;

  end.
//当我更改ListView的一项时
程序TForm1.ListView1更改(发送方:ToObject;项:TListItem;
变更:滴度变更);
开始
TBindings.Notify(发送方,'Items.Item['+IntToStr(Item.Index)+'].Caption');
结束;
//当我将一个新项目添加到我的TListView时,我希望它与我的ListView绑定
itemAdd:=ListView1.Items.Add;
Item.Bind('id',ListView1',Items.Item['+IntToStr(ListView1.Items.Count-1)+'].Caption');
//TBoundObject类。我想与UI绑定的每个类都继承自这个类
单位U_TBoundObject;
接口
使用
Generics.Collections、System.Bindings.Expression、System.Bindings.Helper;
类型
TBoundObject=class
受保护的
类型
TExpressionList=TObjectList;
私有的
FBindings:TExpressionList;
受保护的
过程通知(const-APropertyName:string='');
属性绑定:TExpressionList读取FBindings;
公众的
构造函数创建;事实上的
毁灭者毁灭;推翻
过程绑定(const-AProperty:string;const-ABindToObject:TObject;
常量ABindToProperty:字符串;常量ACreateOptions:
TBindings.TCreateOptions=[coNotifyOutput,coEvaluate]);
程序绑定;
结束;
实施
构造函数TBoundObject.Create;
开始
继承;
FBindings:=TExpressionList.Create(false{AOwnsObjects});
结束;
析构函数TBoundObject.Destroy;
开始
清晰绑定;
FBindings.免费;
继承;
结束;
过程TBoundObject.ClearBindings;
变量
i:TBindingExpression;
开始
因为我在FBindings工作
t绑定。移除绑定(i);
FBindings.清晰;
结束;
过程TBoundObject.Notify(const APropertyName:string);
开始
TBindings.Notify(Self,APropertyName);
结束;
过程TBoundObject.Bind(常量属性:string;
常量ABindToObject:ToObject;常量ABindToProperty:string;
const ACreateOptions:TBindings.TCreateOptions);
开始
//从源头到目的地
添加(TBindings.CreateManagedBinding(
{inputs}
[TBindings.CreateAssociationScope([Associate(Self,'src')]),
“src.+a属性,
{输出}
[TBindings.CreateAssociationScope([Associate(ABindToObject,'dst')]),
“dst”。+ABindToProperty,
零,零,零);
//从目的地到来源
添加(TBindings.CreateManagedBinding(
{inputs}
[TBindings.CreateAssociationScope([Associate(ABindToObject,'src')]),
“src”。+ABindToProperty,
{输出}
[TBindings.CreateAssociationScope([Associate(Self,'dst')]),
“dst”。+A属性,
零,零,零);
结束;
结束。

我知道你想做什么,但你并没有真正做到

本质上,您试图绑定两个对象的属性,但您将子属性(属性的属性)视为属性。你说它是单向的,但对我来说不是

通过直接(而不是间接)处理对象,它变得容易得多

这就是我添加和关联相关对象的方式

procedure TForm2.SpeedButtonAddClick(Sender: TObject);
var
  ItemAdd : TListItem;
  Item : TFeature;
begin
  Item := TFeature.Create;
  fObjectList.Add( Item );
  ItemAdd := ListView1.Items.Add;
  Item.Bind('id', ItemAdd, 'Caption');
end;
这是对象更改的代码

procedure TFeature.SetID(const Value: string);
begin
  if fID <> Value then // prevent an infinite loop
  begin
    fID := Value;
    TBindings.Notify( self, 'id' );
  end;
end;

我已经对它进行了测试,它在两个方向都能工作。

我认为您在这里给我们展示的还不够。你能发布一个最小的可验证代码吗?我们可以自己编译并尝试。(如果不是太长的话,你实际完整的代码可能就足够了。)嗨,实际上我的代码很长,我真的不知道我可以添加什么…让我试试boundobject类!是VCL还是FMX?我猜你的对象列表类似于TObjectList?它是VCL,我的对象类似于TObjectList。t功能继承自TBoundObjectHello man。好的,非常感谢!它的工作方式正是我想要的:)
procedure TForm2.ListView1Change(Sender: TObject; Item: TListItem;
  Change: TItemChange);
begin
  TBindings.Notify(Item, 'Caption');
end;