6

I found

http://developer.android.com/reference/android/app/ActivityManager.html#getRunningTasks(int)

to retrieve current application's baseActivity or topActivity. Then I was able to get the Activity's Resources object.

However, the api is no longer available to third party applications in Lollipop

darktiny
  • 296
  • 2
  • 9

2 Answers2

6

You can retrieve the launcher Intent for an application using PackageManager.getLaunchIntentForPackage and PackageManager.getActivityInfo will return the ActivityInfo for it.

Once you have that information you can create a new Theme, then use the resources from PackageManager.getResourcesForApplication to retrieve the attrs needed to find the colorPrimary value.

    try {
        final PackageManager pm = getPackageManager();

        // The package name of the app you want to receive resources from
        final String appPackageName = ...;
        // Retrieve the Resources from the app
        final Resources res = pm.getResourcesForApplication(appPackageName);
        // Create the attribute set used to get the colorPrimary color
        final int[] attrs = new int[] {
                /** AppCompat attr */
                res.getIdentifier("colorPrimary", "attr", appPackageName),
                /** Framework attr */
                android.R.attr.colorPrimary
        };

        // Create a new Theme and apply the style from the launcher Activity
        final Theme theme = res.newTheme();
        final ComponentName cn = pm.getLaunchIntentForPackage(appPackageName).getComponent();
        theme.applyStyle(pm.getActivityInfo(cn, 0).theme, false);

        // Obtain the colorPrimary color from the attrs
        TypedArray a = theme.obtainStyledAttributes(attrs);
        // Do something with the color
        final int colorPrimary = a.getColor(0, a.getColor(1, Color.WHITE));
        // Make sure you recycle the TypedArray
        a.recycle();
        a = null;
    } catch (final NameNotFoundException e) {
        e.printStackTrace();
    }

One caveat is that the launcher Activity may not contain a theme attribute, in which case you may consider using PackageManager.getApplicationInfo, but there's no guarantee the Application tag contains a theme attribute as well.

Here are some examples:

Contacts

contacts

Play Music

play music

Gmail

gmail

adneal
  • 30,484
  • 10
  • 122
  • 151
  • Thanks for your answer. It was my mistake to describe question clearly. Another problem is how can I get the current running application's packageName. I just write a share extension, and my share dialog share the same task with the current running application. – darktiny Nov 26 '14 at 03:13
  • @darktiny There are other questions regarding this: http://stackoverflow.com/q/26400469/420015 and http://stackoverflow.com/q/26400469/420015 as well as official word from Google https://code.google.com/p/android-developer-preview/issues/detail?id=29 – adneal Nov 26 '14 at 03:39
0

I was struggling because of this for a very long time. Answer from adneal didn't get me right colors, most were just white. The trick I did is load icons, convert them to very low resolution bitmaps and then get color that is the most not-greyish (to reduce a chance of picking white/grey/black colors from an icon) out of them.

Here is the code:

fun getBestPrimaryColor(icon:Drawable): Int{
    val bitmap: Bitmap = icon.toBitmap(5, 5, Bitmap.Config.RGB_565)
    var best_diff_j = 0
    var best_diff_k = 0
    var best_diff = 0
    var current_diff = 0
    for(j in 0..4){
        for(k in 0..4){
            val c = bitmap.getPixel(j,k)
            current_diff = max(listOf(c.red,c.green,c.blue)) - min(listOf(c.red,c.green,c.blue))
            if(current_diff > best_diff){
                best_diff = current_diff
                best_diff_j = j
                best_diff_k = k
            }
        }
    }
    return bitmap.getPixel(best_diff_j, best_diff_k)
}

It turns out like this: Screenshot example

You can change size of the bitmap height and width to get more colors but I don't think it's really necessary.

soggypants
  • 311
  • 2
  • 5