我正在开发一个用于打开/关闭手机摄像头的小部件.
I am developing a widget for turning on/off camera led of phone.
我制作了一个可以像切换按钮(开/关)一样工作的小部件.
I have made a widget that can work like toggle button (on/off).
行为如下:当我启用小部件时,有时 LED 灯仍然亮着.但它不会打开/关闭摄像头指示灯,但会更改图标.
Behavior is like follows : Sometimes the led light remains on when i enable the widget. But it doesnot turn on/off the camera led but it changes the icon.
我无法弄清楚实际问题是什么.
I am not able to figure out whats the actual problem.
同样的事情在 Activity(Torch Light 应用程序)中也能正常工作.
The same thing works fine in Activity (Torch Light Application).
谁能解释一下我该如何解决我的问题?
Can anyone please explain me how can i solve my problem ?
我哪里出错了?
你可以看看下面我到目前为止所做的代码
You can look at the code below that i have done so far
onUpdate
方法
@Override
public void onUpdate(Context context, AppWidgetManager appWidgetManager,
int[] appWidgetIds) {
//super.onUpdate(context, appWidgetManager, appWidgetIds);
remoteViews = new RemoteViews( context.getPackageName(), R.layout.widgetlayout);
watchWidget = new ComponentName( context, FlashLightWidget.class );
Intent intentClick = new Intent(context,FlashLightWidget.class);
intentClick.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, ""+appWidgetIds[0]);
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, appWidgetIds[0],intentClick, 0);
remoteViews.setOnClickPendingIntent(R.id.myToggleWidget, pendingIntent);
appWidgetManager.updateAppWidget( watchWidget, remoteViews );
ctx=context;
}
onReceive
方法如下:
@Override
public void onReceive(Context context, Intent intent) {
// TODO Auto-generated method stub
remoteViews = new RemoteViews( context.getPackageName(), R.layout.widgetlayout);
if (intent.getAction()==null) {
Bundle extras = intent.getExtras();
if(extras!=null) {
if(status)
{
status=false;
remoteViews.setImageViewResource(R.id.myToggleWidget, R.drawable.shutdown1);
processOnClick();
Toast.makeText(context,"Status==false-onclick",Toast.LENGTH_SHORT).show();
}
else
{
status = true;
remoteViews.setImageViewResource(R.id.myToggleWidget, R.drawable.shutdown2);
processOffClick();
Toast.makeText(context,"Status==true--Ofclick",Toast.LENGTH_SHORT).show();
}
}
watchWidget = new ComponentName( context, FlashLightWidget.class );
(AppWidgetManager.getInstance(context)).updateAppWidget( watchWidget, remoteViews );
}
}
}
processOffClick
方法
private void processOffClick() {
if (mCamera != null) {
mCamera.stopPreview();
mCamera.setPreviewCallback(null);
mCamera.release();
mCamera = null;
}
}
processOnClick
方法
private void processOnClick() {
if(mCamera==null)
{
try {
mCamera = Camera.open();
} catch (Exception e) {
e.printStackTrace();
}
}
if (mCamera != null) {
Parameters params = mCamera.getParameters();
List<String> flashModes = params.getSupportedFlashModes();
if (flashModes == null) {
return;
} else {
params.setFlashMode(Parameters.FLASH_MODE_OFF);
mCamera.setParameters(params);
mCamera.startPreview();
String flashMode = params.getFlashMode();
if (!Parameters.FLASH_MODE_TORCH.equals(flashMode)) {
if (flashModes.contains(Parameters.FLASH_MODE_TORCH)) {
params.setFlashMode(Parameters.FLASH_MODE_TORCH);
mCamera.setParameters(params);
}
}
}
} else if (mCamera == null) {
//Toast.makeText(ctx, "Camera not found", Toast.LENGTH_LONG).show();
return;
}
}
搞了半天,终于有空来解决这个问题了.
After a long time, I got free to solve this problem.
这就是我所做的.
FlashlightWidgetProvider
类:
public class FlashlightWidgetProvider extends AppWidgetProvider {
@Override
public void onUpdate(Context context, AppWidgetManager appWidgetManager,
int[] appWidgetIds) {
Intent receiver = new Intent(context, FlashlightWidgetReceiver.class);
receiver.setAction("COM_FLASHLIGHT");
receiver.putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, appWidgetIds);
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, receiver, 0);
RemoteViews views = new RemoteViews(context.getPackageName(),
R.layout.widget_layout);
views.setOnClickPendingIntent(R.id.button, pendingIntent);
appWidgetManager.updateAppWidget(appWidgetIds, views);
}
}
和 FlashlightWidgetReceiver 的 BroadcastReceiver :
and BroadcastReceiver for FlashlightWidgetReceiver :
public class FlashlightWidgetReceiver extends BroadcastReceiver {
private static boolean isLightOn = false;
private static Camera camera;
@Override
public void onReceive(Context context, Intent intent) {
RemoteViews views = new RemoteViews(context.getPackageName(), R.layout.widget_layout);
if(isLightOn) {
views.setImageViewResource(R.id.button, R.drawable.off);
} else {
views.setImageViewResource(R.id.button, R.drawable.on);
}
AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(context);
appWidgetManager.updateAppWidget(new ComponentName(context, FlashlightWidgetProvider.class),
views);
if (isLightOn) {
if (camera != null) {
camera.stopPreview();
camera.release();
camera = null;
isLightOn = false;
}
} else {
// Open the default i.e. the first rear facing camera.
camera = Camera.open();
if(camera == null) {
Toast.makeText(context, R.string.no_camera, Toast.LENGTH_SHORT).show();
} else {
// Set the torch flash mode
Parameters param = camera.getParameters();
param.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH);
try {
camera.setParameters(param);
camera.startPreview();
isLightOn = true;
} catch (Exception e) {
Toast.makeText(context, R.string.no_flash, Toast.LENGTH_SHORT).show();
}
}
}
}
}
Manifest.xml
文件中所需的权限:
<uses-permission android:name="android.permission.CAMERA"></uses-permission>
同时在 Manifest.xml
文件中注册接收器:
Also register receivers in Manifest.xml
file :
<receiver android:name=".FlashlightWidgetProvider" android:icon="@drawable/on" android:label="@string/app_name">
<intent-filter>
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
</intent-filter>
<meta-data android:name="android.appwidget.provider"
android:resource="@xml/flashlight_appwidget_info" />
</receiver>
<receiver android:name="FlashlightWidgetReceiver">
<intent-filter>
<action android:name="COM_FLASHLIGHT"></action>
</intent-filter>
</receiver>
重要提示:如果您的手机支持 FLASH_MODE_TORCH
,则此代码非常有效.
Important Note : This code works perfect if your phone has FLASH_MODE_TORCH
supported.
我已经在三星 Galaxy Ace 2.2.1 和2.3.3.代码不工作,因为该设备没有 FLASH_MODE_TORCH.
I have tested in Samsung Galaxy Ace 2.2.1 & 2.3.3. The code is not working because that device has no FLASH_MODE_TORCH.
在 HTC Salsa、Wildfire 中运行良好..
Works fine in HTC Salsa, Wildfire..
如果有人可以在这里测试并发布结果,那将是最好的.
If anyone can test and post results here, it would be best.
这篇关于用于在android中打开/关闭相机手电筒的小部件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持跟版网!