diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/com/android/camera/PhotoMenu.java | 25 | ||||
-rw-r--r-- | src/com/android/camera/PieController.java | 21 | ||||
-rw-r--r-- | src/com/android/camera/VideoMenu.java | 17 | ||||
-rw-r--r-- | src/com/android/camera/ui/PieItem.java | 73 | ||||
-rw-r--r-- | src/com/android/camera/ui/PieRenderer.java | 167 |
5 files changed, 143 insertions, 160 deletions
diff --git a/src/com/android/camera/PhotoMenu.java b/src/com/android/camera/PhotoMenu.java index 280ad44a9..92396c71b 100644 --- a/src/com/android/camera/PhotoMenu.java +++ b/src/com/android/camera/PhotoMenu.java @@ -34,6 +34,15 @@ public class PhotoMenu extends PieController TimerSettingPopup.Listener, ListPrefSettingPopup.Listener { private static String TAG = "CAM_photomenu"; + + private static final int POS_HDR = 0; + private static final int POS_EXP = 1; + private static final int POS_MORE = 2; + private static final int POS_FLASH = 3; + private static final int POS_SWITCH = 4; + private static final int POS_WB = 1; + private static final int POS_SET = 2; + private final String mSettingOff; private PhotoUI mUI; @@ -53,20 +62,19 @@ public class PhotoMenu extends PieController super.initialize(group); mPopup = null; mSecondPopup = null; - float sweep = (float) (SWEEP * Math.PI); PieItem item = null; // flash if (group.findPreference(CameraSettings.KEY_FLASH_MODE) != null) { - item = makeItem(CameraSettings.KEY_FLASH_MODE, CENTER - sweep, sweep); + item = makeItem(CameraSettings.KEY_FLASH_MODE, POS_FLASH, 5); mRenderer.addItem(item); } // exposure compensation - item = makeItem(CameraSettings.KEY_EXPOSURE, CENTER + sweep, sweep); + item = makeItem(CameraSettings.KEY_EXPOSURE, POS_EXP, 5); mRenderer.addItem(item); // camera switcher if (group.findPreference(CameraSettings.KEY_CAMERA_ID) != null) { item = makeItem(R.drawable.ic_switch_photo_facing_holo_light); - item.setFixedSlice(CENTER - 2 * sweep, sweep); + item.setPosition(POS_SWITCH, 5); item.setOnClickListener(new OnClickListener() { @Override public void onClick(PieItem item) { @@ -88,7 +96,7 @@ public class PhotoMenu extends PieController // hdr if (group.findPreference(CameraSettings.KEY_CAMERA_HDR) != null) { item = makeItem(R.drawable.ic_hdr); - item.setFixedSlice(CENTER + 2 * sweep, sweep); + item.setPosition(POS_HDR, 5); item.setOnClickListener(new OnClickListener() { @Override public void onClick(PieItem item) { @@ -108,11 +116,10 @@ public class PhotoMenu extends PieController // more settings PieItem more = makeItem(R.drawable.ic_settings_holo_light); - more.setFixedSlice(CENTER, sweep); + more.setPosition(POS_MORE, 5); mRenderer.addItem(more); // white balance - item = makeItem(CameraSettings.KEY_WHITE_BALANCE, - CENTER + sweep, sweep); + item = makeItem(CameraSettings.KEY_WHITE_BALANCE, POS_WB, 5); more.addItem(item); // settings popup mOtherKeys = new String[] { @@ -124,7 +131,7 @@ public class PhotoMenu extends PieController CameraSettings.KEY_TIMER_SOUND_EFFECTS, }; item = makeItem(R.drawable.ic_settings_holo_light); - item.setFixedSlice(CENTER, sweep); + item.setPosition(POS_SET, 5); item.setOnClickListener(new OnClickListener() { @Override public void onClick(PieItem item) { diff --git a/src/com/android/camera/PieController.java b/src/com/android/camera/PieController.java index 2145fd894..c5d1b8b41 100644 --- a/src/com/android/camera/PieController.java +++ b/src/com/android/camera/PieController.java @@ -37,10 +37,6 @@ public class PieController { protected static final int MODE_PHOTO = 0; protected static final int MODE_VIDEO = 1; - protected static float CENTER = (float) Math.PI / 2; - protected static final float SWEEP = 0.06f; - - protected CameraActivity mActivity; protected PreferenceGroup mPreferenceGroup; protected OnPreferenceChangedListener mListener; @@ -88,7 +84,7 @@ public class PieController { return new PieItem(drawable, 0); } - public PieItem makeItem(String prefKey, float center, float sweep) { + public PieItem makeItem(String prefKey, int position, int count) { final IconListPreference pref = (IconListPreference) mPreferenceGroup.findPreference(prefKey); if (pref == null) return null; @@ -103,8 +99,7 @@ public class PieController { resid = pref.getSingleIcon(); } PieItem item = makeItem(resid); - // use center and sweep to determine layout - item.setFixedSlice(center, sweep); + item.setPosition(position, count); mPreferences.add(pref); mPreferenceMap.put(pref, item); int nOfEntries = pref.getEntries().length; @@ -116,7 +111,7 @@ public class PieController { } else { inner = makeItem(pref.getEntries()[i]); } - layoutInner(inner, i, nOfEntries); + inner.setPosition(i, nOfEntries); item.addItem(inner); final int index = i; inner.setOnClickListener(new OnClickListener() { @@ -137,14 +132,8 @@ public class PieController { return item; } - protected void layoutInner(PieItem item, int ix, int n) { - float sweep = (float) (SWEEP * Math.PI);//FLOAT_PI_DIVIDED_BY_TWO / Math.max(n, 5); - float start = CENTER + (n - 1) * (sweep / 2f); - item.setFixedSlice(start - ix * sweep, sweep); - } - - public void addItem(String prefKey, float center, float sweep) { - PieItem item = makeItem(prefKey, center, sweep); + public void addItem(String prefKey, int position, int count) { + PieItem item = makeItem(prefKey, position, count); mRenderer.addItem(item); } diff --git a/src/com/android/camera/VideoMenu.java b/src/com/android/camera/VideoMenu.java index 0f987aa87..d9629d3ac 100644 --- a/src/com/android/camera/VideoMenu.java +++ b/src/com/android/camera/VideoMenu.java @@ -34,6 +34,10 @@ public class VideoMenu extends PieController TimeIntervalPopup.Listener { private static String TAG = "CAM_VideoMenu"; + private static final int POS_WB = 1; + private static final int POS_SET = 2; + private static final int POS_FLASH = 3; + private static final int POS_SWITCH = 4; private VideoUI mUI; private String[] mOtherKeys; @@ -53,13 +57,14 @@ public class VideoMenu extends PieController super.initialize(group); mPopup = null; mPopupStatus = POPUP_NONE; - float sweep = (float)(SWEEP * Math.PI); - addItem(CameraSettings.KEY_VIDEOCAMERA_FLASH_MODE, CENTER - sweep, sweep); - addItem(CameraSettings.KEY_WHITE_BALANCE, CENTER + sweep, sweep); + PieItem item = makeItem(CameraSettings.KEY_VIDEOCAMERA_FLASH_MODE, POS_FLASH, 5); + mRenderer.addItem(item); + item = makeItem(CameraSettings.KEY_WHITE_BALANCE, POS_WB, 5); + mRenderer.addItem(item); // camera switcher - PieItem item = makeItem(R.drawable.ic_switch_video_facing_holo_light); - item.setFixedSlice(CENTER - 2 * sweep, sweep); + item = makeItem(R.drawable.ic_switch_video_facing_holo_light); + item.setPosition(POS_SWITCH, 5); item.setOnClickListener(new OnClickListener() { @Override @@ -84,7 +89,7 @@ public class VideoMenu extends PieController CameraSettings.KEY_RECORD_LOCATION }; item = makeItem(R.drawable.ic_settings_holo_light); - item.setFixedSlice(CENTER, sweep); + item.setPosition(POS_SET, 5); item.setOnClickListener(new OnClickListener() { @Override public void onClick(PieItem item) { diff --git a/src/com/android/camera/ui/PieItem.java b/src/com/android/camera/ui/PieItem.java index bbfa1dc82..6128e0422 100644 --- a/src/com/android/camera/ui/PieItem.java +++ b/src/com/android/camera/ui/PieItem.java @@ -19,7 +19,6 @@ package com.android.camera.ui; import android.content.Context; import android.graphics.Canvas; import android.graphics.Path; -import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Drawable; import java.util.ArrayList; @@ -36,12 +35,9 @@ public class PieItem { private Drawable mDrawable; private int level; - private float mCenter; - private float start; - private float sweep; - private float animate; - private int inner; - private int outer; + private int mPosition; + private int mCount; + private boolean mSelected; private boolean mEnabled; private List<PieItem> mItems; @@ -61,9 +57,19 @@ public class PieItem { setAlpha(1f); } mEnabled = true; - setAnimationAngle(getAnimationAngle()); - start = -1; - mCenter = -1; + } + + public void setPosition(int pos, int count) { + mPosition = pos; + mCount = count; + } + + public int getPosition() { + return mPosition; + } + + public int getCount() { + return mCount; } public boolean hasItems() { @@ -85,6 +91,10 @@ public class PieItem { mItems = null; } + public void setLevel(int level) { + this.level = level; + } + public void setPath(Path p) { mPath = p; } @@ -102,14 +112,6 @@ public class PieItem { mDrawable.setAlpha((int) (255 * alpha)); } - public void setAnimationAngle(float a) { - animate = a; - } - - public float getAnimationAngle() { - return animate; - } - public void setEnabled(boolean enabled) { mEnabled = enabled; if (mChangeAlphaWhenDisabled) { @@ -137,41 +139,6 @@ public class PieItem { return level; } - public void setGeometry(float st, float sw, int inside, int outside) { - start = st; - sweep = sw; - inner = inside; - outer = outside; - } - - public void setFixedSlice(float center, float sweep) { - mCenter = center; - this.sweep = sweep; - } - - public float getCenter() { - return mCenter; - } - - public float getStart() { - return start; - } - - public float getStartAngle() { - return start + animate; - } - - public float getSweep() { - return sweep; - } - - public int getInnerRadius() { - return inner; - } - - public int getOuterRadius() { - return outer; - } public void setOnClickListener(OnClickListener listener) { mOnClickListener = listener; diff --git a/src/com/android/camera/ui/PieRenderer.java b/src/com/android/camera/ui/PieRenderer.java index dffa47e1e..0d8312ca4 100644 --- a/src/com/android/camera/ui/PieRenderer.java +++ b/src/com/android/camera/ui/PieRenderer.java @@ -74,10 +74,14 @@ public class PieRenderer extends OverlayRenderer private static final int MSG_OPEN = 0; private static final int MSG_CLOSE = 1; private static final int MSG_OPENSUBMENU = 2; - private static final float PIE_SWEEP = (float)(Math.PI / 2); + + protected static float CENTER = (float) Math.PI / 2; + protected static final float SWEEP_SLICE = 0.14f; + protected static final float SWEEP_ARC = 0.23f; + // geometry - private Point mSliceCenter; private int mRadius; + private int mRadiusInc; // the detection if touch is inside a slice is offset // inbounds by this amount to allow the selection to show before the @@ -101,9 +105,11 @@ public class PieRenderer extends OverlayRenderer private int mFocusY; private int mCenterX; private int mCenterY; + private int mArcCenterY; + private int mSliceCenterY; private int mPieCenterX; private int mPieCenterY; - private int mIconRadius; + private int mSliceRadius; private int mArcRadius; private int mArcOffset; @@ -126,6 +132,9 @@ public class PieRenderer extends OverlayRenderer private LinearAnimation mFadeIn; private FadeOutAnimation mFadeOut; private volatile boolean mFocusCancelled; + private PointF mPolar = new PointF(); + + private Handler mHandler = new Handler() { public void handleMessage(Message msg) { @@ -169,9 +178,9 @@ public class PieRenderer extends OverlayRenderer mOpen.add(new PieItem(null, 0)); Resources res = ctx.getResources(); mRadius = (int) res.getDimensionPixelSize(R.dimen.pie_radius_start); + mRadiusInc = (int) res.getDimensionPixelSize(R.dimen.pie_radius_increment); mCircleSize = mRadius - res.getDimensionPixelSize(R.dimen.focus_radius_offset); mTouchOffset = (int) res.getDimensionPixelSize(R.dimen.pie_touch_offset); - mSliceCenter = new Point(0,0); mSelectedPaint = new Paint(); mSelectedPaint.setColor(Color.argb(255, 51, 181, 229)); mSelectedPaint.setAntiAlias(true); @@ -201,7 +210,7 @@ public class PieRenderer extends OverlayRenderer mMenuArcPaint.setColor(Color.argb(140, 255, 255, 255)); mMenuArcPaint.setStrokeWidth(10); mMenuArcPaint.setStyle(Paint.Style.STROKE); - mIconRadius = res.getDimensionPixelSize(R.dimen.pie_item_radius); + mSliceRadius = res.getDimensionPixelSize(R.dimen.pie_item_radius); mArcRadius = res.getDimensionPixelSize(R.dimen.pie_arc_radius); mArcOffset = res.getDimensionPixelSize(R.dimen.pie_arc_offset); } @@ -299,8 +308,8 @@ public class PieRenderer extends OverlayRenderer public void setCenter(int x, int y) { mPieCenterX = x; mPieCenterY = y; - mSliceCenter.x = x; - mSliceCenter.y = y - mArcOffset + mIconRadius; + mSliceCenterY = y - mArcOffset + mSliceRadius; + mArcCenterY = y - mArcOffset + mArcRadius; } @Override @@ -325,60 +334,40 @@ public class PieRenderer extends OverlayRenderer } private void layoutPie() { - int inner = mIconRadius; - int outer = inner + mTouchOffset; - int gap = 1; - layoutItems(0, getRoot().getItems(), (float) (Math.PI / 2), inner, outer, gap); - } - - private void layoutItems(int level, List<PieItem> items, float centerAngle, int inner, int outer, int gap) { - float emptyangle = PIE_SWEEP / 16; - float sweep = (float) (PIE_SWEEP - 2 * emptyangle) / items.size(); - float angle = centerAngle - PIE_SWEEP / 2 + emptyangle + sweep / 2; - // check if we have custom geometry - // first item we find triggers custom sweep for all - // this allows us to re-use the path - for (PieItem item : items) { - if (item.getCenter() >= 0) { - sweep = item.getSweep(); - break; - } - } - Point p = new Point(mSliceCenter); - p.y -= level * mTouchOffset; - Path path = makeSlice(getDegrees(0) - gap, getDegrees(sweep) + gap, - outer, inner, p); + layoutItems(0, getRoot().getItems()); + } + + private void layoutItems(int level, List<PieItem> items) { + int extend = 1; + Path path = makeSlice(getDegrees(0) + extend, getDegrees(SWEEP_ARC) - extend, + mArcRadius, mArcRadius + mRadiusInc + mRadiusInc / 4, + mPieCenterX, mArcCenterY - level * mRadiusInc); for (PieItem item : items) { // shared between items item.setPath(path); - if (item.getCenter() >= 0) { - angle = item.getCenter(); - } + float angle = getArcCenter(item); int w = item.getIntrinsicWidth(); int h = item.getIntrinsicHeight(); // move views to outer border - int r = inner + (outer - inner) * 2 / 3; + int r = mArcRadius + mRadiusInc * 2 / 3; int x = (int) (r * Math.cos(angle)); - int y = mSliceCenter.y - (level * mTouchOffset) - (int) (r * Math.sin(angle)) - h / 2; - x = mSliceCenter.x + x - w / 2; + int y = mArcCenterY - (level * mRadiusInc) - (int) (r * Math.sin(angle)) - h / 2; + x = mPieCenterX + x - w / 2; item.setBounds(x, y, x + w, y + h); - float itemstart = angle - sweep / 2; - item.setGeometry(itemstart, sweep, inner, outer); + item.setLevel(level); if (item.hasItems()) { - layoutItems(level + 1, item.getItems(), MATH_PI_2, inner, - outer, gap); + layoutItems(level + 1, item.getItems()); } - angle += sweep; } } - private Path makeSlice(float start, float end, int outer, int inner, Point center) { + private Path makeSlice(float start, float end, int inner, int outer, int cx, int cy) { RectF bb = - new RectF(center.x - outer, center.y - outer, center.x + outer, - center.y + outer); + new RectF(cx - outer, cy - outer, cx + outer, + cy + outer); RectF bbi = - new RectF(center.x - inner, center.y - inner, center.x + inner, - center.y + inner); + new RectF(cx - inner, cy - inner, cx + inner, + cy + inner); Path path = new Path(); path.arcTo(bb, start, end - start, true); path.arcTo(bbi, end, start - end); @@ -386,6 +375,18 @@ public class PieRenderer extends OverlayRenderer return path; } + private float getArcCenter(PieItem item) { + return getCenter(item.getPosition(), item.getCount(), SWEEP_ARC); + } + + private float getSliceCenter(PieItem item) { + return getCenter(item.getPosition(), item.getCount(), SWEEP_SLICE); + } + + private float getCenter(int pos, int count, float sweep) { + return CENTER + (count - 1) * sweep / 2f - pos * sweep; + } + /** * converts a * @param angle from 0..PI to Android degrees (clockwise starting at 3 o'clock) @@ -475,14 +476,14 @@ public class PieRenderer extends OverlayRenderer } if (!hasOpenItem() || (mXFade != null)) { // draw base menu - drawArc(canvas, getLevel()); + drawArc(canvas, getLevel(), getParent()); for (PieItem item : getParent().getItems()) { drawItem(Math.max(0, mOpen.size() - 2), canvas, item, alpha); } } if (hasOpenItem()) { int level = getLevel(); - drawArc(canvas, level); + drawArc(canvas, level, getOpenItem()); for (PieItem inner : getOpenItem().getItems()) { if (mFadeOut != null) { drawItem(level, canvas, inner, alpha); @@ -494,25 +495,37 @@ public class PieRenderer extends OverlayRenderer canvas.restoreToCount(state); } - private void drawArc(Canvas canvas, int level) { + private void drawArc(Canvas canvas, int level, PieItem item) { // arc if (mState == STATE_PIE) { - int nr = mArcRadius; - int cy = mPieCenterY - mArcOffset + mArcRadius - level * mTouchOffset; - canvas.drawArc(new RectF(mPieCenterX - nr, cy - mArcRadius, - mPieCenterX + nr, cy + mArcRadius), - 252, 36, false, mMenuArcPaint); + int min = Integer.MAX_VALUE; + int max = Integer.MIN_VALUE; + int count = 0; + for (PieItem child : item.getItems()) { + final int p = child.getPosition(); + count = child.getCount(); + if (p < min) min = p; + if (p > max) max = p; + } + float start = CENTER + (count - 1) * SWEEP_ARC / 2f - min * SWEEP_ARC + SWEEP_ARC / 2f; + float end = CENTER + (count - 1) * SWEEP_ARC / 2f - max * SWEEP_ARC - SWEEP_ARC / 2f; + int cy = mArcCenterY - level * mRadiusInc; + canvas.drawArc(new RectF(mPieCenterX - mArcRadius, cy - mArcRadius, + mPieCenterX + mArcRadius, cy + mArcRadius), + getDegrees(end), getDegrees(start) - getDegrees(end), false, mMenuArcPaint); } } + private void drawItem(int level, Canvas canvas, PieItem item, float alpha) { if (mState == STATE_PIE) { if (item.getPath() != null) { - int y = mSliceCenter.y - level * mTouchOffset; + int y = mArcCenterY - level * mRadiusInc; if (item.isSelected()) { Paint p = mSelectedPaint; int state = canvas.save(); - float r = getDegrees(item.getStartAngle()); - canvas.rotate(r, mSliceCenter.x, y); + float angle = getArcCenter(item) - SWEEP_ARC / 2f; + angle = getDegrees(angle); + canvas.rotate(angle, mPieCenterX, y); if (mFadeOut != null) { p.setAlpha((int)(255 * alpha)); } @@ -537,13 +550,13 @@ public class PieRenderer extends OverlayRenderer float x = evt.getX(); float y = evt.getY(); int action = evt.getActionMasked(); - PointF polar = getPolar(x, y, !mTapMode); + getPolar(x, y, !mTapMode, mPolar); if (MotionEvent.ACTION_DOWN == action) { mDown.x = (int) evt.getX(); mDown.y = (int) evt.getY(); mOpening = false; if (mTapMode) { - PieItem item = findItem(polar); + PieItem item = findItem(mPolar); if ((item != null) && (mCurrentItem != item)) { mState = STATE_PIE; onEnter(item); @@ -557,7 +570,7 @@ public class PieRenderer extends OverlayRenderer if (isVisible()) { PieItem item = mCurrentItem; if (mTapMode) { - item = findItem(polar); + item = findItem(mPolar); if (mOpening) { mOpening = false; return true; @@ -582,7 +595,7 @@ public class PieRenderer extends OverlayRenderer mHandler.removeMessages(MSG_OPENSUBMENU); return false; } else if (MotionEvent.ACTION_MOVE == action) { - if (pulledToCenter(polar)) { + if (pulledToCenter(mPolar)) { mHandler.removeMessages(MSG_OPENSUBMENU); if (hasOpenItem()) { if (mCurrentItem != null) { @@ -595,7 +608,7 @@ public class PieRenderer extends OverlayRenderer } return false; } - PieItem item = findItem(polar); + PieItem item = findItem(mPolar); boolean moved = hasMoved(evt); if ((item != null) && (mCurrentItem != item) && (!mOpening || moved)) { mHandler.removeMessages(MSG_OPENSUBMENU); @@ -612,24 +625,32 @@ public class PieRenderer extends OverlayRenderer } private boolean pulledToCenter(PointF polarCoords) { - return polarCoords.y < mIconRadius - mArcOffset; + return polarCoords.y < mArcRadius - mRadiusInc; } - private PointF getPolar(float x, float y, boolean useOffset) { - PointF res = new PointF(); + private boolean inside(PointF polar, PieItem item) { + float start = getSliceCenter(item) - SWEEP_SLICE / 2f; + boolean res = (mArcRadius < polar.y) + && (start < polar.x) + && (start + SWEEP_SLICE > polar.x) + && (!mTapMode || (mArcRadius + mRadiusInc > polar.y)); + return res; + } + + private void getPolar(float x, float y, boolean useOffset, PointF res) { // get angle and radius from x/y res.x = (float) Math.PI / 2; - x = x - mSliceCenter.x; - y = mSliceCenter.y - getLevel() * mTouchOffset - y; - res.y = (float) Math.sqrt(x * x + y * y); + x = x - mPieCenterX; + float y1 = mSliceCenterY - getLevel() * mRadiusInc - y; + float y2 = mArcCenterY - getLevel() * mRadiusInc - y; + res.y = (float) Math.sqrt(x * x + y2 * y2); if (x != 0) { - res.x = (float) Math.atan2(y, x); + res.x = (float) Math.atan2(y1, x); if (res.x < 0) { res.x = (float) (2 * Math.PI + res.x); } } res.y = res.y + (useOffset ? mTouchOffset : 0); - return res; } private boolean hasMoved(MotionEvent e) { @@ -733,12 +754,6 @@ public class PieRenderer extends OverlayRenderer return null; } - private boolean inside(PointF polar, PieItem item) { - return (item.getInnerRadius() < polar.y) - && (item.getStartAngle() < polar.x) - && (item.getStartAngle() + item.getSweep() > polar.x) - && (!mTapMode || (item.getOuterRadius() > polar.y)); - } @Override public boolean handlesTouch() { |