2017-01-27 9 views
0

У меня есть приложение Xamarin для Android, и у меня есть три действия A, B, C. Активность А начинается B, которая может или не может начать C. Я хочу Активность А, чтобы получить результаты от любой активности B или C.Операционная система Android не работает как ожидается

Если активность B никогда не начинается деятельность CI может успешно получить данные обратно активности A, делая

Intent intent = new Intent(); 
intent.PutExtra("DataId", item.Id); 
SetResult(Result.Ok, intent); 

Когда пользователь хочет начать деятельность C, то я использую этот код, чтобы разрешить пересылку результата от деятельности C обратно к активности

Intent intent = new Intent(this, typeof(ActivityC)); 
intent.PutExtra("DataId", dataId); 
intent.SetFlags(ActivityFlags.ForwardResult); 
StartActivity(intent); 

Если активность B начинается активность C, а затем активность C хочет return data Я делаю это с помощью этого кода

Intent result = new Intent(); 
result.PutExtra("DataId", dataId); 
SetResult(Result.Ok, result); 
Finish(); 
Intent intent = new Intent(this, typeof(ActivityA)); 
intent.SetFlags(ActivityFlags.ClearTop | ActivityFlags.SingleTop); 
StartActivity(intent); 

Все это хорошо работает. Проблема возникает, когда активность C не хочет возвращать данные. Если я вызову Finish(); в действии C, а затем попытаюсь вызвать SetResult(Result.Ok, intent); на активность B, эти значения из активности B никогда не будут возвращены в действие A. Они все еще используют пустые данные из активности C, хотя я никогда не называл SetResult(); `on активность C.

Нижняя линия. Как я могу получить активность B для возврата правильных данных, после запуска активности C и возврата к активности B?

+0

При запуске активность B и активность C , вы используете StartActivityForResult, как описано здесь? https://developer.xamarin.com/recipes/android/fundamentals/activity/start_activity_for_result/ Я бы подумал, что если вы запустите B из A с помощью StartActivityForResult, а затем запустите C из B с тем же, когда вы получите результат от C в B затем установите результат из B, чтобы он вернулся к A, я бы подумал, что он должен работать. Я не вижу, чтобы вы использовали StartActivityForResult в любом месте. – jgoldberger

+0

Я пропустил этот код. Действие A начинает действие B для результата. Вот почему 'SetResult()' работает вообще. Начальная активность C для результата и использования 'ActivityFlags.ForwardResult' выдает исключение ... – JacobK

ответ

1

Проблема возникает, когда активность C не хочет возвращать данные. Если я назову Finish(); по активности C, а затем попытайтесь вызвать SetResult (Result.Ok, намерение); на активность В, эти значения от активности B никогда не возвращаются к деятельности А.

Если вы обратитесь к ForwardResult:

Если установлено и это намерение используется для запуска новой деятельности с существующей один, тогда цель ответа существующей деятельности будет перенесена на новую активность.

Таким образом, из вашего описания, вы перенаправляющий «ответить цель» от ActivityB к ActivityC. Если вы хотите, чтобы отпрыгнуть от ActivityC к ActivityB и пусть ActivityB позвонить SetResult, вам нужно вернуть «ответ цели» обратно ActivityB путем добавления ActivityFlags.ForwardResult снова в ActivityC:

//click the button and go back to ActivityB without result 
private void BtnBackBNoResult_Click(object sender, EventArgs e) 
{ 
    Intent intent = new Intent(this, typeof(ActivityB)); 
    intent.PutExtra("Information", "winffee"); 
    intent.AddFlags(ActivityFlags.ForwardResult); 
    StartActivity(intent); 
} 
+0

Это оказалось очень хорошо с 1 настройкой. Мне не нужен новый экземпляр ActivityB, поэтому я просто добавил 'ActivityFlags.SingleTop'. Огромное спасибо! Кажется, так просто, что я не могу поверить, что не думал об этом. – JacobK

0

Вы можете использовать в Xamarin класса Application, как описан класс here:

Приложения

Если вам необходимо поддерживать состояние через приложение, то вам нужен класс Application. Хотя можно передавать информацию в/из классов Activity и Fragment, если у вас есть требование поддерживать глобальное состояние (например, имя пользователя в настоящее время вошедшего в систему), вы достигаете этого с помощью класса Application.

[Application] 
public class MyApplication : Application 
{ 
    public string CurrentUser = ""; 
} 

Обратите внимание, что класс украшен атрибутом [Приложение]. Это значит, что необходимый элемент генерируется и добавляется в файл AndroidManifest.xml. Это гарантирует, что класс создается при создании приложения/пакета.

<?xml version="1.0" encoding="utf-8"?> 
<manifest xmlns:android="http://schemas.android.com/apk/res/android" 
android:installLocation="auto" package="com.mydemo.apk" android:versionCode="1"> 
    <!--This line ensures the application class is instantiated automatically--> 
    <application android:label="MyDemo" android:icon="@drawable/Icon"></application> 
</manifest> 

Чтобы использовать класс приложения в вашем собственном коде, вам также необходимо определить текущий контекст. В Android контекст ссылается на текущее состояние приложения/объекта. Класс Context также базовый класс (но не ограничиваясь ими)

  • активность класса
  • Класс обслуживания

Есть несколько способов, в которых вы можете определить контекст приложения. Один из способов, чтобы добавить метод к приложению определения класса, который возвращает контекст, как в следующем коде:

[Application] 
public class MyApplication : Application 
{ 
    public Context GetContext() 
    { 
     return ((this).ApplicationContext); 
    } 
} 

Затем в коде приложения, вы можете вызвать его следующим образом.

MyApplication application = (MyApplication)GetContext(); 
String username = application.GetCurrentUser(); 
String password = application.GetPassword(); 
+0

Я знаю, что я могу сохранить информацию в другом месте и получить ее позже, но я хотел бы найти решение, которое перемещает информацию между действиями без использования класса приложения. Мне кажется, что я нашел ошибку в android, если кто-то не знает о решении. – JacobK

+0

Возможно, вам следует показать нам больше кода – CDrosos

+0

. Flag clear_top, который вы используете, возможно, это проблема: https://developer.android.com/reference/android/content/Intent.html#FLAG_ACTIVITY_CLEAR_TOP «Например, рассмотрите задачу, состоящую из действия: A, B, C, D. Если D вызывает startActivity() с намерением, который разрешает компонент активности B, то C и D будут завершены, а B получит заданное намерение, в результате чего стек теперь будет: A, B. " – CDrosos