Windows phone 8 覆盖WP8导航-PhoneApplicationPage中的崩溃

Windows phone 8 覆盖WP8导航-PhoneApplicationPage中的崩溃,windows-phone-8,windows-phone,Windows Phone 8,Windows Phone,我正试图做一些可以说是个坏主意的事情,但我认为这仍然是可能的。我试图覆盖WP8处理后退按钮的方式,并自己实现它。我认为如果我: 计划 只能在整个应用程序中创建一个“框架”和“页面” 始终处理PhoneApplicationPage。按BackKeyPress本人,除非他们即将退出应用程序 复制品 代码 …那么它应该会起作用。然而,我的尝试被Windows Phone阻止了 发现了问题。嗯,冰山一角 InternalOnNavigatedFrom方法的代码为: internal override

我正试图做一些可以说是个坏主意的事情,但我认为这仍然是可能的。我试图覆盖WP8处理后退按钮的方式,并自己实现它。我认为如果我:

计划
  • 只能在整个应用程序中创建一个“框架”和“页面”
  • 始终处理
    PhoneApplicationPage。按BackKeyPress
    本人,除非他们即将退出应用程序
  • 复制品

    代码 …那么它应该会起作用。然而,我的尝试被Windows Phone阻止了


    发现了问题。嗯,冰山一角

    InternalOnNavigatedFrom方法的代码为:

    internal override void InternalOnNavigatedFrom(NavigationEventArgs e)
    {
        PhoneApplicationPage content = e.Content as PhoneApplicationPage;
        string str = ((content == null) || (content.Title == null)) ? string.Empty : content.Title;
        PerfUtil.BeginLogMarker(MarkerEvents.TH_ONNAVIGATEDFROM_PAGE, string.Format("{0},{1},{2}", (base.Title == null) ? "" : base.Title, e.NavigationMode, str));
        this.OnNavigatedFrom(e);
        PerfUtil.EndLogMarker(MarkerEvents.TH_ONNAVIGATEDFROM_PAGE, string.Format("{0},{1},{2}", (base.Title == null) ? "" : base.Title, e.NavigationMode, str));
        DeviceStatus.KeyboardDeployedChanged -= new EventHandler(this.OnKeyboardDeployedChanged);
        Task rootTask = ApplicationHost.Current.RootTask;
        rootTask.OnVisibleRegionChange = (ITask.VisibleRegionChanged) Delegate.Remove(rootTask.OnVisibleRegionChange, new ITask.VisibleRegionChanged(this.OnVisibleRegionChange));
        Task task2 = ApplicationHost.Current.RootTask;
        task2.OnSipVisibilityChange = (ITask.SipVisibilityChange) Delegate.Remove(task2.OnSipVisibilityChange, new ITask.SipVisibilityChange(this.OnSipVisibilityChange));
        this._lastSipHeight = 0.0;
        this._dictionary = null;
    }
    
    经过一点调试后,我得出结论,
    e
    Application.Current.RootTask
    都不是空的。挠头之后,我看了看
    KeyboardDeployedChanged
    事件处理程序的代码:

    public static  event EventHandler KeyboardDeployedChanged
    {
        [SecuritySafeCritical] add
        {
            if (KeyboardDeployedSubscription == null)
            {
                KeyboardDeployedSubscription = new SubscriptionHandler(DeviceTypes.KeyBoard);
            }
            KeyboardDeployedSubscription.Changed += value;
        }
        [SecuritySafeCritical] remove
        {
            KeyboardDeployedSubscription.Changed -= value;
        }
    }
    
    这段代码写得很差。如果在
    add
    之前调用处理程序的
    remove
    部分,
    KeyboardDeployedSubscription
    将为空,并引发异常。为了验证我的理论,我在
    应用程序的构造函数中订阅了该事件:

        public App()
        {
            // Global handler for uncaught exceptions.
            UnhandledException += Application_UnhandledException;
    
            DeviceStatus.KeyboardDeployedChanged += (sender, e) => { };
    
    果然,例外情况消失了。现在,为了理解为什么您的代码会触发这个问题,我回溯到框架的哪个部分应该订阅这个事件。唯一的候选方法是
    InternalOnNavigatedTo
    方法


    因此,您的问题是调用了
    OnNavigatedFrom
    ,尽管从未调用过
    OnNavigatedTo

    由于您正在使用Windows Phone内置的自动导航功能,无法将其导航到WMAppManifest.xml中定义的页面,因此我尝试删除自动导航功能,它基本上起到了作用(没有例外)

    我刚换了

    <DefaultTask Name="_default" NavigationPage="MainPage.xaml" />
    
    
    

    
    

    不确定这是否解决了您的问题,但它至少不再崩溃。

    所以,我解决了这个问题-我的代码有问题,因为我没有研究WP8是如何工作的:)以下是我现在理解的,这可能也是错误的,但我还是要写它

    如何初始化WP8应用程序:
  • 操作系统通过重新水合App.xaml.cs创建应用程序类
  • 这意味着您的构造函数将运行,并且作为其中的一部分,您将创建一个
    PhoneApplicationFrame
  • 创建
    PhoneApplicationFrame
    似乎还设置了一个全局静态变量(在App.xaml中创建
    PhoneApplicationService
    也会发生同样的情况,它设置
    PhoneApplicationService.Current
  • NavigationService
    然后尝试通过资源字符串(即
    “/MainPage.XAML”
    )重新创建XAML视图。它将重新创建以前被删除的部分,如果不是,则默认为WMAppManifest中的部分(这是我不理解的部分)
  • PhoneApplicationFrame.Navigated
    被NavigationService调用-您可以在这里开始实际操作,最重要的是,设置Application.RootVisual,它将发送加载。。。屏蔽
  • PhoneApplicationService.launted
    PhoneApplicationService.Activated
    一旦基本上一切都设置好,最终启动,具体取决于应用程序的唤醒方式

  • 这可能与以下事实有关吗?这是一个“硬件”按钮,事件正在从手机操作系统过渡到应用程序,因此手机操作系统将在收到通知之前做任何它想做的事情…@AwkwardCoder这可能是真的-我在初始化时搞砸了一些事情,但我很难弄清楚它是什么
        public App()
        {
            // Global handler for uncaught exceptions.
            UnhandledException += Application_UnhandledException;
    
            DeviceStatus.KeyboardDeployedChanged += (sender, e) => { };
    
    <DefaultTask Name="_default" NavigationPage="MainPage.xaml" />
    
    <DefaultTask Name="_default" />