3

I'm working on a toggle widget that consists of a button. When pressed, I'd like it to run an activity without opening up anything (just saying on the desktop as usual). Is there a way to directly run an activity from a button press on a desktop widget? Thanks! UPDATE: Now I'm trying to toggle silent mode from within the code without running a new activity. Here is my current code (the buttons do nothing when I click them for some reason)

package toggleHD.widget;

import android.app.Activity;
import android.app.IntentService;
import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.media.AudioManager;
import android.appwidget.AppWidgetManager;
import android.appwidget.AppWidgetProvider;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
import android.widget.RemoteViews;
import android.widget.Toast;


    public class ButtonWidget extends AppWidgetProvider {

        public static String ACTION_WIDGET_CLICK_RECEIVER = "ActionReceiverWidget";

        public static int appid[];
        public static RemoteViews rview;
        @Override
        public void onUpdate(Context context, AppWidgetManager appWidgetManager, 
                int[] appWidgetIds){
            updateWidgetState(context, ""); 
        }
        @Override
        public void onReceive(Context paramContext, Intent paramIntent)
          {
             String str = paramIntent.getAction();
            if (paramIntent.getAction().equals(ACTION_WIDGET_CLICK_RECEIVER)) {
                updateWidgetState(paramContext, str);   
            }
            else
            {
                    if ("android.appwidget.action.APPWIDGET_DELETED".equals(str))
                      {
                        int i = paramIntent.getExtras().getInt("appWidgetId", 0);
                        if (i == 0)
                        {

                        }
                        else
                        {
                            int[] arrayOfInt = new int[1];
                            arrayOfInt[0] = i;
                            onDeleted(paramContext, arrayOfInt);
                        }
                      }
              super.onReceive(paramContext, paramIntent);
            }
          }
         static void updateWidgetState(Context paramContext, String paramString)
          {
            RemoteViews localRemoteViews = buildUpdate(paramContext, paramString);
            ComponentName localComponentName = new ComponentName(paramContext, ButtonWidget.class);
            AppWidgetManager.getInstance(paramContext).updateAppWidget(localComponentName, localRemoteViews);
          }
         private static RemoteViews buildUpdate(Context paramContext, String paramString)
          {
            // Toast.makeText(paramContext, "buildUpdate() ::"+paramString, Toast.LENGTH_SHORT).show();
            rview = new RemoteViews(paramContext.getPackageName(), R.layout.main);
            Intent active = new Intent(paramContext, ButtonWidget.class);
            active.setAction(ACTION_WIDGET_CLICK_RECEIVER);

           // PendingIntent configPendingIntent = PendingIntent.getActivity(paramContext, 0, active, 0);

// upadte this R.id.buttonus1 with your layout or image id on which click you want to start Activity

Intent configIntent = new Intent(paramContext, TestReceiver.class);
configIntent.setAction(ACTION_WIDGET_CLICK_RECEIVER);
PendingIntent configPendingIntent = PendingIntent.getActivity(paramContext, 0, configIntent, 0);
            if(paramString.equals(ACTION_WIDGET_CLICK_RECEIVER))
            {

               //open Activity here..
             //your code for update and what you want on button click
//
         rview.setOnClickPendingIntent(R.id.button_one, configPendingIntent);
            }  
             return rview; 
          }
        @Override
        public void onEnabled(Context context){
            super.onEnabled(context);
           // Toast.makeText(context, "onEnabled()  ", Toast.LENGTH_SHORT).show();
        }
        // Called each time an instance of the App Widget is removed from the host
        @Override
        public void onDeleted(Context context, int [] appWidgetId){
            super.onDeleted(context, appWidgetId);
           // Toast.makeText(context, "onDeleted()  ", Toast.LENGTH_SHORT).show();
        }
        // Called when last instance of App Widget is deleted from the App Widget host.
        @Override
        public void onDisabled(Context context) {
            super.onDisabled(context);
           // Toast.makeText(context, "onDisabled()  ", Toast.LENGTH_SHORT).show();
        }

    }
MattDementous
  • 97
  • 3
  • 7
  • on Home screen widget Click u want to start an activity? – ρяσѕρєя K Mar 30 '12 at 16:02
  • Yes. But I don't want it to open a fullscreen page or anything, just an activity. – MattDementous Mar 30 '12 at 16:03
  • An activity normally is fullscreen, unless you theme it to a dialog theme or similar – Martyn Mar 30 '12 at 16:04
  • I really just want to run a bit of code to toggle ringer modes and bluetooth etc. From what I could tell it wouldn't work within the widget's code, which is why I'm leaning towards using an activity to do it in the background. – MattDementous Mar 30 '12 at 16:05
  • @MattDementous :why it's not working from widget code? – ρяσѕρєя K Mar 30 '12 at 16:07
  • It said I had to extend from Activity. Is there a better way I'm missing? – MattDementous Mar 30 '12 at 16:09
  • @MattDementous : just register a reciver for button click no need to start an activity for toggle ringer mode – ρяσѕρєя K Mar 30 '12 at 16:13
  • @MattDementous: see my answer in this post : [How do I start an Activity when my Widget is clicked](http://stackoverflow.com/questions/9671596/how-do-i-start-an-activity-when-my-widget-is-clicked/9681914#9681914). i have `ACTION_WIDGET_CLICK_RECEIVER` recvier which fire when user click on button from home screen widget – ρяσѕρєя K Mar 30 '12 at 16:59

3 Answers3

7

start activity on Home Screen Widget click:

Method 1: in on onReceive

Intent intentClick =   the new Intent to (context, update, class);
PendingIntent pendingIntent = PendingIntent.getActivity (context, 0,
intentClick, 0);
rv.setOnClickPendingIntent (R.id.layout, pendingIntent);

Method 2: in onReceive

Intent intn = new Intent (context, update. Class);
intn.setFlags (Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity (intn);

but you must register a broadcast for widget click

ρяσѕρєя K
  • 132,198
  • 53
  • 198
  • 213
1

If you want to do sth. in the background, you can use Service instead of Activity: http://developer.android.com/reference/android/app/Service.html

1.you can starService as soon as you app started, or your widget displayed. http://developer.android.com/reference/android/content/Context.html#startService(android.content.Intent)

2.try to bindService when the widge is clicked http://developer.android.com/reference/android/content/Context.html#bindService(android.content.Intent, android.content.ServiceConnection, int)

3.after binded, you can get the service instance from the binder using serviceConnection. Then you can executed the code defined in the service. see the example here :http://developer.android.com/reference/android/app/Service.html

or you can just

  1. try to start service(Only on service instance will be running in every moment)

  2. send broadcast to the service which ask the service to do sth. for you.

Since the activity is designed to display sth to user, and the service is designed to execute in the background.

Mikonos
  • 161
  • 6
0

An alterative is to send a broadcast intent rather starting an activity! I wanted to perform an action when a widget button was pushed -- not specially to start an activity that would show up on screen. You can use this technique to execute your code in the widget itself (where the widget does not necessarily contain an Activity.)

Intent intt = new Intent(ctx, RWidg.class);
intt.setAction("myActionName");
PendingIntent bcInt = PendingIntent.getBroadcast(ctx, 0, intt, 0);

RemoteViews views = new RemoteViews(ctx.getPackageName(), R.layout.widg_lay);
views.setOnClickPendingIntent(R.id.button, bcInt);

appWidgetManager.updateAppWidget(widgId, views);

Rather than using a PendingIntent to start an activity, using the PendingIntent.getBroadcast() creates a PendingIntent with 'secret key': ActivityManager.INTENT_SENDER_BROADCAST which causes the ActivityManager to do a sendBroadcast() rather than a startActivity()

You need to add an 'if' statement to your onRecieve() method to intercept the action name or names that you use:

public void onReceive(Context ctx, Intent intt) {
  String action = intt.getAction();
  if (action.compareTo("myActionName")) {
    // Do your myActionName work here
  } else {
    super.onReceive(ctx, intt);
  }
} // end of onReceive
Ribo
  • 3,363
  • 1
  • 29
  • 35