2012-02-23 1 views
6

내 프로젝트에서 모델이 있고 모델 속성 중 하나를 사용하여 레이블의 표시 상태를 바인딩 할 싶습니다. 모델에 다른 ShowLabel 속성을 추가하고 싶지 않습니다. 나는 이런 식으로 뭔가를 쓸 수 있도록하려면 : .net WinForms 데이터 바인딩을 대신 람다를 사용하여

label.Bindings.Add("Visible", model, m => m.Name != "Default"); 

은 기본적으로 내 모델에 속성을 추가하는 대신 람다 식을 쓸 수 있어야합니다. 이것이 가능한가?

답변

2

Windows Forms 데이터 바인딩은 ICustomTypeDescriptor 인터페이스를 인식하므로 개체가 데이터 바인딩에 대해 표시 할 속성을 런타임에 결정할 수 있습니다. 따라서 구현을 작성하면 Windows Forms에 어떤 속성이든 갖고 있다고 느끼고 구현 방법을 결정할 수 있습니다.

물론 도움이되지 않을 수도 있습니다. 속성을 추가하지 않으려면 상당히 복잡한 인터페이스를 구현하지 않는 것이 좋습니다. 분명한 해결책은 데이터 소스 역할을하는 유형의 작업을 작성하고 현재 바인딩중인 객체 대신 해당 작업에 바인드하는 것입니다.

물론 으로 만들면 대신 해당 래퍼에 구현하려는 모든 속성을 구현하는 것이 더 쉽습니다.

일반적으로 데이터 바인딩을 사용하면 UI의 이점을 위해 모델에 항목을 추가 할 필요가 없으므로 일부 기본 모델에 직접 바인딩하지 않아도됩니다. 이것이 '분리 된 프리젠 테이션'이 인기있는 이유입니다. 모델과 뷰를 직접 연결하는 대신 중간에 중재 할 작업이 있습니다. 일부는이를 뷰 모델이라고 부르며 일부는 발표자라고 부릅니다. 그러나 기본 원칙은 항상 표현의 분리입니다.

프레젠테이션을 별도로 구현하는 것처럼 보이지만 추가 유형을 도입하지 않아도이 중간 계층이 어딘가에 있어야합니다. 왜 그 계층으로 동작 할 클래스 (또는 클래스 집합)를 정의하지 않는 것이 좋을까요?

4

예, Binding 클래스의 Format 이벤트를 사용하여이 작업을 수행 할 수 있습니다. 문제의 속성에는 여전히 바인딩되지만 Format 이벤트 핸들러는 다른 값 (이 경우 bool)을 반환합니다.

var binding = new Binding("Visible", model, "Name"); 
binding.Format += (sender, args) => args.Value = (string)args.Value != "Default"; 
label.DataBindings.Add(binding); 
+0

완벽하게 작동합니다. 이 작업을 수행하기 위해 작은 라이브러리를 작성하는 것에 대해 생각하고 있었지만이 코드를 메소드에 넣는 것은 필요한 것입니다. 감사! –