diff --git a/res/layout/dialog_battery_settings.xml b/res/layout/dialog_battery_settings.xml new file mode 100644 index 0000000..6cea31b --- /dev/null +++ b/res/layout/dialog_battery_settings.xml @@ -0,0 +1,76 @@ + + + + + + + + + + + + + diff --git a/res/layout/led_color_item.xml b/res/layout/led_color_item.xml new file mode 100644 index 0000000..9052caf --- /dev/null +++ b/res/layout/led_color_item.xml @@ -0,0 +1,11 @@ + + + + + diff --git a/res/layout/preference_color_select.xml b/res/layout/preference_color_select.xml new file mode 100644 index 0000000..192d372 --- /dev/null +++ b/res/layout/preference_color_select.xml @@ -0,0 +1,81 @@ + + + + + + + + + + + + + + + + + + + + diff --git a/res/values/cherish_arrays.xml b/res/values/cherish_arrays.xml index 977d558..71e50a9 100644 --- a/res/values/cherish_arrays.xml +++ b/res/values/cherish_arrays.xml @@ -613,4 +613,14 @@ 2 3 + + + @string/led_color_green + @string/led_color_red + + + + #FF00FF00 + #FFFF0000 + diff --git a/res/values/cherish_attrs.xml b/res/values/cherish_attrs.xml index fb2fc72..d23c7ea 100644 --- a/res/values/cherish_attrs.xml +++ b/res/values/cherish_attrs.xml @@ -28,4 +28,10 @@ + + + + + + diff --git a/res/values/cherish_dimens.xml b/res/values/cherish_dimens.xml index e82bf09..2234995 100644 --- a/res/values/cherish_dimens.xml +++ b/res/values/cherish_dimens.xml @@ -16,8 +16,12 @@ --> + 26dp + 26dp 20dp + 18dip + 18dip 20dp 100dp diff --git a/res/values/cherish_strings.xml b/res/values/cherish_strings.xml index fe43791..ff2d089 100644 --- a/res/values/cherish_strings.xml +++ b/res/values/cherish_strings.xml @@ -58,6 +58,8 @@ #ff000000 Set Default + Green + Red Lockscreen charging info @@ -722,5 +724,9 @@ Bar spacing Block size Block spacing + + + true diff --git a/src/com/cherish/settings/preferences/ColorSelectDialog.java b/src/com/cherish/settings/preferences/ColorSelectDialog.java new file mode 100644 index 0000000..4e2cb6f --- /dev/null +++ b/src/com/cherish/settings/preferences/ColorSelectDialog.java @@ -0,0 +1,330 @@ +/* + * Copyright (C) 2010 Daniel Nilsson + * Copyright (C) 2012 The CyanogenMod Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.cherish.settings.preferences; + +import android.app.Activity; +import android.app.AlertDialog; +import android.app.NotificationManager; +import android.content.Context; +import android.graphics.Color; +import android.graphics.PixelFormat; +import android.os.Bundle; +import android.text.Editable; +import android.text.TextWatcher; +import android.text.InputFilter; +import android.text.InputFilter.LengthFilter; +import android.util.Pair; +import android.util.Log; +import android.view.LayoutInflater; +import android.view.View; +import android.view.View.OnFocusChangeListener; +import android.view.ViewGroup; +import android.view.inputmethod.InputMethodManager; +import android.widget.AdapterView; +import android.widget.BaseAdapter; +import android.widget.EditText; +import android.widget.LinearLayout; +import android.widget.Spinner; +import android.widget.SpinnerAdapter; +import android.widget.TextView; + +import com.cherish.settings.R; +import com.cherish.settings.ui.ColorPanelView; +import com.cherish.settings.ui.ColorPickerView; +import com.cherish.settings.ui.ColorPickerView.OnColorChangedListener; + +import java.util.ArrayList; +import java.util.IllegalFormatException; +import java.util.Locale; + +public class ColorSelectDialog extends AlertDialog implements + ColorPickerView.OnColorChangedListener, TextWatcher, OnFocusChangeListener { + + private static final String TAG = "ColorSelectDialog"; + private final static String STATE_KEY_COLOR = "BatteryLightDialog:color"; + + private ColorPickerView mColorPicker; + + private EditText mHexColorInput; + private ColorPanelView mNewColor; + private LayoutInflater mInflater; + private boolean mMultiColor = true; + private Spinner mColorList; + private LinearLayout mColorListView; + private LinearLayout mColorPanelView; + private ColorPanelView mNewListColor; + private LedColorAdapter mLedColorAdapter; + private boolean mWithAlpha; + + private boolean mShowLedPreview; + private boolean mShowMultiColor; + private NotificationManager mNoMan; + private Context mContext; + + protected ColorSelectDialog(Context context, int initialColor, boolean showMultiColor, boolean showLedPreview, boolean withAlpha) { + super(context); + mContext = context; + mShowLedPreview = showLedPreview; + mWithAlpha = withAlpha; + mShowMultiColor = showMultiColor; + mMultiColor = + (getContext().getResources().getBoolean(R.bool.config_has_multi_color_led) || mShowMultiColor); + init(initialColor); + } + + private void init(int color) { + // To fight color banding. + getWindow().setFormat(PixelFormat.RGBA_8888); + setUp(color); + } + + /** + * This function sets up the dialog with the proper values. If the speedOff parameters + * has a -1 value disable both spinners + * + * @param color - the color to set + * @param speedOn - the flash time in ms + * @param speedOff - the flash length in ms + */ + private void setUp(int color) { + mInflater = (LayoutInflater) getContext() + .getSystemService(Context.LAYOUT_INFLATER_SERVICE); + View layout = mInflater.inflate(R.layout.dialog_battery_settings, null); + + mNoMan = (NotificationManager) + mContext.getSystemService(Context.NOTIFICATION_SERVICE); + + mColorPicker = (ColorPickerView) layout.findViewById(R.id.color_picker_view); + mHexColorInput = (EditText) layout.findViewById(R.id.hex_color_input); + mNewColor = (ColorPanelView) layout.findViewById(R.id.color_panel); + mColorPanelView = (LinearLayout) layout.findViewById(R.id.color_panel_view); + + mColorListView = (LinearLayout) layout.findViewById(R.id.color_list_view); + mColorList = (Spinner) layout.findViewById(R.id.color_list_spinner); + mNewListColor = (ColorPanelView) layout.findViewById(R.id.color_list_panel); + + mColorPicker.setOnColorChangedListener(this); + mHexColorInput.setOnFocusChangeListener(this); + setAlphaSliderVisible(mWithAlpha); + mColorPicker.setColor(color, true); + showLed(color); + + mColorList = (Spinner) layout.findViewById(R.id.color_list_spinner); + mLedColorAdapter = new LedColorAdapter( + R.array.entries_led_colors, + R.array.values_led_colors); + mColorList.setAdapter(mLedColorAdapter); + mColorList.setSelection(mLedColorAdapter.getColorPosition(color)); + mColorList.setOnItemSelectedListener(mColorListListener); + + setView(layout); + + // show and hide the correct UI depending if we have multi-color led or not + if (mMultiColor){ + mColorListView.setVisibility(View.GONE); + mColorPicker.setVisibility(View.VISIBLE); + mColorPanelView.setVisibility(View.VISIBLE); + } else { + mColorListView.setVisibility(View.VISIBLE); + mColorPicker.setVisibility(View.GONE); + mColorPanelView.setVisibility(View.GONE); + } + } + + private AdapterView.OnItemSelectedListener mColorListListener = new AdapterView.OnItemSelectedListener() { + + @Override + public void onItemSelected(AdapterView parent, View view, int position, long id) { + int color = mLedColorAdapter.getColor(position); + mNewListColor.setColor(color); + } + + @Override + public void onNothingSelected(AdapterView parent) { + } + }; + + @Override + public Bundle onSaveInstanceState() { + Bundle state = super.onSaveInstanceState(); + state.putInt(STATE_KEY_COLOR, getColor()); + switchOffLed(); + return state; + } + + @Override + public void onRestoreInstanceState(Bundle state) { + super.onRestoreInstanceState(state); + mColorPicker.setColor(state.getInt(STATE_KEY_COLOR), true); + } + + @Override + public void onColorChanged(int color) { + final boolean hasAlpha = mWithAlpha; + final String format = hasAlpha ? "%08x" : "%06x"; + final int mask = hasAlpha ? 0xFFFFFFFF : 0x00FFFFFF; + + mNewColor.setColor(color); + mHexColorInput.setText(String.format(Locale.US, format, color & mask)); + + showLed(color); + } + + private void showLed(int color) { + if (mShowLedPreview) { + if (color == 0xFFFFFFFF) { + // argb white doesn't work + color = 0xffffff; + } + mNoMan.forceShowLedLight(color); + } + } + + public void switchOffLed() { + if (mShowLedPreview) { + mNoMan.forceShowLedLight(-1); + } + } + + @Override + public void onStop() { + super.onStop(); + switchOffLed(); + } + + public void setAlphaSliderVisible(boolean visible) { + mHexColorInput.setFilters(new InputFilter[] { new InputFilter.LengthFilter(visible ? 8 : 6) } ); + mColorPicker.setAlphaSliderVisible(visible); + } + + public int getColor() { + if (mMultiColor){ + return mColorPicker.getColor(); + } else { + return mNewListColor.getColor(); + } + } + + class LedColorAdapter extends BaseAdapter implements SpinnerAdapter { + private ArrayList> mColors; + + public LedColorAdapter(int ledColorResource, int ledValueResource) { + mColors = new ArrayList>(); + + String[] color_names = getContext().getResources().getStringArray(ledColorResource); + String[] color_values = getContext().getResources().getStringArray(ledValueResource); + + for(int i = 0; i < color_values.length; ++i) { + try { + int color = Color.parseColor(color_values[i]); + mColors.add(new Pair(color_names[i], color)); + } catch (IllegalArgumentException ex) { + // Number format is incorrect, ignore entry + } + } + } + + /** + * Will return the position of the spinner entry with the specified + * color. Returns 0 if there is no such entry. + */ + public int getColorPosition(int color) { + for (int position = 0; position < getCount(); ++position) { + if (getItem(position).second.equals(color)) { + return position; + } + } + + return 0; + } + + public int getColor(int position) { + Pair item = getItem(position); + if (item != null){ + return item.second; + } + + // -1 is white + return -1; + } + + @Override + public int getCount() { + return mColors.size(); + } + + @Override + public Pair getItem(int position) { + return mColors.get(position); + } + + @Override + public long getItemId(int position) { + return position; + } + + @Override + public View getView(int position, View view, ViewGroup parent) { + if (view == null) { + view = mInflater.inflate(R.layout.led_color_item, null); + } + + Pair entry = getItem(position); + ((TextView) view.findViewById(R.id.textViewName)).setText(entry.first); + + return view; + } + } + + @Override + public void beforeTextChanged(CharSequence s, int start, int count, int after) { + } + + @Override + public void onTextChanged(CharSequence s, int start, int before, int count) { + } + + @Override + public void afterTextChanged(Editable s) { + String hexColor = mHexColorInput.getText().toString(); + if (!hexColor.isEmpty()) { + try { + int color = Color.parseColor('#' + hexColor); + if (!mWithAlpha) { + color |= 0xFF000000; // set opaque + } + mColorPicker.setColor(color); + mNewColor.setColor(color); + } catch (IllegalArgumentException ex) { + // Number format is incorrect, ignore + } + } + } + + @Override + public void onFocusChange(View v, boolean hasFocus) { + if (!hasFocus) { + mHexColorInput.removeTextChangedListener(this); + InputMethodManager inputMethodManager = (InputMethodManager) getContext() + .getSystemService(Activity.INPUT_METHOD_SERVICE); + inputMethodManager.hideSoftInputFromWindow(v.getWindowToken(), 0); + } else { + mHexColorInput.addTextChangedListener(this); + } + } +} diff --git a/src/com/cherish/settings/preferences/ColorSelectPreference.java b/src/com/cherish/settings/preferences/ColorSelectPreference.java new file mode 100644 index 0000000..f676c84 --- /dev/null +++ b/src/com/cherish/settings/preferences/ColorSelectPreference.java @@ -0,0 +1,188 @@ + +/* + * Copyright (C) 2012 The CyanogenMod Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.cherish.settings.preferences; + +import android.app.AlertDialog; +import android.app.Dialog; +import android.content.Context; +import android.content.DialogInterface; +import android.content.res.Resources; +import android.content.res.TypedArray; +import android.graphics.drawable.ShapeDrawable; +import android.graphics.drawable.shapes.RectShape; +import androidx.preference.Preference; +import androidx.preference.PreferenceViewHolder; +import android.util.AttributeSet; +import android.util.TypedValue; +import android.widget.ImageView; + +import com.cherish.settings.R; + +public class ColorSelectPreference extends Preference implements DialogInterface.OnDismissListener { + + private static String TAG = "ColorSelectPreference"; + public static final int DEFAULT_COLOR = 0xFFFFFF; //White + + private ImageView mLightColorView; + private Resources mResources; + private int mColorValue; + private Dialog mDialog; + + private boolean mShowLedPreview; + private boolean mShowMultiColor; + private boolean mWithAlpha; + + /** + * @param context + * @param attrs + */ + public ColorSelectPreference(Context context, AttributeSet attrs) { + super(context, attrs); + mColorValue = DEFAULT_COLOR; + init(context, attrs); + } + + public ColorSelectPreference(Context context, int color) { + super(context, null); + mColorValue = color; + init(context, null); + } + + public ColorSelectPreference(Context context, AttributeSet attrs, int defStyle) { + super(context, attrs, defStyle); + mColorValue = DEFAULT_COLOR; + init(context, attrs); + } + + private void init(Context context, AttributeSet attrs) { + setLayoutResource(R.layout.preference_color_select); + mResources = getContext().getResources(); + if (attrs != null) { + final TypedArray attributes = context.obtainStyledAttributes(attrs, + R.styleable.ColorSelectPreference); + final TypedValue useWithAlpha = attributes.peekValue( + R.styleable.ColorSelectPreference_withAlpha); + if (useWithAlpha != null) { + mWithAlpha = (useWithAlpha.type == TypedValue.TYPE_INT_BOOLEAN + && useWithAlpha.data != 0); + } + final TypedValue useLedPreview = attributes.peekValue( + R.styleable.ColorSelectPreference_ledPreview); + if (useLedPreview != null) { + mShowLedPreview = (useLedPreview.type == TypedValue.TYPE_INT_BOOLEAN + && useLedPreview.data != 0); + } + final TypedValue useMultiColor = attributes.peekValue( + R.styleable.ColorSelectPreference_multiColor); + if (useMultiColor != null) { + mShowMultiColor = (useMultiColor.type == TypedValue.TYPE_INT_BOOLEAN + && useMultiColor.data != 0); + } + } + } + + public void setColor(int color) { + mColorValue = color; + updatePreferenceViews(); + } + + public int getColor() { + return mColorValue; + } + + @Override + public void onBindViewHolder(PreferenceViewHolder holder) { + super.onBindViewHolder(holder); + + mLightColorView = (ImageView) holder.findViewById(R.id.light_color); + + updatePreferenceViews(); + } + + private void updatePreferenceViews() { + final int width = (int) mResources.getDimension(R.dimen.color_preference_width); + final int height = (int) mResources.getDimension(R.dimen.color_preference_height); + + if (mLightColorView != null) { + mLightColorView.setEnabled(true); + mLightColorView.setImageDrawable(createRectShape(width, height, 0xFF000000 | mColorValue)); + } + } + + @Override + protected void onClick() { + if (mDialog != null && mDialog.isShowing()) return; + mDialog = getDialog(); + mDialog.setOnDismissListener(this); + mDialog.show(); + } + + public Dialog getDialog() { + final ColorSelectDialog d = new ColorSelectDialog(getContext(), + 0xFF000000 | mColorValue, mShowMultiColor, mShowLedPreview, mWithAlpha); + + d.setButton(AlertDialog.BUTTON_POSITIVE, mResources.getString(android.R.string.ok), + new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + if (mShowLedPreview) { + mColorValue = d.getColor() & 0x00FFFFFF; // strip alpha, led does not support it + d.switchOffLed(); + } else { + mColorValue = d.getColor(); + } + updatePreferenceViews(); + callChangeListener(new Integer(mColorValue)); + } + }); + d.setButton(AlertDialog.BUTTON_NEGATIVE, mResources.getString(android.R.string.cancel), + new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + d.switchOffLed(); + } + }); + + return d; + } + + private static ShapeDrawable createRectShape(int width, int height, int color) { + ShapeDrawable shape = new ShapeDrawable(new RectShape()); + shape.setIntrinsicHeight(height); + shape.setIntrinsicWidth(width); + shape.getPaint().setColor(color); + return shape; + } + + @Override + public void onDismiss(DialogInterface dialog) { + mDialog = null; + } + + public void setWithAlpha(boolean value) { + mWithAlpha = value; + } + + public void setWithLedPreview(boolean value) { + mShowLedPreview = value; + } + + public void setWithMultiColor(boolean value) { + mShowMultiColor = value; + } +} diff --git a/src/com/cherish/settings/ui/AlphaPatternDrawable.java b/src/com/cherish/settings/ui/AlphaPatternDrawable.java new file mode 100644 index 0000000..bb204c1 --- /dev/null +++ b/src/com/cherish/settings/ui/AlphaPatternDrawable.java @@ -0,0 +1,125 @@ +/* + * Copyright (C) 2010 Daniel Nilsson + * Copyright (C) 2012 The CyanogenMod Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.cherish.settings.ui; + +import android.graphics.Bitmap; +import android.graphics.Canvas; +import android.graphics.ColorFilter; +import android.graphics.Paint; +import android.graphics.Rect; +import android.graphics.Bitmap.Config; +import android.graphics.drawable.Drawable; + +/** + * This drawable that draws a simple white and gray chess board pattern. It's + * pattern you will often see as a background behind a partly transparent image + * in many applications. + * + * @author Daniel Nilsson + */ +public class AlphaPatternDrawable extends Drawable { + + private int mRectangleSize = 10; + + private Paint mPaint = new Paint(); + private Paint mPaintWhite = new Paint(); + private Paint mPaintGray = new Paint(); + + private int numRectanglesHorizontal; + private int numRectanglesVertical; + + /** + * Bitmap in which the pattern will be cached. + */ + private Bitmap mBitmap; + + public AlphaPatternDrawable(int rectangleSize) { + mRectangleSize = rectangleSize; + mPaintWhite.setColor(0xffffffff); + mPaintGray.setColor(0xffcbcbcb); + } + + @Override + public void draw(Canvas canvas) { + if (mBitmap != null) { + canvas.drawBitmap(mBitmap, null, getBounds(), mPaint); + } + } + + @Override + public int getOpacity() { + return 0; + } + + @Override + public void setAlpha(int alpha) { + throw new UnsupportedOperationException("Alpha is not supported by this drawwable."); + } + + @Override + public void setColorFilter(ColorFilter cf) { + throw new UnsupportedOperationException("ColorFilter is not supported by this drawwable."); + } + + @Override + protected void onBoundsChange(Rect bounds) { + super.onBoundsChange(bounds); + + int height = bounds.height(); + int width = bounds.width(); + + numRectanglesHorizontal = (int) Math.ceil((width / mRectangleSize)); + numRectanglesVertical = (int) Math.ceil(height / mRectangleSize); + + generatePatternBitmap(); + } + + /** + * This will generate a bitmap with the pattern as big as the rectangle we + * were allow to draw on. We do this to cache the bitmap so we don't need + * to recreate it each time draw() is called since it takes a few + * milliseconds. + */ + private void generatePatternBitmap() { + + if (getBounds().width() <= 0 || getBounds().height() <= 0) { + return; + } + + mBitmap = Bitmap.createBitmap(getBounds().width(), getBounds().height(), Config.ARGB_8888); + Canvas canvas = new Canvas(mBitmap); + + Rect r = new Rect(); + boolean verticalStartWhite = true; + for (int i = 0; i <= numRectanglesVertical; i++) { + boolean isWhite = verticalStartWhite; + for (int j = 0; j <= numRectanglesHorizontal; j++) { + r.top = i * mRectangleSize; + r.left = j * mRectangleSize; + r.bottom = r.top + mRectangleSize; + r.right = r.left + mRectangleSize; + + canvas.drawRect(r, isWhite ? mPaintWhite : mPaintGray); + + isWhite = !isWhite; + } + + verticalStartWhite = !verticalStartWhite; + } + } +} diff --git a/src/com/cherish/settings/ui/ColorPanelView.java b/src/com/cherish/settings/ui/ColorPanelView.java new file mode 100644 index 0000000..195aae4 --- /dev/null +++ b/src/com/cherish/settings/ui/ColorPanelView.java @@ -0,0 +1,170 @@ +/* + * Copyright (C) 2010 Daniel Nilsson + * Copyright (C) 2012 The CyanogenMod Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.cherish.settings.ui; + +import android.content.Context; +import android.graphics.Canvas; +import android.graphics.Paint; +import android.graphics.RectF; +import android.util.AttributeSet; +import android.view.View; + +/** + * This class draws a panel which which will be filled with a color which can be + * set. It can be used to show the currently selected color which you will get + * from the {@link ColorPickerView}. + * + * @author Daniel Nilsson + */ +public class ColorPanelView extends View { + + /** + * The width in pixels of the border surrounding the color panel. + */ + private final static float BORDER_WIDTH_PX = 1; + + private static float mDensity = 1f; + + private int mBorderColor = 0xff6E6E6E; + private int mColor = 0xff000000; + + private Paint mBorderPaint; + private Paint mColorPaint; + + private RectF mDrawingRect; + private RectF mColorRect; + + private AlphaPatternDrawable mAlphaPattern; + + public ColorPanelView(Context context) { + this(context, null); + } + + public ColorPanelView(Context context, AttributeSet attrs) { + this(context, attrs, 0); + } + + public ColorPanelView(Context context, AttributeSet attrs, int defStyle) { + super(context, attrs, defStyle); + + init(); + } + + private void init() { + mBorderPaint = new Paint(); + mColorPaint = new Paint(); + mDensity = getContext().getResources().getDisplayMetrics().density; + } + + @Override + protected void onDraw(Canvas canvas) { + + final RectF rect = mColorRect; + + if (BORDER_WIDTH_PX > 0) { + mBorderPaint.setColor(mBorderColor); + canvas.drawRect(mDrawingRect, mBorderPaint); + } + + if (mAlphaPattern != null) { + mAlphaPattern.draw(canvas); + } + + mColorPaint.setColor(mColor); + + canvas.drawRect(rect, mColorPaint); + } + + @Override + protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { + + int width = MeasureSpec.getSize(widthMeasureSpec); + int height = MeasureSpec.getSize(heightMeasureSpec); + + setMeasuredDimension(width, height); + } + + @Override + protected void onSizeChanged(int w, int h, int oldw, int oldh) { + super.onSizeChanged(w, h, oldw, oldh); + + mDrawingRect = new RectF(); + mDrawingRect.left = getPaddingLeft(); + mDrawingRect.right = w - getPaddingRight(); + mDrawingRect.top = getPaddingTop(); + mDrawingRect.bottom = h - getPaddingBottom(); + + setUpColorRect(); + + } + + private void setUpColorRect() { + final RectF dRect = mDrawingRect; + + float left = dRect.left + BORDER_WIDTH_PX; + float top = dRect.top + BORDER_WIDTH_PX; + float bottom = dRect.bottom - BORDER_WIDTH_PX; + float right = dRect.right - BORDER_WIDTH_PX; + + mColorRect = new RectF(left, top, right, bottom); + + mAlphaPattern = new AlphaPatternDrawable((int) (5 * mDensity)); + + mAlphaPattern.setBounds(Math.round(mColorRect.left), + Math.round(mColorRect.top), + Math.round(mColorRect.right), + Math.round(mColorRect.bottom)); + + } + + /** + * Set the color that should be shown by this view. + * + * @param color + */ + public void setColor(int color) { + mColor = color; + invalidate(); + } + + /** + * Get the color currently show by this view. + * + * @return + */ + public int getColor() { + return mColor; + } + + /** + * Set the color of the border surrounding the panel. + * + * @param color + */ + public void setBorderColor(int color) { + mBorderColor = color; + invalidate(); + } + + /** + * Get the color of the border surrounding the panel. + */ + public int getBorderColor() { + return mBorderColor; + } +} diff --git a/src/com/cherish/settings/ui/ColorPickerView.java b/src/com/cherish/settings/ui/ColorPickerView.java new file mode 100644 index 0000000..87f5df7 --- /dev/null +++ b/src/com/cherish/settings/ui/ColorPickerView.java @@ -0,0 +1,841 @@ +/* + * Copyright (C) 2010 Daniel Nilsson + * Copyright (C) 2012 The CyanogenMod Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.cherish.settings.ui; + +import android.content.Context; +import android.graphics.Canvas; +import android.graphics.Color; +import android.graphics.ComposeShader; +import android.graphics.LinearGradient; +import android.graphics.Paint; +import android.graphics.Point; +import android.graphics.PorterDuff.Mode; +import android.graphics.RectF; +import android.graphics.Shader; +import android.graphics.Paint.Align; +import android.graphics.Paint.Style; +import android.graphics.Shader.TileMode; +import android.os.Build; +import android.util.AttributeSet; +import android.view.MotionEvent; +import android.view.View; + +/** + * Displays a color picker to the user and allow them to select a color. A + * slider for the alpha channel is also available. Enable it by setting + * setAlphaSliderVisible(boolean) to true. + * + * @author Daniel Nilsson + */ +public class ColorPickerView extends View { + + public interface OnColorChangedListener { + public void onColorChanged(int color); + } + + private final static int PANEL_SAT_VAL = 0; + private final static int PANEL_HUE = 1; + private final static int PANEL_ALPHA = 2; + + /** + * The width in pixels of the border surrounding all color panels. + */ + private final static float BORDER_WIDTH_PX = 1; + + /** + * The width in dp of the hue panel. + */ + private float HUE_PANEL_WIDTH = 30f; + /** + * The height in dp of the alpha panel + */ + private float ALPHA_PANEL_HEIGHT = 20f; + /** + * The distance in dp between the different color panels. + */ + private float PANEL_SPACING = 10f; + /** + * The radius in dp of the color palette tracker circle. + */ + private float PALETTE_CIRCLE_TRACKER_RADIUS = 5f; + /** + * The dp which the tracker of the hue or alpha panel will extend outside of + * its bounds. + */ + private float RECTANGLE_TRACKER_OFFSET = 2f; + + private static float mDensity = 1f; + + private OnColorChangedListener mListener; + + private Paint mSatValPaint; + private Paint mSatValTrackerPaint; + + private Paint mHuePaint; + private Paint mHueTrackerPaint; + + private Paint mAlphaPaint; + private Paint mAlphaTextPaint; + + private Paint mBorderPaint; + + private Shader mValShader; + private Shader mSatShader; + private Shader mHueShader; + private Shader mAlphaShader; + + private int mAlpha = 0xff; + private float mHue = 360f; + private float mSat = 0f; + private float mVal = 0f; + + private String mAlphaSliderText = "Alpha"; + private int mSliderTrackerColor = 0xff1c1c1c; + private int mBorderColor = 0xff6E6E6E; + private boolean mShowAlphaPanel = false; + + /* + * To remember which panel that has the "focus" when processing hardware + * button data. + */ + private int mLastTouchedPanel = PANEL_SAT_VAL; + + /** + * Offset from the edge we must have or else the finger tracker will get + * clipped when it is drawn outside of the view. + */ + private float mDrawingOffset; + + /* + * Distance form the edges of the view of where we are allowed to draw. + */ + private RectF mDrawingRect; + + private RectF mSatValRect; + private RectF mHueRect; + private RectF mAlphaRect; + + private AlphaPatternDrawable mAlphaPattern; + + private Point mStartTouchPoint = null; + + public ColorPickerView(Context context) { + this(context, null); + } + + public ColorPickerView(Context context, AttributeSet attrs) { + this(context, attrs, 0); + } + + public ColorPickerView(Context context, AttributeSet attrs, int defStyle) { + super(context, attrs, defStyle); + init(); + } + + private void init() { + mDensity = getContext().getResources().getDisplayMetrics().density; + PALETTE_CIRCLE_TRACKER_RADIUS *= mDensity; + RECTANGLE_TRACKER_OFFSET *= mDensity; + HUE_PANEL_WIDTH *= mDensity; + ALPHA_PANEL_HEIGHT *= mDensity; + PANEL_SPACING = PANEL_SPACING * mDensity; + + mDrawingOffset = calculateRequiredOffset(); + initPaintTools(); + + // Needed for receiving track ball motion events. + setFocusableInTouchMode(true); + setFocusable(true); + setClickable(true); + } + + private void initPaintTools() { + mSatValPaint = new Paint(); + mSatValTrackerPaint = new Paint(); + mHuePaint = new Paint(); + mHueTrackerPaint = new Paint(); + mAlphaPaint = new Paint(); + mAlphaTextPaint = new Paint(); + mBorderPaint = new Paint(); + + mSatValTrackerPaint.setStyle(Style.STROKE); + mSatValTrackerPaint.setStrokeWidth(2f * mDensity); + mSatValTrackerPaint.setAntiAlias(true); + + mHueTrackerPaint.setColor(mSliderTrackerColor); + mHueTrackerPaint.setStyle(Style.STROKE); + mHueTrackerPaint.setStrokeWidth(2f * mDensity); + mHueTrackerPaint.setAntiAlias(true); + + mAlphaTextPaint.setColor(0xff1c1c1c); + mAlphaTextPaint.setTextSize(14f * mDensity); + mAlphaTextPaint.setAntiAlias(true); + mAlphaTextPaint.setTextAlign(Align.CENTER); + mAlphaTextPaint.setFakeBoldText(true); + } + + private float calculateRequiredOffset() { + float offset = Math.max(PALETTE_CIRCLE_TRACKER_RADIUS, RECTANGLE_TRACKER_OFFSET); + offset = Math.max(offset, BORDER_WIDTH_PX * mDensity); + + return offset * 1.5f; + } + + private int[] buildHueColorArray() { + int[] hue = new int[361]; + + int count = 0; + for (int i = hue.length - 1; i >= 0; i--, count++) { + hue[count] = Color.HSVToColor(new float[] { + i, 1f, 1f + }); + } + return hue; + } + + @Override + protected void onDraw(Canvas canvas) { + if (mDrawingRect.width() <= 0 || mDrawingRect.height() <= 0) { + return; + } + drawSatValPanel(canvas); + drawHuePanel(canvas); + drawAlphaPanel(canvas); + } + + private void drawSatValPanel(Canvas canvas) { + final RectF rect = mSatValRect; + int rgb = Color.HSVToColor(new float[] { + mHue, 1f, 1f + }); + + if (BORDER_WIDTH_PX > 0) { + mBorderPaint.setColor(mBorderColor); + canvas.drawRect(mDrawingRect.left, mDrawingRect.top, rect.right + BORDER_WIDTH_PX, + rect.bottom + BORDER_WIDTH_PX, mBorderPaint); + } + + // On Honeycomb+ we need to use software rendering to create the shader properly + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) { + setLayerType(View.LAYER_TYPE_SOFTWARE, null); + } + + // Get the overlaying gradients ready and create the ComposeShader + if (mValShader == null) { + mValShader = new LinearGradient(rect.left, rect.top, rect.left, rect.bottom, + 0xffffffff, 0xff000000, TileMode.CLAMP); + } + mSatShader = new LinearGradient(rect.left, rect.top, rect.right, rect.top, + 0xffffffff, rgb, TileMode.CLAMP); + ComposeShader mShader = new ComposeShader(mValShader, mSatShader, Mode.MULTIPLY); + mSatValPaint.setShader(mShader); + canvas.drawRect(rect, mSatValPaint); + + Point p = satValToPoint(mSat, mVal); + mSatValTrackerPaint.setColor(0xff000000); + canvas.drawCircle(p.x, p.y, PALETTE_CIRCLE_TRACKER_RADIUS - 1f * mDensity, + mSatValTrackerPaint); + + mSatValTrackerPaint.setColor(0xffdddddd); + canvas.drawCircle(p.x, p.y, PALETTE_CIRCLE_TRACKER_RADIUS, mSatValTrackerPaint); + } + + private void drawHuePanel(Canvas canvas) { + final RectF rect = mHueRect; + + if (BORDER_WIDTH_PX > 0) { + mBorderPaint.setColor(mBorderColor); + canvas.drawRect(rect.left - BORDER_WIDTH_PX, + rect.top - BORDER_WIDTH_PX, + rect.right + BORDER_WIDTH_PX, + rect.bottom + BORDER_WIDTH_PX, + mBorderPaint); + } + + if (mHueShader == null) { + mHueShader = new LinearGradient(rect.left, rect.top, rect.left, rect.bottom, + buildHueColorArray(), null, TileMode.CLAMP); + mHuePaint.setShader(mHueShader); + } + + canvas.drawRect(rect, mHuePaint); + + float rectHeight = 4 * mDensity / 2; + + Point p = hueToPoint(mHue); + + RectF r = new RectF(); + r.left = rect.left - RECTANGLE_TRACKER_OFFSET; + r.right = rect.right + RECTANGLE_TRACKER_OFFSET; + r.top = p.y - rectHeight; + r.bottom = p.y + rectHeight; + + canvas.drawRoundRect(r, 2, 2, mHueTrackerPaint); + + } + + private void drawAlphaPanel(Canvas canvas) { + if (!mShowAlphaPanel || mAlphaRect == null || mAlphaPattern == null) { + return; + } + + final RectF rect = mAlphaRect; + + if (BORDER_WIDTH_PX > 0) { + mBorderPaint.setColor(mBorderColor); + canvas.drawRect(rect.left - BORDER_WIDTH_PX, + rect.top - BORDER_WIDTH_PX, + rect.right + BORDER_WIDTH_PX, + rect.bottom + BORDER_WIDTH_PX, + mBorderPaint); + } + + mAlphaPattern.draw(canvas); + + float[] hsv = new float[] { + mHue, mSat, mVal + }; + int color = Color.HSVToColor(hsv); + int acolor = Color.HSVToColor(0, hsv); + + mAlphaShader = new LinearGradient(rect.left, rect.top, rect.right, rect.top, + color, acolor, TileMode.CLAMP); + + mAlphaPaint.setShader(mAlphaShader); + + canvas.drawRect(rect, mAlphaPaint); + + if (mAlphaSliderText != null && mAlphaSliderText != "") { + canvas.drawText(mAlphaSliderText, rect.centerX(), rect.centerY() + 4 * mDensity, + mAlphaTextPaint); + } + + float rectWidth = 4 * mDensity / 2; + Point p = alphaToPoint(mAlpha); + + RectF r = new RectF(); + r.left = p.x - rectWidth; + r.right = p.x + rectWidth; + r.top = rect.top - RECTANGLE_TRACKER_OFFSET; + r.bottom = rect.bottom + RECTANGLE_TRACKER_OFFSET; + + canvas.drawRoundRect(r, 2, 2, mHueTrackerPaint); + } + + private Point hueToPoint(float hue) { + final RectF rect = mHueRect; + final float height = rect.height(); + + Point p = new Point(); + p.y = (int) (height - (hue * height / 360f) + rect.top); + p.x = (int) rect.left; + return p; + } + + private Point satValToPoint(float sat, float val) { + + final RectF rect = mSatValRect; + final float height = rect.height(); + final float width = rect.width(); + + Point p = new Point(); + + p.x = (int) (sat * width + rect.left); + p.y = (int) ((1f - val) * height + rect.top); + + return p; + } + + private Point alphaToPoint(int alpha) { + final RectF rect = mAlphaRect; + final float width = rect.width(); + + Point p = new Point(); + p.x = (int) (width - (alpha * width / 0xff) + rect.left); + p.y = (int) rect.top; + return p; + } + + private float[] pointToSatVal(float x, float y) { + final RectF rect = mSatValRect; + float[] result = new float[2]; + float width = rect.width(); + float height = rect.height(); + + if (x < rect.left) { + x = 0f; + } else if (x > rect.right) { + x = width; + } else { + x = x - rect.left; + } + + if (y < rect.top) { + y = 0f; + } else if (y > rect.bottom) { + y = height; + } else { + y = y - rect.top; + } + + result[0] = 1.f / width * x; + result[1] = 1.f - (1.f / height * y); + return result; + } + + private float pointToHue(float y) { + final RectF rect = mHueRect; + float height = rect.height(); + + if (y < rect.top) { + y = 0f; + } else if (y > rect.bottom) { + y = height; + } else { + y = y - rect.top; + } + return 360f - (y * 360f / height); + } + + private int pointToAlpha(int x) { + final RectF rect = mAlphaRect; + final int width = (int) rect.width(); + + if (x < rect.left) { + x = 0; + } else if (x > rect.right) { + x = width; + } else { + x = x - (int) rect.left; + } + return 0xff - (x * 0xff / width); + } + + @Override + public boolean onTrackballEvent(MotionEvent event) { + float x = event.getX(); + float y = event.getY(); + boolean update = false; + + if (event.getAction() == MotionEvent.ACTION_MOVE) { + switch (mLastTouchedPanel) { + case PANEL_SAT_VAL: + float sat, + val; + sat = mSat + x / 50f; + val = mVal - y / 50f; + if (sat < 0f) { + sat = 0f; + } else if (sat > 1f) { + sat = 1f; + } + + if (val < 0f) { + val = 0f; + } else if (val > 1f) { + val = 1f; + } + mSat = sat; + mVal = val; + update = true; + break; + case PANEL_HUE: + float hue = mHue - y * 10f; + if (hue < 0f) { + hue = 0f; + } else if (hue > 360f) { + hue = 360f; + } + mHue = hue; + update = true; + break; + case PANEL_ALPHA: + if (!mShowAlphaPanel || mAlphaRect == null) { + update = false; + } else { + int alpha = (int) (mAlpha - x * 10); + if (alpha < 0) { + alpha = 0; + } else if (alpha > 0xff) { + alpha = 0xff; + } + mAlpha = alpha; + update = true; + } + break; + } + } + + if (update) { + if (mListener != null) { + mListener.onColorChanged(Color.HSVToColor(mAlpha, new float[] { + mHue, mSat, mVal + })); + } + invalidate(); + return true; + } + return super.onTrackballEvent(event); + } + + @Override + public boolean onTouchEvent(MotionEvent event) { + boolean update = false; + + switch (event.getAction()) { + case MotionEvent.ACTION_DOWN: + mStartTouchPoint = new Point((int) event.getX(), (int) event.getY()); + update = moveTrackersIfNeeded(event); + break; + case MotionEvent.ACTION_MOVE: + update = moveTrackersIfNeeded(event); + break; + case MotionEvent.ACTION_UP: + mStartTouchPoint = null; + update = moveTrackersIfNeeded(event); + break; + } + + if (update) { + requestFocus(); + if (mListener != null) { + mListener.onColorChanged(Color.HSVToColor(mAlpha, new float[] { + mHue, mSat, mVal + })); + } + invalidate(); + return true; + } + + return super.onTouchEvent(event); + } + + private boolean moveTrackersIfNeeded(MotionEvent event) { + + if (mStartTouchPoint == null) + return false; + + boolean update = false; + int startX = mStartTouchPoint.x; + int startY = mStartTouchPoint.y; + + if (mHueRect.contains(startX, startY)) { + mLastTouchedPanel = PANEL_HUE; + mHue = pointToHue(event.getY()); + update = true; + } else if (mSatValRect.contains(startX, startY)) { + mLastTouchedPanel = PANEL_SAT_VAL; + float[] result = pointToSatVal(event.getX(), event.getY()); + mSat = result[0]; + mVal = result[1]; + update = true; + } else if (mAlphaRect != null && mAlphaRect.contains(startX, startY)) { + mLastTouchedPanel = PANEL_ALPHA; + mAlpha = pointToAlpha((int) event.getX()); + update = true; + } + + return update; + } + + @Override + protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { + int width = 0; + int height = 0; + + int widthMode = MeasureSpec.getMode(widthMeasureSpec); + int heightMode = MeasureSpec.getMode(heightMeasureSpec); + + int widthAllowed = MeasureSpec.getSize(widthMeasureSpec); + int heightAllowed = MeasureSpec.getSize(heightMeasureSpec); + + widthAllowed = chooseWidth(widthMode, widthAllowed); + heightAllowed = chooseHeight(heightMode, heightAllowed); + + if (!mShowAlphaPanel) { + height = (int) (widthAllowed - PANEL_SPACING - HUE_PANEL_WIDTH); + + // If calculated height (based on the width) is more than the + // allowed height. + if (height > heightAllowed && heightMode != MeasureSpec.UNSPECIFIED) { + height = heightAllowed; + width = (int) (height + PANEL_SPACING + HUE_PANEL_WIDTH); + } else { + width = widthAllowed; + } + } else { + + width = (int) (heightAllowed - ALPHA_PANEL_HEIGHT + HUE_PANEL_WIDTH); + + if (width > widthAllowed && widthMode != MeasureSpec.UNSPECIFIED) { + width = widthAllowed; + height = (int) (widthAllowed - HUE_PANEL_WIDTH + ALPHA_PANEL_HEIGHT); + } else { + height = heightAllowed; + } + } + setMeasuredDimension(width, height); + } + + private int chooseWidth(int mode, int size) { + if (mode == MeasureSpec.AT_MOST || mode == MeasureSpec.EXACTLY) { + return size; + } else { // (mode == MeasureSpec.UNSPECIFIED) + return getPrefferedWidth(); + } + } + + private int chooseHeight(int mode, int size) { + if (mode == MeasureSpec.AT_MOST || mode == MeasureSpec.EXACTLY) { + return size; + } else { // (mode == MeasureSpec.UNSPECIFIED) + return getPrefferedHeight(); + } + } + + private int getPrefferedWidth() { + int width = getPrefferedHeight(); + if (mShowAlphaPanel) { + width -= (PANEL_SPACING + ALPHA_PANEL_HEIGHT); + } + return (int) (width + HUE_PANEL_WIDTH + PANEL_SPACING); + } + + private int getPrefferedHeight() { + int height = (int) (200 * mDensity); + if (mShowAlphaPanel) { + height += PANEL_SPACING + ALPHA_PANEL_HEIGHT; + } + return height; + } + + @Override + protected void onSizeChanged(int w, int h, int oldw, int oldh) { + super.onSizeChanged(w, h, oldw, oldh); + + mDrawingRect = new RectF(); + mDrawingRect.left = mDrawingOffset + getPaddingLeft(); + mDrawingRect.right = w - mDrawingOffset - getPaddingRight(); + mDrawingRect.top = mDrawingOffset + getPaddingTop(); + mDrawingRect.bottom = h - mDrawingOffset - getPaddingBottom(); + + setUpSatValRect(); + setUpHueRect(); + setUpAlphaRect(); + } + + private void setUpSatValRect() { + final RectF dRect = mDrawingRect; + float panelSide = dRect.height() - BORDER_WIDTH_PX * 2; + + if (mShowAlphaPanel) { + panelSide -= PANEL_SPACING + ALPHA_PANEL_HEIGHT; + } + + float left = dRect.left + BORDER_WIDTH_PX; + float top = dRect.top + BORDER_WIDTH_PX; + float bottom = top + panelSide; + float right = left + panelSide; + mSatValRect = new RectF(left, top, right, bottom); + } + + private void setUpHueRect() { + final RectF dRect = mDrawingRect; + + float left = dRect.right - HUE_PANEL_WIDTH + BORDER_WIDTH_PX; + float top = dRect.top + BORDER_WIDTH_PX; + float bottom = dRect.bottom - BORDER_WIDTH_PX + - (mShowAlphaPanel ? (PANEL_SPACING + ALPHA_PANEL_HEIGHT) : 0); + float right = dRect.right - BORDER_WIDTH_PX; + + mHueRect = new RectF(left, top, right, bottom); + } + + private void setUpAlphaRect() { + if (!mShowAlphaPanel) { + return; + } + + final RectF dRect = mDrawingRect; + float left = dRect.left + BORDER_WIDTH_PX; + float top = dRect.bottom - ALPHA_PANEL_HEIGHT + BORDER_WIDTH_PX; + float bottom = dRect.bottom - BORDER_WIDTH_PX; + float right = dRect.right - BORDER_WIDTH_PX; + + mAlphaRect = new RectF(left, top, right, bottom); + mAlphaPattern = new AlphaPatternDrawable((int) (5 * mDensity)); + mAlphaPattern.setBounds(Math.round(mAlphaRect.left), Math + .round(mAlphaRect.top), Math.round(mAlphaRect.right), Math + .round(mAlphaRect.bottom)); + } + + /** + * Set a OnColorChangedListener to get notified when the color selected by + * the user has changed. + * + * @param listener + */ + public void setOnColorChangedListener(OnColorChangedListener listener) { + mListener = listener; + } + + /** + * Set the color of the border surrounding all panels. + * + * @param color + */ + public void setBorderColor(int color) { + mBorderColor = color; + invalidate(); + } + + /** + * Get the color of the border surrounding all panels. + */ + public int getBorderColor() { + return mBorderColor; + } + + /** + * Get the current color this view is showing. + * + * @return the current color. + */ + public int getColor() { + return Color.HSVToColor(mAlpha, new float[] { + mHue, mSat, mVal + }); + } + + /** + * Set the color the view should show. + * + * @param color The color that should be selected. + */ + public void setColor(int color) { + setColor(color, false); + } + + /** + * Set the color this view should show. + * + * @param color The color that should be selected. + * @param callback If you want to get a callback to your + * OnColorChangedListener. + */ + public void setColor(int color, boolean callback) { + int alpha = Color.alpha(color); + int red = Color.red(color); + int blue = Color.blue(color); + int green = Color.green(color); + float[] hsv = new float[3]; + + Color.RGBToHSV(red, green, blue, hsv); + mAlpha = alpha; + mHue = hsv[0]; + mSat = hsv[1]; + mVal = hsv[2]; + + if (callback && mListener != null) { + mListener.onColorChanged(Color.HSVToColor(mAlpha, new float[] { + mHue, mSat, mVal + })); + } + invalidate(); + } + + /** + * Get the drawing offset of the color picker view. The drawing offset is + * the distance from the side of a panel to the side of the view minus the + * padding. Useful if you want to have your own panel below showing the + * currently selected color and want to align it perfectly. + * + * @return The offset in pixels. + */ + public float getDrawingOffset() { + return mDrawingOffset; + } + + /** + * Set if the user is allowed to adjust the alpha panel. Default is false. + * If it is set to false no alpha will be set. + * + * @param visible + */ + public void setAlphaSliderVisible(boolean visible) { + if (mShowAlphaPanel != visible) { + mShowAlphaPanel = visible; + + /* + * Reset all shader to force a recreation. Otherwise they will not + * look right after the size of the view has changed. + */ + mValShader = null; + mSatShader = null; + mHueShader = null; + mAlphaShader = null; + requestLayout(); + } + + } + + public boolean isAlphaSliderVisible() { + return mShowAlphaPanel; + } + + public void setSliderTrackerColor(int color) { + mSliderTrackerColor = color; + mHueTrackerPaint.setColor(mSliderTrackerColor); + invalidate(); + } + + public int getSliderTrackerColor() { + return mSliderTrackerColor; + } + + /** + * Set the text that should be shown in the alpha slider. Set to null to + * disable text. + * + * @param res string resource id. + */ + public void setAlphaSliderText(int res) { + String text = getContext().getString(res); + setAlphaSliderText(text); + } + + /** + * Set the text that should be shown in the alpha slider. Set to null to + * disable text. + * + * @param text Text that should be shown. + */ + public void setAlphaSliderText(String text) { + mAlphaSliderText = text; + invalidate(); + } + + /** + * Get the current value of the text that will be shown in the alpha slider. + * + * @return + */ + public String getAlphaSliderText() { + return mAlphaSliderText; + } +}