【问题标题】:How to configure manifest file for my custom navigation (task relevance ?)如何为我的自定义导航配置清单文件(任务相关性?)
【发布时间】:2012-08-23 18:57:43
【问题描述】:

我的应用程序中有一个特殊的导航,我想知道如何正确设置它。

Activity H 是我的应用程序的主屏幕。从这个活动中,我们可以启动活动 A、B、C 和 D。从活动 A 我们可以启动 A',然后启动 A'',从活动 B 我们可以启动 B',启动 B'',等等。

问题是,从任何活动,我们可以去活动H,A,B,C或D。但是,当用户启动A->A'->A''->C,然后去回到A,他必须被重定向到A''。此外,在这个例子中,如果用户按回 A'',他必须被重定向到 A' 而不是 C。如果他再次按回,他必须被重定向到 A,并且再次返回应该将他重定向到H(主屏幕)活动,而不是 C !

最后,当用户从 H 按下返回时,并且仅在此时,应用程序(以及所有任务,如果选择的解决方案是创建分离的任务)应该关闭。

其他示例:H -> A -> B -> H -> back -> 应用程序结束

我怎样才能做到这一点? 我曾想过使用这样的任务:

<!-- A-->
<activity
    android:name=".A"
    android:excludeFromRecents="true"
    android:taskAffinity=".A"
    android:label="@string/my_A_label">
</activity>
<activity
    android:name=".A'"
    android:taskAffinity=".A"
    android:label="@string/my_A'_label">
</activity>
<activity
    android:name=".A''"
    android:taskAffinity=".A"
    android:label="@string/my_A''_label">
</activity>


<!-- B-->
<activity
    android:name=".B"
    android:excludeFromRecents="true"
    android:taskAffinity=".B"
    android:label="@string/my_B_label">
</activity>
<activity
    android:name=".B'"
    android:taskAffinity=".B"
    android:label="@string/my_B'_label">
</activity>
<activity
    android:name=".B''"
    android:taskAffinity=".B"
    android:label="@string/my_B''_label">
</activity>

...

如您所见,我为每个主页创建了任务:A、B、C、D。 我不知道这是否是一件好事,因为例如,对于任务,用户可以通过“最后一个任务”选项长按他的主页按钮来查看所有这些活动,而我不想要这个行为。为此,活动 A、B、C、D(每个任务的根屏幕)具有属性 android:excludeFromRecents="true"。但是现在,另一个问题:当用户点击他的主页按钮并返回我的应用程序时,他会返回主屏幕,而不是最后一个启动的活动......

而且,我的第二个例子没有得到尊重。

你有解决所有这些问题的想法吗?

P.S : 请不要告诉我改变我的导航系统:-)

编辑:这里有一个流程图,代表了所需的后台。这种行为似乎很正常。我的情况有什么不同没有出现在这个图表上。实际上,仅表示后退按钮。每个上下文 - 由不同的颜色表示 - 可以切换到另一个上下文,而无需覆盖此处描述的后退声明。

EDIT2:感谢 David Wasser 的建议,我已经实现了两个类,它们完全符合我所描述的行为,而不使用 android 任务。也感谢 JoxTraex 的帮助 :-) 这是我所做的:我的活动 A、B、C、D 扩展了 RootActivity,除 H 之外的其他活动扩展了 CustomNavigationActivity。

根活动:

import android.content.Intent;

public abstract class RootActivity extends CustomNavigationActivity{

@Override
public void onBackPressed(){

    Intent intent = new Intent(this, HomeScreen.class);
    intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
    startActivity(intent);

}

}

自定义导航活动:

import android.content.Intent;

public abstract class CustomNavigationActivity extends Activity{

private int actualRequestCode;
private int menuRequestCode = -1;

@Override
protected void onResume(){

    if (getIntent().hasExtra("childLaunched")){

        Intent intent = new Intent(this, (Class<?>) getIntent().getExtras().get("childLaunched"));
        intent.addFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
        startActivity(intent);

    }

    super.onResume();       

}

@Override
public void startActivity (Intent intent) {

    this.startActivityForResult(intent, 0);

}

@Override
public void startActivityForResult(Intent intent, int requestCode){

    Class<?> targetClass = null;
    this.actualRequestCode = requestCode;

    if (this.actualRequestCode == this.menuRequestCode){
        this.menuRequestCode -= 1;
    }

    try {
        if (intent.getComponent() != null){
            targetClass = Class.forName(intent.getComponent().getClassName());
        }
    }
    catch (ClassNotFoundException e) {
        e.printStackTrace();
    }

    if (targetClass == null){
        super.startActivityForResult(intent, this.actualRequestCode);
    }
    else if (!targetClass.equals(Menu.class)){
        getIntent().putExtra("childLaunched", targetClass);
        super.startActivityForResult(intent, this.actualRequestCode);
    }
    else{
        super.startActivityForResult(intent, this.menuRequestCode);     
    }

}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data){

    if (requestCode == this.actualRequestCode){
        getIntent().removeExtra("childLaunched");
    }

}

}

【问题讨论】:

  • 好吧,我不明白为什么您不能在 H 处创建您的应用程序的唯一入口。每当应用程序启动时,它总是在 H 处。让 home 的要求始终是 root解决了。但是,您能解释一下您的数据和这种流程的原因吗?也许有更好的方法。例如,在识别状态的意图中使用动作。还可以根据需要使用附加功能来更改内容,从而无需进行多项活动。您也可以更改活动布局......这么多不同的选项。有一种方法可以处理它..所以探索效率。 @塞巴斯蒂安

标签: android navigation android-manifest task


【解决方案1】:

您肯定希望为此执行不同的任务。如果用户离开应用程序(按 HOME、接听电话等)并想回来,它将完全打乱您的导航。如果每个任务的根目录中的活动都有唯一的图标和/或名称,并且这些任务都可以并行运行,则只能使用单独的任务。只有这样,您才不会混淆用户。看来你不想要了。

看看我对Activities Stack Issue的回答

这不是您想要的,但您可能会从这个答案中得到一些想法。如果您在查看此内容后仍有疑问,请添加 cmets,我可以为您提供更多帮助。

【讨论】:

    【解决方案2】:

    不要以这种方式控制它。只需使用 Intents 的控制,它就更直接了。通过这种方式,您可以防止那些可能出现故障的悬空活动。

    在标记您的活动时,请勿使用 ACTION_MAIN 标记所有活动

    请参阅文档以找出原因。

    A -> B -> C
    
    A -> B
    
    Intent intent = new Intent((context), MyClassB.class);
    
    B -> C
    
    Intent intent = new Intent((context), MyClassC.class);
    
    C -> A
    
    Intent intent = new Intent((context), MyClassA.class);
    

    但要正确处理此问题,您必须清楚地了解您希望流程如何。流程图可能会使您受益或解释您当前的问题。如果我可以说,您当前的实施/流程是一团糟。我建议使用上述流程图来清理这个想法。

    此外,如果您只希望 ONE Activity 成为您的主根,那么您的 Main Activity 应该具有 ACTION_MAIN 的 IntentFilter,其他应该 NOT

    【讨论】:

    • 你能给我一些示例代码吗?我不知道如何使用 startActivity() 和 startActivityForResult() 来实现。对我来说,不管理每个案例是不可能的(这很丑,不是吗?)此外,目前,我从未在我的活动 H(主屏幕)的其他活动中使用 ACTION_MAIN 标签。
    • 它不是一个标签,它是一个intentFilter。 @塞巴斯蒂安
    • 是的,当然,我的错误。我从未将意图过滤器用于我的家庭活动 (H) 的其他活动(使用 CATEGORY_LAUNCHER 和 ACTION_MAIN 的意图过滤器)。
    • 那么每次启动应用程序时,H 都应该是应用程序的根目录。那你的具体问题是什么? @Sebastien 请创建您的应用程序的流程图并HIGHLIGHT问题区域。
    • 刚刚用图表编辑过。我希望你能更好地理解我的问题:-) @JoxTraex
    【解决方案3】:

    您可以通过以下方式提示该活动运行另一个活动 startActivity(new Intent(MainActivity.this, MenuActivity.class));

    【讨论】:

    • 我不明白这个经典的活动启动将如何解决我的问题。
    猜你喜欢
    • 2016-08-13
    • 2021-11-06
    • 2013-05-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-10-03
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多