代码改变世界

Silverlight中使用DomainDataSource模拟Duplex通信

2012-11-28 13:11  java20130722  阅读(146)  评论(0编辑  收藏  举报

为了更清楚的做演示,我们将模拟一个场景,可以想象Guard和Officer是silverlight的不同client。在Guard中提交一个请求,然后由Officer批准。然后Guard知道Officer已经批准后再做下一步的操作。

这里就不再介绍如何创建Entity Model以及Domain Service Class了。如果有需要,可以移步到: http://blog.csdn.net/kiwi_coder/article/details/8158389

本文github:https://github.com/kiwiwin/silverlight-demo,文件夹:domain-service-duplex-by-auto-refresh-demo

 

 

1.定义界面和DomainDataSource

其中id是primary key

MainPage.xaml

<Grid x:Name="LayoutRoot" Background="White">
        <sdk:DataGrid ItemsSource="{Binding Data, ElementName=guardDataSource}" AutoGenerateColumns="True" Height="184" HorizontalAlignment="Left" Margin="12,54,0,0" Name="guardDataGrid" VerticalAlignment="Top" Width="164" />
        <sdk:Label Content="Guard" Height="28" HorizontalAlignment="Center" Margin="29,20,251,0" VerticalAlignment="Top" Width="120" />
        <sdk:DataGrid ItemsSource="{Binding Data, ElementName=officerDataSource}" Name="officerDataGrid"
                      AutoGenerateColumns="False"  Height="184" HorizontalAlignment="Left" Margin="208,54,0,0" VerticalAlignment="Top" Width="164">
            <sdk:DataGrid.Columns>
                <sdk:DataGridTextColumn Binding="{Binding name}" Header="name"/>
                <sdk:DataGridTextColumn Binding="{Binding status}" Header="status"/>
                <sdk:DataGridTemplateColumn Header="Accept">
                    <sdk:DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            <Button Content="Accept" Click="AcceptButton_OnClick"/>
                        </DataTemplate>
                    </sdk:DataGridTemplateColumn.CellTemplate>
                </sdk:DataGridTemplateColumn>
            </sdk:DataGrid.Columns>
        </sdk:DataGrid>
        <sdk:Label Content="Officer" Height="28" HorizontalAlignment="Center" Margin="227,20,53,0" VerticalAlignment="Top" Width="120" />
        <TextBox Height="28" HorizontalAlignment="Left" Margin="12,244,0,0" Name="nameTextBox" VerticalAlignment="Top" Width="120" />
        <Button Content="Add" Height="28" HorizontalAlignment="Left" Margin="138,244,0,0" Name="addButton" VerticalAlignment="Top" Width="38" Click="addButton_Click" />
        <riaControls:DomainDataSource Name="guardDataSource" AutoLoad="True" LoadSize="10" QueryName="GetRegisters">
            <riaControls:DomainDataSource.DomainContext>
                <server:RegisterDomainContext/>
            </riaControls:DomainDataSource.DomainContext>
        </riaControls:DomainDataSource>
        <riaControls:DomainDataSource Name="officerDataSource" AutoLoad="True" LoadSize="10" QueryName="GetRegisters">
            <riaControls:DomainDataSource.DomainContext>
                <server:RegisterDomainContext/>
            </riaControls:DomainDataSource.DomainContext>
        </riaControls:DomainDataSource>
    </Grid>

 

MainPage.xaml的AddButton Click事件:

       private void addButton_Click(object sender, RoutedEventArgs e)
        {
            Register register = new Register {name = nameTextBox.Text, status = "Wait"};
            RegisterDomainContext context = guardDataSource.DomainContext as RegisterDomainContext;
            context.Registers.Add(register);
            guardDataSource.SubmitChanges();
        }

运行:

上图中,当点击Add按钮时,两个datagrid并没有更新,这是因为当两个domian data source load以后,变不会再自动load了。但是点击Add以后,数据已经被添加到入了数据库。

 

2.添加RefreshInterval

可以通过RefreshInterval设置时间间隔,让domain data source自动更新.

        public MainPage()
        {
            InitializeComponent();

            guardDataSource.RefreshInterval = TimeSpan.FromSeconds(5);
            officerDataSource.RefreshInterval = TimeSpan.FromSeconds(5);
        }

运行:

添加

点击Officer的Accept按钮

此时Officer的status变为Accpet,而Guard没有改变。这样的结果还是不符合我们的预期。

 

3.修改load behavior

造成上面Officer做了修改,Guard不能读出Officer的修改这个现象是因为guardDataSource所对应的domain context的load behavior的默认类型为Keep Current。所以,当我们在officerDataSource上做修改时,binding officerDataSource的datagrid能够知道,而guardDataSource对应的datagrid不会知道。

msdn上关于几种loadbehavior的介绍:

 

这个时候,可以给guardDataSource添加一个LoadingData的delegate,在这个delegate中修改load behavior。代码如下:

        private void GuardDataSource_OnLoadingData(object sender, LoadingDataEventArgs e)
        {
            e.LoadBehavior = LoadBehavior.MergeIntoCurrent;
        }

好,这样就ok了