【问题标题】:UWP updating current window from backgroundUWP 从后台更新当前窗口
【发布时间】:2020-07-20 05:05:46
【问题描述】:

我正在将应用程序从 WinRT 移植到 UWP。 (我已经移植到 iOS 和 Android)

我的应用有多个页面。我需要能够确定当前查看的是哪个页面,然后更新内容。 (由于各种原因,DataBinding 不是一个选项。)

我有一个在后台运行的例程(不是在 UI 线程上),从调度计时器调用。

在WinRT中,我是这样处理的:

            // If current window is MainPage, then update the displayed fields 
        var _Frame = Window.Current.Content as Frame;
        Page _Page = _Frame.Content as Page;
        if (_Page is MainPage)
        {
            MainPage _XPage = _Frame.Content as MainPage;
            _XPage.SetFieldsTick(spoton);
        }

由于 UWP 为 Windows.Current.Content 返回 null,因此我在 Navigation 例程中设置了标志以跟踪当前视图。我想正确地解决这个问题。

下一步是如何实际更改字段。

我在 XAML 代码后面有一个设置字段的例程

        public void SetFieldsTick(bool spot)
    {
        UTC_Data.Text = Vars.DateStrZ;
    }

如果我想从我的后台例程中引用它,那么例程必须是静态的。如果我进行此更改,则例程无法引用页面上的字段,因为它们不是静态的。

我知道这可能很明显,但我很难过。

提前致谢。

【问题讨论】:

  • 你的后台例程中能否成功获取当前页面?另外,您提到要在后台例程中调用SetFieldsTick方法,当您在例程中获取MainPage实例时,可以直接调用_XPage.SetFieldsTick,为什么一定要将SetFieldsTick方法设为静态?你能提供更多关于这些的细节吗?
  • 当我运行程序时,行“var _Frame = Window.Current.Content as Frame;”引发异常:“Window.Current.Content = 'Window.Current.Content' 引发了类型为 'System.NullReferenceException' 的异常”
  • SetFieldsTick 在页面加载和工作正常时被调用,当从类中调用时。在后台例程中,由于_XPage 未初始化,我将其称为“Home_Page.SetFieldsTick(true);”我收到编译错误“非静态字段、方法或属性需要对象引用。”如果我将例程设为静态,我会收到相同的编译错误,但这次是页面中的每个字段引用.
  • 我尝试向 Home_Page 添加一个计时器,但是当它尝试调用 SetFieldsTick 时,我收到一条消息“UTC_Data.Text = 'UTC_Data.Text' 引发了 'System.Exception' 类型的异常”( UTC_Data 是我要更新的第一个字段)那么,如何在不使用数据绑定的情况下从后台更新当前视图?
  • 当我尝试测试时,我没有收到这些异常。你能提供一个简单的样本,可以复制给我们测试吗?会更有帮助。

标签: xaml view uwp winrt-xaml updating


【解决方案1】:

您使用的Timer 将提供一种机制,用于以指定的时间间隔在线程池线程上执行方法。它在单独的线程上运行。因此,如果您想处理应用程序的 UI,它需要在 UI 的调度程序线程上运行。在这种情况下,您可以使用Dispatcher.RunAsync 方法在 UI 线程上进行回调。例如:

App.xaml.cs:

public void StartTimer() 
{ 
    DateTime startTime; 
    startTime = DateTime.UtcNow; 
    var dispatcherTimer = new System.Threading.Timer(DispatcherTimer_Tick, startTime, 0, 1000); 
}

private async void DispatcherTimer_Tick(object state)
{
    await CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
    {
        var _Frame = Window.Current.Content as Frame;
        Page _Page = _Frame.Content as Page;
        if (_Page is MainPage)
        {
            MainPage _XPage = _Frame.Content as MainPage;
            _XPage.SetFieldsTick(true);
        }
    });
}

另外,推荐使用DispatcherTimer,它可以用来在产生UI线程的同一线程上运行代码。在这种情况下,您不需要在 UI 线程上进行回调。

public void StartTimer() 
{ 
    var dispatcherTimer = new DispatcherTimer();
    dispatcherTimer.Tick += dispatcherTimer_Tick;
    dispatcherTimer.Interval = new TimeSpan(0, 0, 1);
    dispatcherTimer.Start();
}

private void dispatcherTimer_Tick(object sender, object e)
{
    var _Frame = Window.Current.Content as Frame;
    Page _Page = _Frame.Content as Page;
    if (_Page is MainPage)
    {
        MainPage _XPage = _Frame.Content as MainPage;
        _XPage.SetFieldsTick(true);
    }
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-11-22
    • 1970-01-01
    • 2011-12-02
    • 1970-01-01
    • 2018-06-29
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多