package se.alexanderblom.delicious.helpers;
import java.util.List;
import android.graphics.Typeface;
import android.text.Spannable;
import android.text.SpannableStringBuilder;
import android.text.style.ForegroundColorSpan;
import android.text.style.StyleSpan;
import com.google.common.base.Charsets;
import com.google.common.hash.HashFunction;
import com.google.common.hash.Hashing;
public class TagsBinder {
private static final float SATURATION = 0.7f;
private static final float LIGHTNESS = 0.8f;
// Hard space
private static final char SEPARATOR = '\u00a0';
// This gives nice looking colors and is consistent
private static final int HASH_SEED = 1337;
private static final HashFunction HASH_FUNCTION = Hashing.murmur3_32(HASH_SEED);
public static Spannable buildTagList(List<String> tags) {
SpannableStringBuilder builder = new SpannableStringBuilder();
if (tags == null || tags.isEmpty()) {
return builder;
}
for (String tag : tags) {
int pos = builder.length();
builder.append(tag);
int color = generateColor(tag);
builder.setSpan(new ForegroundColorSpan(color), pos, builder.length(), 0);
builder.append(SEPARATOR);
// Thin space, so we get 1.5 spaces between
builder.append('\u2009');
}
// Remove last thin and hard space
builder.delete(builder.length() - 2, builder.length());
// Make the whole thing bold
builder.setSpan(new StyleSpan(Typeface.BOLD), 0, builder.length(), 0);
return builder;
}
public static int generateColor(String text) {
float hue = floatFromText(text, 0f, 1f);
return HSBtoColor(hue, SATURATION, LIGHTNESS);
}
private static float floatFromText(String text, float low, float high) {
int hash = HASH_FUNCTION.hashString(text, Charsets.UTF_8).asInt();
final float old_min = Integer.MIN_VALUE;
final float old_max = Integer.MAX_VALUE;
float hue = ((hash - old_min) / (old_max - old_min)) * (high - low);
// Return limited in range (low, high)
return Math.max(low, Math.min(hue, high));
}
/**
* Adapted from Color.java in Android
*
* See https://github.com/android/platform_frameworks_base/blob/master/graphics/java/android/graphics/Color.java
*/
private static int HSBtoColor(float h, float s, float b) {
//h = MathUtils.constrain(h, 0.0f, 1.0f);
//s = MathUtils.constrain(s, 0.0f, 1.0f);
//b = MathUtils.constrain(b, 0.0f, 1.0f);
float red = 0.0f;
float green = 0.0f;
float blue = 0.0f;
final float hf = (h - (int) h) * 6.0f;
final int ihf = (int) hf;
final float f = hf - ihf;
final float pv = b * (1.0f - s);
final float qv = b * (1.0f - s * f);
final float tv = b * (1.0f - s * (1.0f - f));
switch (ihf) {
case 0: // Red is the dominant color
red = b;
green = tv;
blue = pv;
break;
case 1: // Green is the dominant color
red = qv;
green = b;
blue = pv;
break;
case 2:
red = pv;
green = b;
blue = tv;
break;
case 3: // Blue is the dominant color
red = pv;
green = qv;
blue = b;
break;
case 4:
red = tv;
green = pv;
blue = b;
break;
case 5: // Red is the dominant color
red = b;
green = pv;
blue = qv;
break;
}
return 0xFF000000 | (((int) (red * 255.0f)) << 16)
| (((int) (green * 255.0f)) << 8) | ((int) (blue * 255.0f));
}
}