アプリケーションに特別なナビゲーションがあり、どうすれば適切に設定できるのでしょうか。
アクティビティHは、アプリケーションのホーム画面です。このアクティビティから、アクティビティA、B、C、およびDを起動できます。アクティビティAから、A''を起動するA'を起動でき、アクティビティBから、B'、B''を起動するA'を起動できます。
問題は、どのアクティビティからでも、アクティビティH、A、B、C、またはDに移動できることです。ただし、ユーザーがA-> A'-> A''-> Cを起動してから、Aに戻ると、彼はA''にリダイレクトする必要があります。さらに、この例でも、ユーザーがA''を押し戻すと、CではなくA'にリダイレクトされる必要があります。もう一度押すと、Aにリダイレクトされる必要があり、もう一度押すと、にリダイレクトされます。 CではなくH(ホーム画面)アクティビティ!
最後に、ユーザーがHから押し戻すと、この時点でのみ、アプリケーション(および、ソリューションが個別のタスクを作成することを選択した場合はすべてのタスク)をシャットダウンする必要があります。
その他の例:H-> A->B->H->戻る->アプリケーションの終了
どうすればこれを達成できますか?私はそのようなタスクを使用することを考えました:
<!-- 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"です。しかし、今、別の問題があります。ユーザーがホームボタンをクリックしてアプリケーションに戻ると、最後に起動したアクティビティではなく、ホーム画面に戻ります...
さらに、私の2番目の例は尊重されていません。
これらすべての問題を解決するためのアイデアはありますか?
PS:ナビゲーションシステムを変更するように言わないでください:-)
編集:ここでは、必要なバックコンポートメントを表すフローチャートを示します。この状況は正常なようです。私の場合の違いは、このチャートには表示されていません。実際、戻るボタンのみが表示されます。異なる色で表される各コンテキストは、ここで説明するバックコンポートメントをオーバーライドすることなく、別のコンテキストに切り替えることができます。
EDIT2:David Wasserのアドバイスのおかげで、Androidタスクを使用せずに、説明した機能を正確に実行する2つのクラスを実装しました。JoxTraexの助けにも感謝します:-)ここで私がしたこと:私のアクティビティA、B、C、DはRootActivityを拡張し、Hを除く他のアクティビティはCustomNavigationActivityを拡張します。
RootActivity:
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);
}
}
CustomNavigationActivity:
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");
}
}
}