C#Universal app无法加载

时间:2016-06-16 19:56:19

标签: c# xaml win-universal-app

我试图编写一款能够不断提高加密货币价格的应用程序。 CallAPI()函数从JSON格式的在线API获取价格,解析它,然后将其发送到应用程序前端的文本块。它在while循环中运行,并且之间有一个短暂的中断:

    public MainPage()
    {
        this.InitializeComponent();

        KrakenConnector KC = new KrakenConnector();

        while (true)
        {
            CallAPI(KC, 0);
            CallAPI(KC, 1);
            CallAPI(KC, 2);
            CallAPI(KC, 3);
            CallAPI(KC, 4);
            CallAPI(KC, 5);
            Task.Delay(1000).Wait();
        }
    }

我刚刚获得了Windows通用应用的默认启动画面,而且它没有进入实际应用。我怎样才能解决这个问题?为什么不进入应用程序?我不应该在CallAPI函数中设置文本块吗?

2 个答案:

答案 0 :(得分:0)

试试这个

private bool isLoaded = true;

public MainPage()
{
    this.InitializeComponent();
    this.WorkItAsync();
    this.Unloaded += (s, e) => this.isLoaded = false;
}

private async Task WorkItAsync()
{
    var KC = new KrakenConnector();

    while (this.isLoaded)
    {
        CallAPI(KC, 0);
        CallAPI(KC, 1);
        CallAPI(KC, 2);
        CallAPI(KC, 3);
        CallAPI(KC, 4);
        CallAPI(KC, 5);
        await Task.Delay(1000);
    }
}

答案 1 :(得分:0)

您的MainPage构造函数永远不会退出。此外,您在UI线程上进行了调用Task.Delay,这是禁忌。你应该在后台线程上做。

这是一个更好的方法的骨架:

public sealed partial class MainPage
{
    private bool running;

    public MainPage()
    {
        InitializeComponent();
    }

    protected override void OnNavigatedTo(NavigationEventArgs e)
    {
        running = true;

        // Start background thread
        Task.Run(
            async () =>
            {
                int counter = 0;
                while (running)
                {
                    // UI updates must happen on the UI thread;
                    // we use the Dispatcher for this:
                    await Dispatcher.RunAsync(
                        CoreDispatcherPriority.Normal,
                        () => test.Text = counter.ToString());
                    await Task.Delay(1000);
                    ++counter;
                }
            });
    }

    protected override void OnNavigatedFrom(NavigationEventArgs e)
    {
        running = false;
    }

相应的XAML:

<Page
    x:Class="App2.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">

    <StackPanel>
        <TextBlock
            x:Name="test"
            FontSize="24"
            HorizontalAlignment="Center"
            Margin="0,24,0,0" />
        <!-- The button doesn't do anything; it's just to show that the UI is live -->
        <Button
            Content="Hello, world!"
            HorizontalAlignment="Center"
            Margin="0,24,0,0" />
    </StackPanel>
</Page>

使用bool来控制循环有点简单;更好的方法是使用CancellationTokenSource,它还能够阻止Task.Delay在其轨道上死亡。这是另一个需要:

public sealed partial class MainPage
{
    private CancellationTokenSource cancellationTokenSource;

    public MainPage()
    {
        InitializeComponent();
    }

    protected override void OnNavigatedTo(NavigationEventArgs e)
    {
        cancellationTokenSource = new CancellationTokenSource();
        CancellationToken token = cancellationTokenSource.Token;

        // Start background thread
        Task.Run(
            async () =>
            {
                int counter = 0;
                while (true)
                {
                    if (token.IsCancellationRequested)
                    {
                        // Stop the loop; we're moving away from the page
                        break;
                    }

                    // UI updates must happen on the UI thread;
                    // we use the Dispatcher for this:
                    await Dispatcher.RunAsync(
                        CoreDispatcherPriority.Normal,
                        () => test.Text = counter.ToString());
                    await Task.Delay(1000, token);
                    ++counter;
                }
            });
    }

    protected override void OnNavigatedFrom(NavigationEventArgs e)
    {
        cancellationTokenSource?.Cancel();
    }
}