Permalink
Browse files

设备旋转后,通过Bundle保存绘制的自定义矩形框。

  • Loading branch information...
li2 committed Nov 11, 2015
1 parent 2d58e5e commit 47bc602622e4f55deef16acb37b24f20162f7b63
@@ -1,10 +1,13 @@
package me.li2.android.boxdrawingview;
import android.graphics.PointF;
import android.os.Parcel;
import android.os.Parcelable;
// 新建一个Box类,用于存储一个矩形框两个角的坐标:
// 原始坐标点(手指的初始位置)、当前坐标点(手指的当前位置)。
public class Box {
public class Box implements Parcelable {
private PointF mOrigin;
private PointF mCurrent;
@@ -23,4 +26,40 @@ public void setCurrent(PointF current) {
public PointF getOrigin() {
return mOrigin;
}
// public interface Parcelable
// Interface for classes whose instances can be written to and restored from a Parcel.
// http://developer.android.com/intl/zh-cn/reference/android/os/Parcelable.html
// Parcelable接口允许类的实例可以被写入Parcel,并从中恢复。
// 然后我们就可以在View.onSaveInstanceState()方法中存储 ArrayList of Objects: mBoxes,调用
// Bundle.putParcelableArrayList(String key, ArrayList<? extends Parcelable> value)
@Override
public int describeContents() {
return 0;
}
@Override
public void writeToParcel(Parcel out, int flags) {
out.writeValue(mOrigin);
out.writeValue(mCurrent);
}
public static final Parcelable.Creator<Box> CREATOR = new Parcelable.Creator<Box>() {
@Override
public Box createFromParcel(Parcel in) {
return new Box(in);
}
@Override
public Box[] newArray(int size) {
return new Box[size];
}
};
private Box(Parcel in) {
mOrigin = (PointF) in.readValue(null);
mCurrent = (PointF) in.readValue(null);
}
}
@@ -6,7 +6,7 @@
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.PointF;
import android.os.Parcel;
import android.os.Bundle;
import android.os.Parcelable;
import android.util.AttributeSet;
import android.util.Log;
@@ -105,63 +105,34 @@ public boolean onTouchEvent(MotionEvent event) {
return true;
}
// 使用Bundle在设备旋转时保存数据。
// prevent custom views from losing state across screen orientation changes
// http://stackoverflow.com/a/3542895/2722270
static class BoxDrawingState extends BaseSavedState {
Box currentBox;
ArrayList<Box> boxes;
BoxDrawingState(Parcelable superState) {
super(superState);
}
private BoxDrawingState(Parcel in) {
super(in);
currentBox = (Box)in.readValue(null);
in.readList(boxes, null);
}
@Override
public void writeToParcel(Parcel out, int flags) {
super.writeToParcel(out, flags);
out.writeValue(currentBox);
out.writeList(boxes);
}
@Override
public String toString() {
return "BoxDrawingView.SavedState{"
+ Integer.toHexString(System.identityHashCode(this))
+ " Boxes=" + boxes + "}";
}
Parcelable.Creator<BoxDrawingState> CREATOR = new Parcelable.Creator<BoxDrawingState>() {
@Override
public BoxDrawingState createFromParcel(Parcel in) {
return new BoxDrawingState(in);
}
@Override
public BoxDrawingState[] newArray(int size) {
return new BoxDrawingState[size];
}
};
}
// http://stackoverflow.com/a/8127813/2722270
// RuntimeException: Unable to start activity ComponentInfo{.DragAndDraw}:
// java.lang.IllegalArgumentException: Wrong state class, expecting View State but received class Bundle instead.
// This usually happens when two views of different type have the same id in the same hierarchy.
private static final String PARCEL_KEY_STATE = "instanceState";
private static final String PARCEL_KEY_BOXES = "boxes";
@Override
protected Parcelable onSaveInstanceState() {
Parcelable superState = super.onSaveInstanceState();
BoxDrawingState boxDrawingState = new BoxDrawingState(superState);
boxDrawingState.currentBox = mCurrentBox;
boxDrawingState.boxes = mBoxes;
return boxDrawingState;
super.onSaveInstanceState();
Bundle bundle = new Bundle();
bundle.putParcelable(PARCEL_KEY_STATE, super.onSaveInstanceState());
bundle.putParcelableArrayList(PARCEL_KEY_BOXES, mBoxes);
return bundle;
}
@Override
protected void onRestoreInstanceState(Parcelable state) {
BoxDrawingState boxDrawingState = (BoxDrawingState) state;
super.onRestoreInstanceState(boxDrawingState.getSuperState());
mCurrentBox = boxDrawingState.currentBox;
mBoxes = boxDrawingState.boxes;
if (state instanceof Bundle) {
Bundle bundle = (Bundle)state;
mBoxes = bundle.getParcelableArrayList(PARCEL_KEY_BOXES);
// 如果没有下面这行代码,将导致 IllegalArgumentException.
state = bundle.getParcelable(PARCEL_KEY_STATE);
}
super.onRestoreInstanceState(state);
}
}

0 comments on commit 47bc602

Please sign in to comment.