bingding学习

一、简介

wpf的核心理念是变传统的ui驱动数据变成数据驱动ui,支撑这个理念的基础就是本章讲的data binding和与之相关的数据校验和数据转换。在使用binding的时候,最重要的就是设置它的源和路径。
bingding的源
有三个属性用来设置源:elementname(string)、source(object) 和 relativesource(relativesource)。注:这三个只能指定一个,否则异常。
elementname:源为一个元素(element),这里用的是此元素中设置的name属性。
source:以object作为源。<textblock text=”{binding source={staticresource mydatasource}, path=personname}”/>
relativesource:源相对于绑定目标的位置。
源是元素本身:{binding relativesource={relativesource self}};
源是tempalte中元素的parent:{binding relativesource={relativesource templatedparent}};
源是绑定以collection形式的前一个数据:{binding relativesource={relativesource previousdata}},msdn上关于previousdata的说明并不多。
以上三项为relativesource中的static值,使用这些值可以减少内存开销。
源是ancestor(可能比parent还高):{binding relativesource={relativesource findancestor,ancestorlevel=n, ancestortype={x:type desiredtype}}}

bingding的path:
binding中的path是 propertypath对象。
在最简单的情况下,path 属性值是要用于绑定的源对象的属性名称,如 path=propertyname。
通过类似于c#中使用的语法,可以指定属性的子属性。例如,子句 path=shoppingcart.order 将绑定设置为对象的子属性 order 或属性 shoppingcart。
若要绑定到附加属性,请将附加属性用括号括起。例如,若要绑定到附加属性 dockpanel.dock,则语法为 path=(dockpanel.dock)。
在应用了索引器的属性名称之后的方括号内,可以指定属性的索引器。例如,子句 path=shoppingcart[0] 将绑定设置为与属性的内部索引处理文本字符串“0”的方式对应的索引。此外,还支持多个索引器。
在 path 子句中可以同时使用索引器和子属性,例如,path=shoppingcart.shippinginfo[mailingaddress,street]。
在索引器内部,可以有多个由逗号(,) 分隔的索引器参数。可以使用圆括号指定每个参数的类型。例如,可以使用 path=”[(sys:int32)42,(sys:int32)24]”,其中 sys 映射到 system 命名空间。
如果源为集合视图,则可以用斜杠(/) 指定当前项。例如,子句 path=/ 设置到视图中当前项的绑定。如果源为集合,则此语法指定默认集合视图的当前项。
可以结合使用属性名和斜杠来遍历作为集合的属性。例如,path=/offices/managername 指定源集合的当前项,该源集合包含同样是集合的 offices 属性。其当前项是包含 managername 属性的对象。
也可以使用句点(.)路径绑定到当前源。例如,text=”{binding}” 等效于 text=”{binding path=.}”。

二、案例

案例一:

grid代码:

   <grid>
        <!--行-->
        <grid.rowdefinitions>
            <rowdefinition height="200" />
            <rowdefinition height="200"/>
            <rowdefinition height="*"/>
        </grid.rowdefinitions>

        <!--列-->
        <grid.columndefinitions>
            <columndefinition width="200" />
            <columndefinition width="200" />
            <columndefinition width="*" />
        </grid.columndefinitions>

        <!--设置在grid中布局位置-->
        <!--将mainwindow分为3x3的布局,则位于中间(1,1)位置,个人理解相当于坐标。-->
        <stackpanel  grid.row="1" grid.column="1">
            <textblock width="250" height="30" text="颜色:" textwrapping="wrap"  background="azure" fontsize="20"/>
            <listbox x:name="listcolor" width="200" height="90"  background="azure"  fontsize="20">
                <listboxitem content="blue"/>
                <listboxitem content="red"/>
                <listboxitem content="green"/>
                <listboxitem content="gray"/>
                <listboxitem content="cyan"/>
                <listboxitem content="greenyellow"/>
                <listboxitem content="orange"/>
            </listbox>
            <textblock width="200" height="30" textwrapping="wrap"  fontsize="20" margin="3,1,2,1"   background="azure" text="改变背景色:" />
            <!--绑定选择值-->
            <textblock width="200" height="30" text="{binding elementname=listcolor, path=selecteditem.content, mode=oneway}"  background="{binding elementname=listcolor, path=selecteditem.content, mode=oneway}">
            </textblock>
            <textbox name="txttwoway" text="{binding elementname=listcolor,path=selecteditem.content,mode=twoway}"  background="{binding elementname=listcolor,  path=selecteditem.content,mode=twoway}" >
            </textbox>
        </stackpanel>
    </grid>

执行效果:

案例二:

grid代码:

<grid>
        <stackpanel>
            <textblock text="{binding elementname=slider,path=value}"/>
            <slider x:name="slider" maximum="100" minimum="1"/>
        </stackpanel>
 </grid> 

执行效果:

三、总结

在上例子中绑定数据源时候用到了mode属性,通过查阅资料得知有以下区别:
onetime:一次性绑定,将数据给控件,绑定就结束。
oneway:数据源改变会影响绑定该数据源的控件。
twoway:数据源改变会影响绑定该数据源的控件,并且控件中数据改变时也会影响到数据源。