diff --git a/res/layout/running_processes_header.xml b/res/layout/running_processes_header.xml index aa106ac2c27..ac315437c2b 100644 --- a/res/layout/running_processes_header.xml +++ b/res/layout/running_processes_header.xml @@ -36,7 +36,7 @@ android:gravity="left|center_vertical" android:text="@string/running_processes_header_title" /> - - = DisplayMetrics.DENSITY_HIGH - ? 2 : 1; - mEdgeGradientPaint.setStrokeWidth(mLineWidth); - mEdgeGradientPaint.setAntiAlias(true); - mLeftColor = mMiddleColor = Utils.getColorAccent(context); - } - - public void setOnRegionTappedListener(OnRegionTappedListener listener) { - if (listener != mOnRegionTappedListener) { - mOnRegionTappedListener = listener; - setClickable(listener != null); - } - } - - public void setColoredRegions(int regions) { - mColoredRegions = regions; - invalidate(); - } - - public void setRatios(float red, float yellow, float green) { - mRedRatio = red; - mYellowRatio = yellow; - mGreenRatio = green; - invalidate(); - } - - public void setColors(int red, int yellow, int green) { - mLeftColor = red; - mMiddleColor = yellow; - mRightColor = green; - updateIndicator(); - invalidate(); - } - - public void setShowIndicator(boolean showIndicator) { - mShowIndicator = showIndicator; - updateIndicator(); - invalidate(); - } - - public void setShowingGreen(boolean showingGreen) { - if (mShowingGreen != showingGreen) { - mShowingGreen = showingGreen; - updateIndicator(); - invalidate(); - } - } - - private void updateIndicator() { - int off = getPaddingTop() - getPaddingBottom(); - if (off < 0) off = 0; - mRect.top = off; - mRect.bottom = getHeight(); - if (!mShowIndicator) { - return; - } - if (mShowingGreen) { - mColorGradientPaint.setShader(new LinearGradient( - 0, 0, 0, off-2, mRightColor &0xffffff, mRightColor, Shader.TileMode.CLAMP)); - } else { - mColorGradientPaint.setShader(new LinearGradient( - 0, 0, 0, off-2, mMiddleColor&0xffffff, mMiddleColor, Shader.TileMode.CLAMP)); - } - mEdgeGradientPaint.setShader(new LinearGradient( - 0, 0, 0, off/2, 0x00a0a0a0, 0xffa0a0a0, Shader.TileMode.CLAMP)); - } - - @Override - protected void onSizeChanged(int w, int h, int oldw, int oldh) { - super.onSizeChanged(w, h, oldw, oldh); - updateIndicator(); - } - - @Override - public boolean onTouchEvent(MotionEvent event) { - if (mOnRegionTappedListener != null) { - switch (event.getAction()) { - case MotionEvent.ACTION_DOWN: { - final int x = (int) event.getX(); - if (x < mLastLeftDiv) { - mLastRegion = REGION_RED; - } else if (x < mLastRightDiv) { - mLastRegion = REGION_YELLOW; - } else { - mLastRegion = REGION_GREEN; - } - invalidate(); - } break; - } - } - return super.onTouchEvent(event); - } - - @Override - protected void dispatchSetPressed(boolean pressed) { - invalidate(); - } - - @Override - public boolean performClick() { - if (mOnRegionTappedListener != null && mLastRegion != 0) { - mOnRegionTappedListener.onRegionTapped(mLastRegion); - mLastRegion = 0; - } - return super.performClick(); - } - - private int pickColor(int color, int region) { - if (isPressed() && (mLastRegion®ion) != 0) { - return WHITE_COLOR; - } - if ((mColoredRegions®ion) == 0) { - return GRAY_COLOR; - } - return color; - } - - @Override - protected void onDraw(Canvas canvas) { - super.onDraw(canvas); - - int width = getWidth(); - - int left = 0; - - int right = left + (int)(width*mRedRatio); - int right2 = right + (int)(width*mYellowRatio); - int right3 = right2 + (int)(width*mGreenRatio); - - int indicatorLeft, indicatorRight; - if (mShowingGreen) { - indicatorLeft = right2; - indicatorRight = right3; - } else { - indicatorLeft = right; - indicatorRight = right2; - } - - if (mLastInterestingLeft != indicatorLeft || mLastInterestingRight != indicatorRight) { - mColorPath.reset(); - mEdgePath.reset(); - if (mShowIndicator && indicatorLeft < indicatorRight) { - final int midTopY = mRect.top; - final int midBottomY = 0; - final int xoff = 2; - mColorPath.moveTo(indicatorLeft, mRect.top); - mColorPath.cubicTo(indicatorLeft, midBottomY, - -xoff, midTopY, - -xoff, 0); - mColorPath.lineTo(width+xoff-1, 0); - mColorPath.cubicTo(width+xoff-1, midTopY, - indicatorRight, midBottomY, - indicatorRight, mRect.top); - mColorPath.close(); - final float lineOffset = mLineWidth+.5f; - mEdgePath.moveTo(-xoff+lineOffset, 0); - mEdgePath.cubicTo(-xoff+lineOffset, midTopY, - indicatorLeft+lineOffset, midBottomY, - indicatorLeft+lineOffset, mRect.top); - mEdgePath.moveTo(width+xoff-1-lineOffset, 0); - mEdgePath.cubicTo(width+xoff-1-lineOffset, midTopY, - indicatorRight-lineOffset, midBottomY, - indicatorRight-lineOffset, mRect.top); - } - mLastInterestingLeft = indicatorLeft; - mLastInterestingRight = indicatorRight; - } - - if (!mEdgePath.isEmpty()) { - canvas.drawPath(mEdgePath, mEdgeGradientPaint); - canvas.drawPath(mColorPath, mColorGradientPaint); - } - - if (left < right) { - mRect.left = left; - mRect.right = right; - mPaint.setColor(pickColor(mLeftColor, REGION_RED)); - canvas.drawRect(mRect, mPaint); - width -= (right-left); - left = right; - } - - mLastLeftDiv = right; - mLastRightDiv = right2; - - right = right2; - - if (left < right) { - mRect.left = left; - mRect.right = right; - mPaint.setColor(pickColor(mMiddleColor, REGION_YELLOW)); - canvas.drawRect(mRect, mPaint); - width -= (right-left); - left = right; - } - - - right = left + width; - if (left < right) { - mRect.left = left; - mRect.right = right; - mPaint.setColor(pickColor(mRightColor, REGION_GREEN)); - canvas.drawRect(mRect, mPaint); - } - } -} \ No newline at end of file diff --git a/src/com/android/settings/applications/RunningProcessesView.java b/src/com/android/settings/applications/RunningProcessesView.java index b36543504f2..dd8bcf89a67 100644 --- a/src/com/android/settings/applications/RunningProcessesView.java +++ b/src/com/android/settings/applications/RunningProcessesView.java @@ -43,6 +43,7 @@ import com.android.internal.util.MemInfoReader; import com.android.settings.R; import com.android.settings.SettingsActivity; import com.android.settings.Utils; +import com.android.settings.widget.LinearColorBar; import java.util.ArrayList; import java.util.Collections; diff --git a/src/com/android/settings/datausage/DataUsageSummary.java b/src/com/android/settings/datausage/DataUsageSummary.java index b4d5f50ee04..e626c3a5594 100644 --- a/src/com/android/settings/datausage/DataUsageSummary.java +++ b/src/com/android/settings/datausage/DataUsageSummary.java @@ -20,8 +20,6 @@ import android.content.Context; import android.content.Intent; import android.net.NetworkPolicyManager; import android.net.NetworkTemplate; -import android.net.wifi.WifiConfiguration; -import android.net.wifi.WifiManager; import android.os.Bundle; import android.os.UserManager; import android.provider.SearchIndexableResource; diff --git a/src/com/android/settings/widget/LinearColorBar.java b/src/com/android/settings/widget/LinearColorBar.java new file mode 100644 index 00000000000..b3e685efc75 --- /dev/null +++ b/src/com/android/settings/widget/LinearColorBar.java @@ -0,0 +1,192 @@ +/* + * Copyright (C) 2018 The Android Open Source 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.android.settings.widget; + +import android.content.Context; +import android.graphics.Canvas; +import android.graphics.Paint; +import android.graphics.Rect; +import android.util.AttributeSet; +import android.util.DisplayMetrics; +import android.widget.LinearLayout; + +import com.android.settings.Utils; + +public class LinearColorBar extends LinearLayout { + + static final int RIGHT_COLOR = 0xffced7db; + static final int GRAY_COLOR = 0xff555555; + static final int WHITE_COLOR = 0xffffffff; + + private float mRedRatio; + private float mYellowRatio; + private float mGreenRatio; + + private int mLeftColor; + private int mMiddleColor; + private int mRightColor = RIGHT_COLOR; + + private int mColoredRegions = REGION_RED | REGION_YELLOW | REGION_GREEN; + + final Rect mRect = new Rect(); + final Paint mPaint = new Paint(); + + int mLineWidth; + + int mLastRegion; + + final Paint mColorGradientPaint = new Paint(); + final Paint mEdgeGradientPaint = new Paint(); + + public static final int REGION_RED = 1 << 0; + public static final int REGION_YELLOW = 1 << 1; + public static final int REGION_GREEN = 1 << 2; + + public LinearColorBar(Context context, AttributeSet attrs) { + super(context, attrs); + setWillNotDraw(false); + mPaint.setStyle(Paint.Style.FILL); + mColorGradientPaint.setStyle(Paint.Style.FILL); + mColorGradientPaint.setAntiAlias(true); + mEdgeGradientPaint.setStyle(Paint.Style.STROKE); + mLineWidth = getResources().getDisplayMetrics().densityDpi >= DisplayMetrics.DENSITY_HIGH + ? 2 : 1; + mEdgeGradientPaint.setStrokeWidth(mLineWidth); + mEdgeGradientPaint.setAntiAlias(true); + mLeftColor = mMiddleColor = Utils.getColorAccent(context); + } + + public void setRatios(float red, float yellow, float green) { + mRedRatio = red; + mYellowRatio = yellow; + mGreenRatio = green; + invalidate(); + } + + public void setColors(int red, int yellow, int green) { + mLeftColor = red; + mMiddleColor = yellow; + mRightColor = green; + updateIndicator(); + invalidate(); + } + + private void updateIndicator() { + int off = getPaddingTop() - getPaddingBottom(); + if (off < 0) off = 0; + mRect.top = off; + mRect.bottom = getHeight(); + } + + @Override + protected void onSizeChanged(int w, int h, int oldw, int oldh) { + super.onSizeChanged(w, h, oldw, oldh); + updateIndicator(); + } + + @Override + protected void dispatchSetPressed(boolean pressed) { + invalidate(); + } + + private int pickColor(int color, int region) { + if (isPressed() && (mLastRegion & region) != 0) { + return WHITE_COLOR; + } + if ((mColoredRegions & region) == 0) { + return GRAY_COLOR; + } + return color; + } + + @Override + protected void onDraw(Canvas canvas) { + super.onDraw(canvas); + + final int width = getWidth(); + + if (!isLayoutRtl()) { + drawLtr(canvas, width); + } else { + drawRtl(canvas, width); + } + } + + private void drawLtr(Canvas canvas, int width) { + int start = 0; + int end = start + (int) (width * mRedRatio); + int end2 = end + (int) (width * mYellowRatio); + + if (start < end) { + mRect.left = start; + mRect.right = end; + mPaint.setColor(pickColor(mLeftColor, REGION_RED)); + canvas.drawRect(mRect, mPaint); + start = end; + } + + end = end2; + + if (start < end) { + mRect.left = start; + mRect.right = end; + mPaint.setColor(pickColor(mMiddleColor, REGION_YELLOW)); + canvas.drawRect(mRect, mPaint); + start = end; + } + + end = width; + if (start < end) { + mRect.left = start; + mRect.right = end; + mPaint.setColor(pickColor(mRightColor, REGION_GREEN)); + canvas.drawRect(mRect, mPaint); + } + } + + private void drawRtl(Canvas canvas, int width) { + int start = width; + int end = start - (int) (width * mRedRatio); + int end2 = end - (int) (width * mYellowRatio); + + if (start > end) { + mRect.left = end; + mRect.right = start; + mPaint.setColor(pickColor(mLeftColor, REGION_RED)); + canvas.drawRect(mRect, mPaint); + start = end; + } + + end = end2; + + if (start > end) { + mRect.left = end; + mRect.right = start; + mPaint.setColor(pickColor(mMiddleColor, REGION_YELLOW)); + canvas.drawRect(mRect, mPaint); + start = end; + } + + end = 0; + if (start > end) { + mRect.left = end; + mRect.right = start; + mPaint.setColor(pickColor(mRightColor, REGION_GREEN)); + canvas.drawRect(mRect, mPaint); + } + } +} \ No newline at end of file diff --git a/tests/robotests/src/com/android/settings/widget/LinearColorBarTest.java b/tests/robotests/src/com/android/settings/widget/LinearColorBarTest.java new file mode 100644 index 00000000000..dc14ae70798 --- /dev/null +++ b/tests/robotests/src/com/android/settings/widget/LinearColorBarTest.java @@ -0,0 +1,87 @@ +/* + * Copyright (C) 2018 The Android Open Source 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.android.settings.widget; + + +import static com.google.common.truth.Truth.assertThat; +import static org.mockito.Mockito.spy; +import static org.mockito.Mockito.when; + +import android.content.Context; +import android.graphics.Canvas; + +import com.android.settings.TestConfig; +import com.android.settings.testutils.SettingsRobolectricTestRunner; + +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.robolectric.RuntimeEnvironment; +import org.robolectric.Shadows; +import org.robolectric.annotation.Config; +import org.robolectric.shadows.ShadowCanvas; + +@RunWith(SettingsRobolectricTestRunner.class) +@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) +public class LinearColorBarTest { + + private static final int HEIGHT = 100; + private static final int WIDTH = 100; + + private Context mContext; + private LinearColorBar mLinearColorBar; + private Canvas mCanvas; + + @Before + public void setUp() { + mContext = RuntimeEnvironment.application; + mLinearColorBar = spy(new LinearColorBar(mContext, null /* attrs */)); + when(mLinearColorBar.getHeight()).thenReturn(HEIGHT); + when(mLinearColorBar.getWidth()).thenReturn(WIDTH); + mLinearColorBar.setRatios(0.2f, 0.4f, 0.4f); + mLinearColorBar.setColors(1, 2, 3); + mCanvas = new Canvas(); + } + + @Test + public void draw_ltr_showStartFromLeft() { + mLinearColorBar.onDraw(mCanvas); + + final ShadowCanvas shadowCanvas = Shadows.shadowOf(mCanvas); + assertThat(shadowCanvas.getRectPaintHistoryCount()).isEqualTo(3); + + // 3 boxes, takes space of 20%, 40%, 40% of the the WIDTH correspondingly. + assertThat(shadowCanvas.getDrawnRect(0).left).isWithin(0.01f).of(0); + assertThat(shadowCanvas.getDrawnRect(1).left).isWithin(0.01f).of(20); + assertThat(shadowCanvas.getDrawnRect(2).left).isWithin(0.01f).of(60); + } + + @Test + public void draw_rtl_showStartFromRight() { + when(mLinearColorBar.isLayoutRtl()).thenReturn(true); + + mLinearColorBar.onDraw(mCanvas); + + final ShadowCanvas shadowCanvas = Shadows.shadowOf(mCanvas); + assertThat(shadowCanvas.getRectPaintHistoryCount()).isEqualTo(3); + + // 3 boxes, takes space of 20%, 40%, 40% of the the WIDTH correspondingly. + assertThat(shadowCanvas.getDrawnRect(0).right).isWithin(0.01f).of(100); + assertThat(shadowCanvas.getDrawnRect(1).right).isWithin(0.01f).of(80); + assertThat(shadowCanvas.getDrawnRect(2).right).isWithin(0.01f).of(40); + } +}