我有一个设备,显然有一些方向坏了,因为重启后,大约一个小时,它会旋转屏幕以响应方向的变化 - 然后它会停止响应,两者都在“桌面”级别和应用程序级别。
所以,我找到Change Screen Orientation programmatically using a Button,我假设我可以创建一个“仅限图标按钮”的应用程序,按下时,不会运行新的应用程序,而只是尝试更改方向。
“icon / button-only”应用的骨架是Lock screen (it.reyboz.screenlock)的副本。我在一个要点上发布了这个项目 - 但是由于在gist中默认有文件夹(和二进制文件)很难,这是你可以用来获取代码的过程:
git clone https://gist.github.com/e6422677cababc17526d0cb57aceb76a.git dl_archive_git
cd dl_archive_git
bash run-me-to-unpack.sh
# check upacked dir:
tree rotate-btn-droid
cd rotate-btn-droid/
# change your SDK path (ASDKPATH) in buildme.sh, and then:
bash buildme.sh
# if your java install is not in the path, then call the last command with JAVA_HOME prepended:
# JAVA_HOME=/path/to/jdkXXX bash buildme.sh
基本上,我只是想在MainActivity.java
中执行以下操作:
Display display = ((WindowManager) getSystemService(WINDOW_SERVICE)).getDefaultDisplay();
int orientation = display.getOrientation();
// OR: orientation = getRequestedOrientation(); // inside an Activity
switch(orientation) {
case Configuration.ORIENTATION_PORTRAIT:
setRequestedOrientation (Build.VERSION.SDK_INT < 9 ?
ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE :
ActivityInfo.SCREEN_ORIENTATION_SENSOR_LANDSCAPE);
break;
case Configuration.ORIENTATION_LANDSCAPE:
setRequestedOrientation (Build.VERSION.SDK_INT < 9 ?
ActivityInfo.SCREEN_ORIENTATION_PORTRAIT :
ActivityInfo.SCREEN_ORIENTATION_SENSOR_PORTRAIT);
break;
}
...但是,当我点击应用程序图标并运行此代码时,没有任何反应。
所以,我的问题是 - 原则上是否可以在“桌面”级别强制更改设备方向?如果是这样,它是否依赖于Android版本(可能是供应商品牌) - 以及如何?
答案 0 :(得分:0)
只是好奇所以试了Sam's solution并做了一些改变:
在Manifest
权限<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW"/>
此权限也是危险权限,但如果您从Play商店安装应用程序,则无需担心。
我做了这样的窗口服务:
public class MyServiceNew extends Service {
private View view;
public MyServiceNew() {
}
@Override
public IBinder onBind(Intent intent) {
throw new UnsupportedOperationException("Not yet implemented");
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
int flag = intent.getExtras().getInt("Flag");
WindowManager.LayoutParams layout;
if (flag == 1) {
layout = generateLayoutLandscape();
} else {
layout = generateLayoutPortrait();
}
WindowManager wm = (WindowManager) getSystemService(WINDOW_SERVICE);
wm.addView(view, layout);
return super.onStartCommand(intent, flags, startId);
}
private WindowManager.LayoutParams generateLayoutPortrait() {
Toast.makeText(this, "Port", Toast.LENGTH_LONG).show();
view = new View(this);
WindowManager.LayoutParams params = new WindowManager.LayoutParams(
WindowManager.LayoutParams.TYPE_SYSTEM_OVERLAY,
WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH,
PixelFormat.TRANSPARENT);
params.alpha = 0f;
params.width = 0;
params.height = 0;
//The orientation to force
params.screenOrientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
return params;
}
private WindowManager.LayoutParams generateLayoutLandscape() {
Toast.makeText(this, "Land", Toast.LENGTH_LONG).show();
view = new View(this);
WindowManager.LayoutParams params = new WindowManager.LayoutParams(
WindowManager.LayoutParams.TYPE_SYSTEM_OVERLAY,
WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH,
PixelFormat.TRANSPARENT);
params.alpha = 0f;
params.width = 0;
params.height = 0;
//The orientation to force
params.screenOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
return params;
}
}
从开发时的Activity中确保包含ACTION_MANAGE_OVERLAY_PERMISSION
;再次,您不必担心将通过Google Play Store
安装应用的用户。这里使用以下代码允许M以上设备的许可:
public void requestSystemAlertPermission(int requestCode) {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M)
return;
final String packageName = getPackageName();
final Intent intent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION, Uri.parse("package:" + packageName));
startActivityForResult(intent, requestCode);
}
现在只需启动您的服务并为Portrait或Landscape传递额外内容 我使用1代表Landscape,2代表Portrait
Intent intentLand = new Intent(SoNew.this, MyServiceNew.class);
intentLand.putExtra("Flag", 2); //or change 1 for Port
startService(intentLand);
希望这会有所帮助:)