简体   繁体   English

Android:手动屏幕方向而不重新启动活动?

[英]Android: manual screen orientation without restarting the activity?

I need to make an app playing video with a button for full-screen on the video. 我需要制作一个应用程序播放带有全屏视频按钮的视频。 The button is used to manually switch between landscape and portrait of the video display. 该按钮用于在视频显示的横向和纵向之间手动切换。 We don't want the auto rotation detect. 我们不希望自动旋转检测。 So the Manifest file is set as below. 因此Manifest文件设置如下。

<activity
    android:name=".VideoActivity"
    android:screenOrientation="portrait"
    android:configChanges="keyboardHidden"/>

I used 我用了

setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR_LANDSCAPE); or setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR_PORTRAIT); setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR_PORTRAIT);

to manually set the orientation. 手动设置方向。 It works but it restarts the activity - the onCreate() was found called. 它工作但它重新启动活动 - 发现onCreate()被调用。 So the video playback restarts from the beginning unexpectedly. 因此,视频播放意外地从头开始重新开始。 I cannot make it smooth as like as using onConfigurationChanged() - the auto rotation detect method. 我不能像使用onConfigurationChanged()一样平滑 - 自动旋转检测方法。

So how to make manual screen orientation change without restarting the activity? 那么如何在不重新启动活动的情况下更改手动屏幕方向?

Thank you. 谢谢。

For manaul orientation change: 对于manaul方向更改:

<activity
    android:name=".VideoDetails"
    android:configChanges="orientation"/>

public class VideoDetails extends Activity {
    ...
    onStart() {
        setRequestedOrientation(orientation);
    }
    onConfigurationChanged(Configuration newConfig){
        // do stuff for orientation change.
    }
    onClick() {
        setRequestedOrientation(orientation);
    }
}

For auto-orientation detect: 对于自动定向检测:

<activity
    android:name=".VideoDetails"
    android:configChanges="orientation"/>

public class VideoDetails extends Activity {
    ...
    onConfigurationChanged(Configuration newConfig){
        // do stuff for orientation change.
    }
}

http://developer.android.com/guide/topics/resources/runtime-changes.html . http://developer.android.com/guide/topics/resources/runtime-changes.html You can have a looking at the link under the heading Handling the Configuration Change Yourself 您可以查看“ 处理配置更改自己 ”标题下的链接

<activity android:name=".MyActivity"
      android:configChanges="orientation|keyboardHidden"
      android:label="@string/app_name">

Now, when one of these configurations change, MyActivity does not restart. 现在,当其中一个配置发生更改时,MyActivity不会重新启动。 Instead, the MyActivity receives a call to onConfigurationChanged(). 相反,MyActivity接收对onConfigurationChanged()的调用。 This method is passed a Configuration object that specifies the new device configuration. 此方法传递一个Configuration对象,该对象指定新设备配置。

 android:configChanges="orientation|screenSize" (andorid 3.2 and above screen size also changes. add this)

Suppose your video is 10 minutes. 假设您的视频是10分钟。 The video plays till 5 minutes and orientation changes, you know that it has played till 5 minutes. 视频播放到5分钟,方向发生变化,你知道它已播放到5分钟。

You can save the actual progress of the video in onSaveInstanceState() and get the saved data in onRestoreInstanceState() from the Bundle, after that you can start the playing with either the progress data, or from the beginning if there was no data saved. 您可以在onSaveInstanceState()中保存视频的实际进度,并从Bundle中获取onRestoreInstanceState()中保存的数据,之后您可以使用进度数据开始播放,或者如果没有保存数据则从头开始播放。

When orientation changes activity is destroyed and recreated. 当方向更改活动被销毁并重新创建时。 If you want to save data and retain you can do as below for saving large set of data 如果要保存数据并保留,可以执行以下操作来保存大量数据

 @Override
 public Object onRetainNonConfigurationInstance() {
 final MyDataObject data = collectMyLoadedData();
 return data;
 }


@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);

final MyDataObject data = (MyDataObject) getLastNonConfigurationInstance();
if (data == null) {
    data = loadMyData();
}

}

For small set of data 对于小数据集

 @Override
 public void onSaveInstanceState(Bundle savedInstanceState) {
 super.onSaveInstanceState(savedInstanceState);
 // Save UI state changes to the savedInstanceState.
 // This bundle will be passed to onCreate if the process is
 // killed and restarted.
 savedInstanceState.putString("NICK_NAME", Name);//save nick name
 }

 @Override
 public void onRestoreInstanceState(Bundle savedInstanceState) {
 super.onRestoreInstanceState(savedInstanceState);
 // Restore UI state from the savedInstanceState.
 // This bundle has also been passed to onCreate.
 Name = savedInstanceState.getString("NICK_NAME");//restore nick name
 }

To check orientation 检查方向

@Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);

// Checks the orientation of the screen
if (newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE) {
    Toast.makeText(this, "landscape", Toast.LENGTH_SHORT).show();
} else if (newConfig.orientation == Configuration.ORIENTATION_PORTRAIT){
    Toast.makeText(this, "portrait", Toast.LENGTH_SHORT).show();
}
}

VideoView in Android . Android中的VideoView In this case also video is streamed from the server. 在这种情况下,视频也从服务器流式传输。 Check the answer accepted (commonsware answer). 检查接受的答案(commonsware答案)。 Exactly the same i suggested. 我建议完全一样。

Start by adding the android:configChanges node to your Activity's manifest node 首先将android:configChanges节点添加到Activity's manifest节点

android:configChanges="keyboardHidden|orientation"

For more information check this link 有关更多信息,请查看链接

Add the tag 添加标签

"android:configChanges="keyboard|keyboardHidden|orientation|screenSize|navigation" for your activity in Manifest.xml,

And Override the method 并覆盖该方法

public void onConfigurationChanged(Configuration newConfig) {}

If you need to change your layout on orientationchange chek this one replace layout on orientation change 如果您需要在orientationchange chek 上更改布局,则可以在方向更改时替换布局

Having the app restart after orientation change is inevitable. 在方向更改后重新启动应用程序是不可避免的。

Keep the variable related to video status on Application so that the Activity does not restart playback at the begin. 保持与视频状态相关的变量在应用程序上,以便活动不会在开始时重新开始播放。

This code is from a sample app I made to test this answer. 此代码来自我为测试此答案而制作的示例应用程序。

public class MyApplication extends Application {
int counter;
@Override
public void onCreate() {
    super.onCreate();
    counter = 0;
    }
}   

Add the Application on your manifest 在清单上添加应用程序

<application
    android:allowBackup="true"
    android:icon="@drawable/ic_launcher"
    android:label="@string/app_name"
    android:theme="@style/AppTheme"
    android:name="com.example.orientationchange.MyApplication" >
    <activity
 ...

Use withing Activity: 使用活动:

public class MainActivity extends Activity {

TextView output;
MyApplication app ;
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    app = (MyApplication) getApplication();
    setContentView(R.layout.activity_main);
    output = (TextView) findViewById(R.id.output);
    //A counter thread used to test the solution.
    new CounterTask().execute( 100 );
}
 ...

Now the rotation does not clean the status variables. 现在旋转不会清除状态变量。

You can alternatively use Preferences for a more code-heavy solution to preserving the state. 您也可以使用“首选项”来获取更多代码密集型解决方案来保留状态。 The preferences will also remember the state from one use of the app to another, where the Application state is cleaned onDestroy() of the app. 首选项还将记住从一次使用应用程序到另一次应用程序的状态,其中应用程序状态被清除应用程序的onDestroy()。

I was looking for solution very long, and for me worked defining orientation in Manifest as locked : 我一直在寻找解决方案,对我来说,在Manifest中将方向定义为锁定

<activity
    android:name=".VideoActivity"
    android:screenOrientation="locked"
    android:configChanges="keyboardHidden"/>

This prevents Activity to be recreated even if you call setRequestedOrientation() 即使您调用setRequestedOrientation() ,也可以防止重新创建Activity

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM