2013-07-16 2 views
3

Прошло несколько дней, когда я придерживаюсь одной и той же проблемы, поэтому я, наконец, приступаю к сообществу. Я постараюсь сделать его максимально ясным.Добавить программно UIElement к представлению асинхронным способом

На самом деле я пытаюсь добавить асинхронный способ UIElement на мой холст. Определите в моем MainPage.

Как я понимаю, основной способ добавить UIElement к Canvas, чтобы добавить его на UIElementCollection, например, с помощью линии я должен делать так:

 Line line = new Line(); 

     // Line attributes 
     line.Stroke = new SolidColorBrush(Colors.Purple); 
     line.StrokeThickness = 15; 
     Point point1 = new Point(); 
     point1.X = 0; 
     point1.Y = 0; 
     Point point2 = new Point(); 
     point2.X = 480; 
     point2.Y = 720; 
     line.X1 = point1.X; 
     line.Y1 = point1.Y; 
     line.X2 = point2.X; 
     line.Y2 = point2.Y; 
     // Line attributes 

     MyCanvas.Children.Add(line); 

Давайте представим, что у меня есть вызов класса Графика, которая должна получить доступ к этому холсту, чтобы рисовать на нем.

public class Graphics 
{ 
    public void drawLine() 
    { 
      //Using Dispatcher in order to access the main UI thread 
      Deployment.Current.Dispatcher.BeginInvoke(() => 
      { 
       Line line = new Line(); 

       // Line attributes 

       /** 
       * Here I want to acces the Canvas of the MainPage 
       * I have no Idea what to put here !!! 
       * 
       **/ 

      }); 
     } 
    } 

В местечке «У меня нет идеи, что здесь поставить !!!» Я попытался получить доступ непосредственно к MainPage Canvas -> FAIL

Я попытался объявить публичный статический UIElementCollection в MainPage, чтобы та добавить свой UIElement затем передать его на холст, но не представляется возможным, потому что UIElementCollection имеет no constructor -> FAIL

Но эти идеи, похоже, грязные и не очень элегантные. Поэтому в ходе моих исследований я вижу, что MVVM должен делать магию. Но все учебники, которые я нашел, делали данные, ожидающие прохождения через файл xaml, который не может быть использован в моем случае.

Так что у меня 2 вопроса:

Первый: Как использовать UIElementCollection холста? (Есть скрытый метод, называемый, который рисует его, как Paint или Перекрасить в JAVA?)

Во-вторых: Если я хочу следовать шаблону MVVM можно рассматривать MainPage как мой взгляд, Графика класса, как мой ViewModel и UIElement как моя модель?

Заранее благодарю вас за помощь и не стесняйтесь сказать мне, если какая-то часть недостаточно ясна.

Yann

ответ

1

Это действительно простой пример, но вы должны получить идти в правильном направлении.

Graphics.cs

public class Graphics 
{ 
    public ObservableCollection<UIElement> UIElements { get; set; } 
    int poisiton = 0; 
    private Timer backgroundTimer; 
    public Graphics() 
    { 
     this.UIElements = new ObservableCollection<UIElement>(); 
     this.backgroundTimer = new Timer(new TimerCallback((timer) => { 
      Deployment.Current.Dispatcher.BeginInvoke(() => this.GenerateLine()); 
     }), null, 2000, 3000); 
    } 

    private void GenerateLine() 
    { 
     Line line = new Line(); 

     // Line attributes 
     line.Stroke = new SolidColorBrush(Colors.Purple); 
     line.StrokeThickness = 15; 
     Point point1 = new Point(); 
     point1.X = this.poisiton; 
     point1.Y = this.poisiton; 
     Point point2 = new Point(); 
     point2.X = this.poisiton; 
     point2.Y = this.poisiton + 30; 
     line.X1 = point1.X; 
     line.Y1 = point1.Y; 
     line.X2 = point2.X; 
     line.Y2 = point2.Y; 
     // Line attributes 

     this.poisiton += 10; 
     UIElements.Add(line); 
    } 
} 

MainPage.xaml.cs

public MainPage() 
{ 
     InitializeComponent(); 

     this.Loaded += MainPage_Loaded; 
     // Sample code to localize the ApplicationBar 
     //BuildLocalizedApplicationBar(); 
} 

    void MainPage_Loaded(object sender, RoutedEventArgs e) 
    { 
     var graphics = new Graphics(); 
     this.ContentPanel.DataContext = graphics; 
    } 

MainPage.xaml

<Canvas x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0"> 
     <ItemsControl ItemsSource="{Binding UIElements}"> 

     </ItemsControl> 
    </Canvas> 

Я надеюсь, что это помогает.

+0

Огромное спасибо за вашу помощь! У вас есть идея, как сделать это асинхронно? Потому что в этом случае я могу сделать это только в конструкторе. – Yann

+0

Можете ли вы дать мне дополнительную информацию о том, как вы хотите, чтобы она была асинхронной? Что вызывает добавление элемента? etc – Blounty

+0

Давайте скажем, что работает другой поток. Этот поток может захотеть использовать GenerateLines(), в этом случае некоторый объект Line будет добавлен в коллекцию наблюдаемых UIElements. Я хотел бы сделать что-то вроде шаблона MVVM. Это означает, что я хотел бы, чтобы событие было увеличено, чтобы добавить эту строку на экране, но, к сожалению, класс UIElement не реализует INotifyProperty, поэтому я не знаю, как поднять это событие, и я не знаю, как сделать мой MainPage прослушивает эти события, чтобы перекрасить. Спасибо за помощь и ваше время! – Yann