Android: onRetainNonConfigurationInstance () и изменения ориентации с различными макетами - PullRequest
0 голосов
/ 27 января 2011

У меня есть действие, которое должно иметь два довольно разных макета в зависимости от того, держит ли пользователь его в альбомной или портретной ориентации.

В onRetainNonConfigurationInstance () я храню много информации и извлекаю ее в onCreate (), если она существует, для восстановления пользовательских данных.

У меня есть метод, чтобы определить, находится ли телефон в настоящее время в портретном или ландшафтном режиме - если getWindowManager (). GetDefaultDisplay (). GetWidth () больше, чем getWindowManager (). GetDefaultDisplay (). GetHeight (), тогда это в ландшафте.

В моем xml-файле макета портрета у меня есть несколько видов изображений, которых нет в xml-файле альбомного макета. В onCreate () я проверяю, находим ли мы портрет, затем инициализирую и изменяю их, если это так. Если мы находимся в ландшафтном режиме, я не.

Все это прекрасно работает для переключения с портретного на ландшафтное, но затем при переключении обратно в портретный код мой код, который выполняется только для портретного режима, выдает исключение нулевого указателя - он не может найти элементы вида.

Трассировка стека:

E/AndroidRuntime( 4800): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.apps.hyperview/com.apps.hyperview.PopUp}: java.lang.NullPointerException
E/AndroidRuntime( 4800):        at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2268)
E/AndroidRuntime( 4800):        at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2284)
E/AndroidRuntime( 4800):        at android.app.ActivityThread.handleRelaunchActivity(ActivityThread.java:3278)
E/AndroidRuntime( 4800):        at android.app.ActivityThread.access$1900(ActivityThread.java:112)
E/AndroidRuntime( 4800):        at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1696)
E/AndroidRuntime( 4800):        at android.os.Handler.dispatchMessage(Handler.java:99)
E/AndroidRuntime( 4800):        at android.os.Looper.loop(Looper.java:123)
E/AndroidRuntime( 4800):        at android.app.ActivityThread.main(ActivityThread.java:3948)
E/AndroidRuntime( 4800):        at java.lang.reflect.Method.invokeNative(Native Method)
E/AndroidRuntime( 4800):        at java.lang.reflect.Method.invoke(Method.java:521)
E/AndroidRuntime( 4800):        at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:782)
E/AndroidRuntime( 4800):        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:540)
E/AndroidRuntime( 4800):        at dalvik.system.NativeStart.main(Native Method)
E/AndroidRuntime( 4800): Caused by: java.lang.NullPointerException
E/AndroidRuntime( 4800):        at com.apps.hyperview.PopUp.onCreate(PopUp.java:147)
E/AndroidRuntime( 4800):        at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1123)
E/AndroidRuntime( 4800):        at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2231)

У кого-нибудь есть идеи, что я делаю не так?

Спасибо !! r3mo

EDIT:

Раздел Popup.java, вызывающий проблемы:

// Check orientation. If we're in portrait...
if( isInPortrait() )
{
        spacer_above = (ImageView) findViewById(R.id.image_display_popup_spacer_above);
        spacer_above.setVisibility(View.INVISIBLE);    // THIS IS CAUSING THE NULLPOINTER
        spacer_below = (ImageView) findViewById(R.id.image_display_popup_spacer_below);
        spacer_below.setVisibility(View.INVISIBLE);
}
else;

Портретная версия файла макета содержит эти «проставки», а альбомная версия - нет. Это то, как изменения ориентации и различные макеты должны обрабатываться при использовании onRetainNonConfigurationInstance ()? Код все прекрасно работает при переходе от портрета к ландшафту, но при возвращении к портрету я получаю исключение NullPointerException.

РЕДАКТИРОВАТЬ 2:

isInPortrait (), кажется, работает нормально - однако я изменю это. Причина, по которой я не просто делаю видимости невидимыми, заключается в том, что структура макета значительно отличается в ландшафте. Очевидно, что этот ландшафтный макет работает нормально - ошибка возникает при переходе от портрета к ландшафту, а затем обратно к портрету.

Вся помощь приветствуется!

РЕДАКТИРОВАТЬ 3:

Теперь я изменил то, как я делаю это, чтобы иметь один и тот же файл макета в layout-port / и layout-land / и создавать элементы представления, которые мне не нужны в альбомной ориентации View.GONE. Конечно, было бы неплохо получить информацию об этой проблеме - кажется, очень мощная функция Android, позволяющая иметь полностью различных макетов для пейзажа и портрета.

Спасибо!

1 Ответ

0 голосов
/ 28 января 2011

Вы можете поместить макет портрета в res / layout-port, альбомную версию макета в res / layout-land и по умолчанию (для квадратных экранов, я полагаю) в res / layout. Система автоматически (и надежно) определяет, какую версию макета использовать. Есть ли причина, по которой вы этого не делаете?

...