2012-12-02 195 views
4

我想用戶按下按鈕時以編程方式鎖定設備。我知道,我將需要使用deviceAdminReciever,我已經這樣做了,但我的應用程序崩潰每當我運行它鎖定android手機

以下是我的清單:

<manifest xmlns:android="http://schemas.android.com/apk/res/android" 
package="com.example.MyApp" 
android:versionCode="1" 
android:versionName="1.0" > 

<uses-sdk 
    android:minSdkVersion="8" 
    android:targetSdkVersion="15" /> 

<application 
    android:icon="@drawable/ic_launcher" 
    android:label="@string/app_name" 
    android:theme="@style/AppTheme" > 
    <activity 
     android:name=".MainActivity" 
     android:label="@string/title_activity_main" > 
     <intent-filter> 
      <action android:name="android.intent.action.MAIN" /> 

      <category android:name="android.intent.category.LAUNCHER" /> 
     </intent-filter> 
    </activity> 

    <receiver 
     android:name=".MainActivity" 
     android:permission="android.permission.BIND_DEVICE_ADMIN" > 
     <meta-data 
      android:name="android.app.device_admin" 
      android:resource="@xml/device_admin_sample" /> 

     <intent-filter> 
      <action android:name="android.app.action.DEVICE_ADMIN_ENABLED" /> 
     </intent-filter> 
    </receiver> 
</application> 

<uses-feature android:name="android.hardware.camera" /> 

</manifest> 

以下是我的Java代碼:

public class MainActivity extends DeviceAdminReceiver { 

public static class MyActivity extends Activity { 

    protected static final int ACTIVATION_REQUEST = 1; 
    private ImageButton btn; 

    private DevicePolicyManager mDPM; 
    private ComponentName mDeviceAdminSample; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 

     mDPM = (DevicePolicyManager) getSystemService(Context.DEVICE_POLICY_SERVICE); 
     mDeviceAdminSample = new ComponentName(Potter.this, 
       MainActivity.class); 
     setContentView(R.layout.activity_main); 



     btn = (ImageButton) findViewById(R.id.btn); 

     btn.setOnClickListener(new View.OnClickListener() { 

      public void onClick(View v) { 

       Intent intent = new Intent(
        DevicePolicyManager.ACTION_ADD_DEVICE_ADMIN); 
      mDeviceAdminSample = new ComponentName(this, MainActivity.class); 
      intent.putExtra(DevicePolicyManager.EXTRA_DEVICE_ADMIN, 
        mDeviceAdminSample); 
      startActivityForResult(intent, ACTIVATION_REQUEST); 
      mDPM.lockNow(); 

      } 
     }); 

    } 

    @Override 
    public boolean onCreateOptionsMenu(Menu menu) { 
     getMenuInflater().inflate(R.menu.activity_main, menu); 
     return true; 
    } 

    @Override 
    protected void onActivityResult(int requestCode, int resultCode, 
      Intent data) { 
     super.onActivityResult(requestCode, resultCode, data); 

     switch (requestCode) { 
     case ACTIVATION_REQUEST: 
       if (resultCode == Activity.RESULT_OK) { 
        Log.i("DeviceAdminSample", "Administration enabled!"); 
       } else { 
        Log.i("DeviceAdminSample", "Administration enable FAILED!"); 
       } 
       return; 


     } 
    } 


} 
} 

但是,當我運行應用程序它崩潰。我該如何解決這個問題?

+0

後,當您的應用程序崩潰我們這裏 –

回答

5

好吧,DeviceAdminReceiver是BroadcastReceiver,而不是活動。現在,您的清單聲明MainActivity這兩個組件,所以其中一個聲明是不正確的。 MainActivity是這個類的不好名字,因爲它不是一個Activity,它應該可能是MainReceiver或類似的東西(僅僅爲了一致性)。

您的應用程序崩潰是因爲Android正試圖將不是Activity的MainActivity作爲您的應用程序的主要活動啓動,而無法執行此操作。

此外,根據您的代碼,MyActivity是此接收器的內部類。這不是我會建議堅持的範例,可能會導致一些混亂。我將這兩個實體定義爲完全獨立的類。如果其中一個必須是另一個的內部類,那麼BroadcastReceiver將作爲Activity的內部類更有意義。在BARE MINIMUM中,如果您不重構任何Java代碼,則需要更新您的清單以根據您所寫的內容引用適當的元素,這意味着將實際的Activity引用爲內部類。

<activity 
    android:name=".MainActivity$MyActivity" 
    android:label="@string/title_activity_main" > 
    <intent-filter> 
     <action android:name="android.intent.action.MAIN" /> 

     <category android:name="android.intent.category.LAUNCHER" /> 
    </intent-filter> 
</activity> 

<receiver 
    android:name=".MainActivity" 
    android:permission="android.permission.BIND_DEVICE_ADMIN" > 
    <meta-data 
     android:name="android.app.device_admin" 
     android:resource="@xml/device_admin_sample" /> 

    <intent-filter> 
     <action android:name="android.app.action.DEVICE_ADMIN_ENABLED" /> 
    </intent-filter> 
</receiver> 

也許花點時間再次審查在SDK中的設備管理API示例,它位於

<SDK location>/samples/<platform-version>/ApiDemos/src/com/example/android/apis/app/DeviceAdminSample.java 

你的機器上。

3

這裏是我的代碼工作:

清單:

<application 
    android:icon="@drawable/ic_power_settings_new_black_48dp" 
    android:label="Screen Off" 
    android:theme="@android:style/Theme.NoDisplay"> 
    <activity android:name=".MainActivity"> 
     <intent-filter> 
      <action android:name="android.intent.action.MAIN" /> 
      <category android:name="android.intent.category.LAUNCHER" /> 
     </intent-filter> 
    </activity> 
    <receiver android:name="android.app.admin.DeviceAdminReceiver"> 
     <meta-data android:name="android.app.device_admin" 
      android:resource="@xml/device_admin" /> 
     <intent-filter> 
      <action android:name="android.app.action.DEVICE_ADMIN_ENABLED" /> 
     </intent-filter> 
    </receiver> 
</application> 

MainActivity.java:

package com.example.anhkhoachu.screenoff; 

import android.app.Activity; 
import android.app.Application; 
import android.app.admin.DeviceAdminReceiver; 
import android.app.admin.DevicePolicyManager; 
import android.content.ComponentName; 
import android.content.Context; 
import android.content.Intent; 
import android.os.Bundle; 
import android.widget.Toast; 


public class MainActivity extends Activity { 
DevicePolicyManager dpm; 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    dpm = (DevicePolicyManager) getSystemService(Context.DEVICE_POLICY_SERVICE); 
    try { 
     dpm.lockNow(); 
     finish(); 
    } catch (SecurityException e) { 
     Intent it = new Intent(DevicePolicyManager.ACTION_ADD_DEVICE_ADMIN); 
     it.putExtra(DevicePolicyManager.EXTRA_DEVICE_ADMIN, new ComponentName(this, DeviceAdminReceiver.class)); 
     startActivityForResult(it, 0); 
    } 
} 

@Override 
protected void onActivityResult(int requestCode, int resultCode, Intent data) { 
    if (resultCode == RESULT_OK) { 
     dpm.lockNow(); 
    } else { 
     Toast.makeText(this, "Device administrator must be activated to lock the screen", Toast.LENGTH_LONG).show(); 
    } 
    finish(); 
}} 

device_admin.xml:

<device-admin> <uses-policies> <force-lock /> </uses-policies> </device-admin>

+0

是APK logcat的結果:https://drive.google.com/file/d/0BxFhEK3zsRBedG1HZGtlMUZId2M/view?usp=sharing –