diff --git a/app/src/main/java/org/solovyev/android/calculator/Keyboard.java b/app/src/main/java/org/solovyev/android/calculator/Keyboard.java index 4b37ea06..4adbf7d4 100644 --- a/app/src/main/java/org/solovyev/android/calculator/Keyboard.java +++ b/app/src/main/java/org/solovyev/android/calculator/Keyboard.java @@ -26,10 +26,9 @@ import android.content.SharedPreferences; import android.support.annotation.NonNull; import android.text.TextUtils; import android.util.Log; + import com.squareup.otto.Bus; -import dagger.Lazy; -import jscl.math.Expression; -import jscl.math.Generic; + import org.solovyev.android.Check; import org.solovyev.android.calculator.buttons.CppSpecialButton; import org.solovyev.android.calculator.ga.Ga; @@ -42,6 +41,10 @@ import javax.annotation.Nullable; import javax.inject.Inject; import javax.inject.Singleton; +import dagger.Lazy; +import jscl.math.Expression; +import jscl.math.Generic; + @Singleton public class Keyboard implements SharedPreferences.OnSharedPreferenceChangeListener { @@ -69,17 +72,23 @@ public class Keyboard implements SharedPreferences.OnSharedPreferenceChangeListe @Inject ActivityLauncher launcher; private boolean vibrateOnKeypress; + private boolean highContrast; @Inject public Keyboard(@Nonnull SharedPreferences preferences) { preferences.registerOnSharedPreferenceChangeListener(this); vibrateOnKeypress = Preferences.Gui.vibrateOnKeypress.getPreference(preferences); + highContrast = Preferences.Gui.highContrast.getPreference(preferences); } public boolean isVibrateOnKeypress() { return vibrateOnKeypress; } + public boolean isHighContrast() { + return highContrast; + } + public boolean buttonPressed(@Nullable String text) { if (TextUtils.isEmpty(text)) { return false; @@ -292,6 +301,8 @@ public class Keyboard implements SharedPreferences.OnSharedPreferenceChangeListe public void onSharedPreferenceChanged(SharedPreferences preferences, String key) { if (Preferences.Gui.vibrateOnKeypress.isSameKey(key)) { vibrateOnKeypress = Preferences.Gui.vibrateOnKeypress.getPreference(preferences); + } else if (Preferences.Gui.highContrast.isSameKey(key)) { + highContrast = Preferences.Gui.highContrast.getPreference(preferences); } } } diff --git a/app/src/main/java/org/solovyev/android/calculator/Preferences.java b/app/src/main/java/org/solovyev/android/calculator/Preferences.java index e2966ae5..b9549f09 100644 --- a/app/src/main/java/org/solovyev/android/calculator/Preferences.java +++ b/app/src/main/java/org/solovyev/android/calculator/Preferences.java @@ -47,6 +47,7 @@ import org.solovyev.android.prefs.*; import javax.annotation.Nonnull; import javax.annotation.Nullable; + import java.util.EnumMap; import java.util.Map; @@ -54,7 +55,7 @@ import static org.solovyev.android.prefs.IntegerPreference.DEF_VALUE; public final class Preferences { - private static final Preference version = IntegerPreference.of("version", 2); + private static final Preference version = IntegerPreference.of("version", 3); private Preferences() { throw new AssertionError(); @@ -86,6 +87,11 @@ public final class Preferences { } version.putDefault(editor); editor.apply(); + } else if (currentVersion == 2) { + final SharedPreferences.Editor editor = preferences.edit(); + Gui.highContrast.tryPutDefault(preferences, editor); + version.putDefault(editor); + editor.apply(); } } @@ -112,6 +118,7 @@ public final class Preferences { Gui.rotateScreen.tryPutDefault(preferences, editor); Gui.keepScreenOn.tryPutDefault(preferences, editor); Gui.language.tryPutDefault(preferences, editor); + Gui.highContrast.tryPutDefault(preferences, editor); Calculations.calculateOnFly.tryPutDefault(preferences, editor); @@ -250,6 +257,7 @@ public final class Preferences { public static final Preference useBackAsPrevious = BooleanPreference.of("gui.useBackAsPrevious", false); public static final Preference rotateScreen = BooleanPreference.of("gui.rotateScreen", true); public static final Preference keepScreenOn = BooleanPreference.of("gui.keepScreenOn", true); + public static final Preference highContrast = BooleanPreference.of("gui.highContrast", false); public static final Preference vibrateOnKeypress = BooleanPreference.of("gui.vibrateOnKeypress", true); @Nonnull diff --git a/app/src/main/java/org/solovyev/android/calculator/keyboard/BaseKeyboardUi.java b/app/src/main/java/org/solovyev/android/calculator/keyboard/BaseKeyboardUi.java index ee7c45fd..98799cf4 100644 --- a/app/src/main/java/org/solovyev/android/calculator/keyboard/BaseKeyboardUi.java +++ b/app/src/main/java/org/solovyev/android/calculator/keyboard/BaseKeyboardUi.java @@ -143,6 +143,7 @@ public abstract class BaseKeyboardUi implements SharedPreferences.OnSharedPrefer } dragButtons.add(button); button.setVibrateOnDrag(keyboard.isVibrateOnKeypress()); + button.setHighContrast(keyboard.isHighContrast()); prepareButton((View) button); button.setOnDragListener(listener); button.setTextSize(TypedValue.COMPLEX_UNIT_PX, textSize); @@ -187,6 +188,11 @@ public abstract class BaseKeyboardUi implements SharedPreferences.OnSharedPrefer for (DragView dragButton : dragButtons) { dragButton.setVibrateOnDrag(vibrate); } + } else if (Preferences.Gui.highContrast.isSameKey(key)) { + final boolean highContrast = Preferences.Gui.highContrast.getPreference(preferences); + for (DragView dragButton : dragButtons) { + dragButton.setHighContrast(highContrast); + } } } diff --git a/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionDragButton.java b/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionDragButton.java index 127a809c..3d44f3e2 100644 --- a/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionDragButton.java +++ b/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionDragButton.java @@ -10,10 +10,16 @@ import android.util.AttributeSet; import javax.annotation.Nonnull; +import static android.graphics.Color.BLACK; +import static android.util.TypedValue.COMPLEX_UNIT_DIP; +import static android.util.TypedValue.applyDimension; +import static org.solovyev.android.views.dragbutton.DirectionTextView.SHADOW_RADIUS_DPS; + public class DirectionDragButton extends DragButton implements DirectionDragView { private final DirectionTextView textView = new DirectionTextView(); @NonNull private final TextPaint baseTextPaint = new TextPaint(); + private boolean highContrast; public DirectionDragButton(Context context) { super(context); @@ -86,4 +92,18 @@ public class DirectionDragButton extends DragButton implements DirectionDragView getText(direction).setAlpha(alpha); } } + + @Override + public void setHighContrast(boolean highContrast) { + if(this.highContrast == highContrast) { + return; + } + this.highContrast = highContrast; + this.textView.setHighContrast(highContrast); + if (highContrast) { + setShadowLayer(applyDimension(COMPLEX_UNIT_DIP, SHADOW_RADIUS_DPS, getResources().getDisplayMetrics()), 0, 0, BLACK); + } else { + setShadowLayer(0, 0, 0, BLACK); + } + } } diff --git a/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionDragImageButton.java b/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionDragImageButton.java index 9cdc759b..9b882723 100644 --- a/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionDragImageButton.java +++ b/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionDragImageButton.java @@ -69,4 +69,8 @@ public class DirectionDragImageButton extends DragImageButton implements Directi public float getTextSize() { return baseTextPaint.getTextSize(); } + + @Override + public void setHighContrast(boolean highContrast) { + } } diff --git a/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionTextView.java b/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionTextView.java index d401d2d5..f268318c 100644 --- a/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionTextView.java +++ b/app/src/main/java/org/solovyev/android/views/dragbutton/DirectionTextView.java @@ -2,7 +2,11 @@ package org.solovyev.android.views.dragbutton; import android.content.Context; import android.content.res.TypedArray; -import android.graphics.*; +import android.graphics.Canvas; +import android.graphics.Color; +import android.graphics.PointF; +import android.graphics.Rect; +import android.graphics.Typeface; import android.support.annotation.NonNull; import android.support.annotation.Nullable; import android.text.TextPaint; @@ -10,17 +14,24 @@ import android.text.TextUtils; import android.util.AttributeSet; import android.view.View; import android.widget.TextView; + import com.google.common.base.Strings; + import org.solovyev.android.Check; import org.solovyev.android.calculator.R; import java.util.EnumMap; import java.util.Map; +import static android.graphics.Color.BLACK; +import static android.util.TypedValue.COMPLEX_UNIT_DIP; +import static android.util.TypedValue.applyDimension; + public class DirectionTextView { public static final float DEF_ALPHA = 0.4f; public static final float DEF_SCALE = 0.4f; + public static final float SHADOW_RADIUS_DPS = 2; @NonNull private final Map texts = new EnumMap<>(DragDirection.class); @@ -78,6 +89,12 @@ public class DirectionTextView { return texts.get(direction); } + public void setHighContrast(boolean highContrast) { + for (Text text : texts.values()) { + text.setHighContrast(highContrast); + } + } + public static class Text { public final Rect bounds = new Rect(); @NonNull @@ -96,6 +113,7 @@ public class DirectionTextView { private int color; private float alpha; private boolean visible = true; + private boolean highContrast; private int padding; public Text(@NonNull DragDirection direction, @NonNull View view, float minTextSize) { @@ -138,9 +156,18 @@ public class DirectionTextView { // set real text size value paint.setTextSize(Math.max(base.getTextSize() * scale, minTextSize)); + initPaintShadow(); invalidate(true); } + private void initPaintShadow() { + if (highContrast) { + paint.setShadowLayer(applyDimension(COMPLEX_UNIT_DIP, SHADOW_RADIUS_DPS, view.getResources().getDisplayMetrics()), 0, 0, BLACK); + } else { + paint.setShadowLayer(0, 0, 0, BLACK); + } + } + private int intAlpha() { return (int) (255 * alpha); } @@ -161,6 +188,15 @@ public class DirectionTextView { setColor(color, alpha); } + public void setHighContrast(boolean highContrast) { + if (this.highContrast == highContrast) { + return; + } + this.highContrast = highContrast; + initPaintShadow(); + invalidate(false); + } + public void setColor(int color, float alpha) { if (this.color == color && this.alpha == alpha) { return; @@ -187,6 +223,10 @@ public class DirectionTextView { if (offset.x == 0 && offset.y == 0) { calculatePosition(); } + if (highContrast) { + paint.setColor(Color.WHITE); + paint.setAlpha(255); + } final int width = view.getWidth(); final int height = view.getHeight(); switch (direction) { @@ -203,6 +243,10 @@ public class DirectionTextView { canvas.drawText(value, width + offset.x, height / 2 + offset.y, paint); break; } + if (highContrast) { + paint.setColor(color); + paint.setAlpha(intAlpha()); + } } private void calculatePosition() { diff --git a/app/src/main/java/org/solovyev/android/views/dragbutton/DragButton.java b/app/src/main/java/org/solovyev/android/views/dragbutton/DragButton.java index d0d8049b..ddb7e828 100644 --- a/app/src/main/java/org/solovyev/android/views/dragbutton/DragButton.java +++ b/app/src/main/java/org/solovyev/android/views/dragbutton/DragButton.java @@ -9,7 +9,7 @@ import android.util.AttributeSet; import android.view.MotionEvent; import android.widget.Button; -public class DragButton extends Button implements DragView { +public abstract class DragButton extends Button implements DragView { @NonNull private final DragGestureDetector dragDetector = new DragGestureDetector(this); diff --git a/app/src/main/java/org/solovyev/android/views/dragbutton/DragImageButton.java b/app/src/main/java/org/solovyev/android/views/dragbutton/DragImageButton.java index 9413ce51..95f6f7dd 100644 --- a/app/src/main/java/org/solovyev/android/views/dragbutton/DragImageButton.java +++ b/app/src/main/java/org/solovyev/android/views/dragbutton/DragImageButton.java @@ -9,7 +9,7 @@ import android.util.AttributeSet; import android.view.MotionEvent; import android.widget.ImageButton; -public class DragImageButton extends ImageButton implements DragView { +public abstract class DragImageButton extends ImageButton implements DragView { @NonNull private final DragGestureDetector dragDetector = new DragGestureDetector(this); diff --git a/app/src/main/java/org/solovyev/android/views/dragbutton/DragView.java b/app/src/main/java/org/solovyev/android/views/dragbutton/DragView.java index 06c3813a..d37fbbc5 100644 --- a/app/src/main/java/org/solovyev/android/views/dragbutton/DragView.java +++ b/app/src/main/java/org/solovyev/android/views/dragbutton/DragView.java @@ -6,4 +6,5 @@ public interface DragView { int getId(); void setOnDragListener(@Nullable DragListener listener); void setVibrateOnDrag(boolean vibrateOnDrag); + void setHighContrast(boolean highContrast); } diff --git a/app/src/main/res/xml/preferences_appearance.xml b/app/src/main/res/xml/preferences_appearance.xml index b5781f59..6870eddb 100644 --- a/app/src/main/res/xml/preferences_appearance.xml +++ b/app/src/main/res/xml/preferences_appearance.xml @@ -38,6 +38,10 @@ a:key="gui.theme" a:title="@string/cpp_theme" /> + +