我已經被賦予創建兩個人的簡單Silverlight聊天框的任務。我的控制必須符合以下要求Silverlight Chat WrapPanel崩潰/錯誤
- 滾動,如果它太長
- 文本必須包裹
- 當添加一個新的項目/信息必須滾動該項目進入視野現在
我已經成功地完成了一個用戶控件來滿足這些要求,但是我遇到了一個可能的錯誤/崩潰,我無法修復我的生活。我正在尋找修復這個bug的方法,或者尋找一種創建可滾動聊天控件的方法。
這是我一直在使用的代碼。我們將從我的XAML開始聊天窗口
<ListBox x:Name="lbChatHistory" Grid.Row="0" Grid.Column="0" Grid.ColumnSpan="2" ScrollViewer.VerticalScrollBarVisibility="Visible" ScrollViewer.HorizontalScrollBarVisibility="Disabled" >
<ListBox.ItemTemplate>
<DataTemplate>
<Grid Background="Beige">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="70"></ColumnDefinition>
<ColumnDefinition Width="Auto"></ColumnDefinition>
</Grid.ColumnDefinitions>
<TextBlock x:Name="lblPlayer" Foreground="{Binding ForeColor}" Text="{Binding Player}" Grid.Column="0"></TextBlock>
<ContentPresenter Grid.Column="1" Width="200" Content="{Binding Message}" />
</Grid>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
這個想法是添加一個新項目到列表框中。該項目(如XAML中所示)是一個簡單的2列網格。一列用於用戶名,一列用於消息。
現在我添加到ListBox的「項目」是一個自定義類。它有三個我在XAML中使用綁定的屬性(Player,ForeColor和Message)
Player是要顯示的當前用戶的字符串。
ForeColor只是一個前景色偏好。它有助於區分消息之間的差異。
消息是WrapPanel。我編程打破提供的字符串的空白空間爲每個單詞。然後,每個字,我一個新的的TextBlock元素添加到WrapPanel
這是自定義類。
public class ChatMessage :DependencyObject, INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
public static DependencyProperty PlayerProperty = DependencyProperty.Register("Player", typeof(string), typeof(ChatMessage),
new PropertyMetadata(
new PropertyChangedCallback(OnPlayerPropertyChanged)));
public static DependencyProperty MessageProperty = DependencyProperty.Register("Message", typeof(WrapPanel), typeof(ChatMessage),
new PropertyMetadata(
new PropertyChangedCallback(OnMessagePropertyChanged)));
public static DependencyProperty ForeColorProperty = DependencyProperty.Register("ForeColor", typeof(SolidColorBrush), typeof(ChatMessage),
new PropertyMetadata(
new PropertyChangedCallback(OnForeColorPropertyChanged)));
private static void OnForeColorPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
ChatMessage c = d as ChatMessage;
c.ForeColor = (SolidColorBrush) e.NewValue;
}
public ChatMessage()
{
Message = new WrapPanel();
ForeColor = new SolidColorBrush(Colors.White);
}
private static void OnMessagePropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
ChatMessage c = d as ChatMessage;
c.Message = (WrapPanel) e.NewValue;
}
private static void OnPlayerPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
ChatMessage c = d as ChatMessage;
c.Player = e.NewValue.ToString();
}
public SolidColorBrush ForeColor
{
get { return (SolidColorBrush) GetValue(ForeColorProperty); }
set
{
SetValue(ForeColorProperty, value);
if(PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs("ForeColor"));
}
}
public string Player
{
get { return (string) GetValue(PlayerProperty); }
set
{
SetValue(PlayerProperty, value);
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs("Player"));
}
}
public WrapPanel Message
{
get { return (WrapPanel) GetValue(MessageProperty); }
set
{
SetValue(MessageProperty, value);
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs("Message"));
}
}
}
最後,我將我的項目添加到列表框中。這是簡單的方法。它需要上面的ChatMessage類作爲參數
public void AddChatItem(ChatMessage msg)
{
lbChatHistory.Items.Add(msg);
lbChatHistory.ScrollIntoView(msg);
}
現在我測試了這一切,它的一切工作。我得到的問題是當我使用滾動條。您可以使用側滾動條或箭頭鍵向下滾動,但是當您向上滾動Silverlight崩潰時。 FireBug返回ManagedRuntimeError#4004與XamlParseException。
我很接近有這個控制工作,我可以品嚐它!關於我應該做什麼或改變什麼的想法?有沒有比我採取的更好的方法?
在此先感謝。
UPDATE
我發現使用的ScrollViewer和一個ItemsControl代替列表框控件的替代解決方案。大多數情況下它很穩定。