我正在使用pl.polidea.coverflow(http://code.google.com/p/android-coverflow/,它扩展了android.widget.Gallery)。
如果我没有在AndroidMenifest中指定android:targetSdkVersion,它运行良好..
如果我将android:targetSdkVersion指定为< 14,它也运作良好..
但是如果我将android:targetSdkVersion设置为> = 14,则封面流的行为会被混淆..它会以某个角度显示居中的图像(在某些天使处旋转图像,如封面流中的侧面图像)..
这是主要的coverflow.java文件。
package pl.polidea.coverflow;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Camera;
import android.graphics.Matrix;
import android.util.AttributeSet;
import android.view.View;
import android.view.animation.Transformation;
import android.widget.Gallery;
import android.widget.ImageView;
import android.widget.SpinnerAdapter;
/**
* Cover Flow implementation.
*
*/
public class CoverFlow extends Gallery {
/**
* Graphics Camera used for transforming the matrix of ImageViews.
*/
private final Camera mCamera = new Camera();
/**
* The maximum angle the Child ImageView will be rotated by.
*/
private int mMaxRotationAngle = 30; //default is 60
/**
* The maximum zoom on the centre Child.
*/
private int mMaxZoom = -115; //default is -120
/**
* The Centre of the Coverflow.
*/
private int mCoveflowCenter;
/** The image height. */
private float imageHeight;
/** The image width. */
private float imageWidth;
/** The reflection gap. */
private float reflectionGap;
/** The with reflection. */
private boolean withReflection;
/** The image reflection ratio. */
private float imageReflectionRatio;
/**
* Gets the image height.
*
* @return the image height
*/
public float getImageHeight() {
return imageHeight;
}
/**
* Sets the image height.
*
* @param imageHeight
* the new image height
*/
public void setImageHeight(final float imageHeight) {
this.imageHeight = imageHeight;
}
/**
* Gets the image width.
*
* @return the image width
*/
public float getImageWidth() {
return imageWidth;
}
/**
* Sets the image width.
*
* @param imageWidth
* the new image width
*/
public void setImageWidth(final float imageWidth) {
this.imageWidth = imageWidth;
}
/**
* Gets the reflection gap.
*
* @return the reflection gap
*/
public float getReflectionGap() {
return reflectionGap;
}
/**
* Sets the reflection gap.
*
* @param reflectionGap
* the new reflection gap
*/
public void setReflectionGap(final float reflectionGap) {
this.reflectionGap = reflectionGap;
}
/**
* Checks if is with reflection.
*
* @return true, if is with reflection
*/
public boolean isWithReflection() {
return withReflection;
}
/**
* Sets the with reflection.
*
* @param withReflection
* the new with reflection
*/
public void setWithReflection(final boolean withReflection) {
this.withReflection = withReflection;
}
/**
* Sets the image reflection ratio.
*
* @param imageReflectionRatio
* the new image reflection ratio
*/
public void setImageReflectionRatio(final float imageReflectionRatio) {
this.imageReflectionRatio = imageReflectionRatio;
}
/**
* Gets the image reflection ratio.
*
* @return the image reflection ratio
*/
public float getImageReflectionRatio() {
return imageReflectionRatio;
}
public CoverFlow(final Context context) {
super(context);
this.setStaticTransformationsEnabled(true);
}
public CoverFlow(final Context context, final AttributeSet attrs) {
this(context, attrs, android.R.attr.galleryStyle);
}
public CoverFlow(final Context context, final AttributeSet attrs, final int defStyle) {
super(context, attrs, defStyle);
parseAttributes(context, attrs);
this.setStaticTransformationsEnabled(true);
}
/**
* Get the max rotational angle of the image.
*
* @return the mMaxRotationAngle
*/
public int getMaxRotationAngle() {
return mMaxRotationAngle;
}
/**
* Sets the.
*
* @param adapter
* the new adapter
*/
@Override
public void setAdapter(final SpinnerAdapter adapter) {
if (!(adapter instanceof AbstractCoverFlowImageAdapter)) {
throw new IllegalArgumentException("The adapter should derive from "
+ AbstractCoverFlowImageAdapter.class.getName());
}
final AbstractCoverFlowImageAdapter coverAdapter = (AbstractCoverFlowImageAdapter) adapter;
coverAdapter.setWidth(imageWidth);
coverAdapter.setHeight((float)(imageHeight*(1.2)));
if (withReflection) {
final ReflectingImageAdapter reflectAdapter = new ReflectingImageAdapter(coverAdapter);
reflectAdapter.setReflectionGap(reflectionGap);
reflectAdapter.setWidthRatio(imageReflectionRatio);
reflectAdapter.setWidth(imageWidth);
reflectAdapter.setHeight(imageHeight * (1 + imageReflectionRatio));
super.setAdapter(reflectAdapter);
} else {
super.setAdapter(adapter);
}
}
/**
* Set the max rotational angle of each image.
*
* @param maxRotationAngle
* the mMaxRotationAngle to set
*/
public void setMaxRotationAngle(final int maxRotationAngle) {
mMaxRotationAngle = maxRotationAngle;
}
/**
* Get the Max zoom of the centre image.
*
* @return the mMaxZoom
*/
public int getMaxZoom() {
return mMaxZoom;
}
/**
* Set the max zoom of the centre image.
*
* @param maxZoom
* the mMaxZoom to set
*/
public void setMaxZoom(final int maxZoom) {
mMaxZoom = maxZoom;
}
/**
* Get the Centre of the Coverflow.
*
* @return The centre of this Coverflow.
*/
private int getCenterOfCoverflow() {
return (getWidth() - getPaddingLeft() - getPaddingRight()) / 2 + getPaddingLeft();
}
/**
* Get the Centre of the View.
*
* @return The centre of the given view.
*/
private static int getCenterOfView(final View view) {
return view.getLeft() + view.getWidth() / 2;
}
/**
* {@inheritDoc}
*
* @see #setStaticTransformationsEnabled(boolean)
*/
@Override
protected boolean getChildStaticTransformation(final View child, final Transformation t) {
final int childCenter = getCenterOfView(child);
final int childWidth = child.getWidth();
int rotationAngle = 0;
t.clear();
t.setTransformationType(Transformation.TYPE_MATRIX);
if (childCenter == mCoveflowCenter) {
transformImageBitmap((ImageView) child, t, 0);
} else {
rotationAngle = (int) ((float) (mCoveflowCenter - childCenter) / childWidth * mMaxRotationAngle);
if (Math.abs(rotationAngle) > mMaxRotationAngle) {
rotationAngle = rotationAngle < 0 ? -mMaxRotationAngle : mMaxRotationAngle;
}
transformImageBitmap((ImageView) child, t, rotationAngle);
}
return true;
}
/**
* This is called during layout when the size of this view has changed. If
* you were just added to the view hierarchy, you're called with the old
* values of 0.
*
* @param w
* Current width of this view.
* @param h
* Current height of this view.
* @param oldw
* Old width of this view.
* @param oldh
* Old height of this view.
*/
@Override
protected void onSizeChanged(final int w, final int h, final int oldw, final int oldh) {
mCoveflowCenter = getCenterOfCoverflow();
super.onSizeChanged(w, h, oldw, oldh);
}
/**
* Transform the Image Bitmap by the Angle passed.
*
* @param imageView
* ImageView the ImageView whose bitmap we want to rotate
* @param t
* transformation
* @param rotationAngle
* the Angle by which to rotate the Bitmap
*/
private void transformImageBitmap(final ImageView child, final Transformation t, final int rotationAngle) {
mCamera.save();
final Matrix imageMatrix = t.getMatrix();
final int height = child.getLayoutParams().height;
final int width = child.getLayoutParams().width;
final int rotation = Math.abs(rotationAngle);
mCamera.translate(0.0f, 0.0f, 100.0f);
// As the angle of the view gets less, zoom in
if (rotation < mMaxRotationAngle) {
final float zoomAmount = (float) (mMaxZoom + rotation * 1.5);
mCamera.translate(0.0f, 0.0f, zoomAmount);
}
mCamera.rotateY(rotationAngle);
mCamera.getMatrix(imageMatrix);
imageMatrix.preTranslate(-(width / 2.0f), -(height / 2.0f));
imageMatrix.postTranslate((width / 2.0f), (height / 2.0f));
mCamera.restore();
}
/**
* Parses the attributes.
*
* @param context
* the context
* @param attrs
* the attrs
*/
private void parseAttributes(final Context context, final AttributeSet attrs) {
final TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.CoverFlow);
try {
imageWidth = a.getDimension(R.styleable.CoverFlow_imageWidth, 480);
imageHeight = a.getDimension(R.styleable.CoverFlow_imageHeight, 320);
withReflection = a.getBoolean(R.styleable.CoverFlow_withReflection, false);
imageReflectionRatio = a.getFloat(R.styleable.CoverFlow_imageReflectionRatio, 0.4f);
reflectionGap = a.getDimension(R.styleable.CoverFlow_reflectionGap, 4);
setSpacing(-20);
setAlwaysDrawnWithCacheEnabled(true);
} finally {
a.recycle();
}
}
}
答案 0 :(得分:0)
我刚刚更改了coverflow.java并完成了..我现在可以将android:targetSdkVersion设置为&gt; = 14 ..
这是coverflow.java的代码:
package pl.polidea.coverflow;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Camera;
import android.graphics.Matrix;
import android.util.AttributeSet;
import android.util.Log;
import android.view.View;
import android.view.animation.Transformation;
import android.widget.Gallery;
import android.widget.ImageView;
import android.widget.SpinnerAdapter;
/**
* Cover Flow implementation.
*
*/
public class CoverFlow extends Gallery {
/**
* Graphics Camera used for transforming the matrix of ImageViews.
*/
private final Camera mCamera = new Camera();
/**
* The maximum angle the Child ImageView will be rotated by.
*/
private int mMaxRotationAngle = 30; //default is 60
/**
* The maximum zoom on the centre Child.
*/
private int mMaxZoom = -115; //default is -120
/**
* The Centre of the Coverflow.
*/
private int mCoveflowCenter;
/** The image height. */
private float imageHeight;
/** The image width. */
private float imageWidth;
/** The reflection gap. */
private float reflectionGap;
/** The with reflection. */
private boolean withReflection;
/** The image reflection ratio. */
private float imageReflectionRatio;
/**
* Gets the image height.
*
* @return the image height
*/
public float getImageHeight() {
return imageHeight;
}
/**
* Sets the image height.
*
* @param imageHeight
* the new image height
*/
public void setImageHeight(final float imageHeight) {
this.imageHeight = imageHeight;
}
/**
* Gets the image width.
*
* @return the image width
*/
public float getImageWidth() {
return imageWidth;
}
/**
* Sets the image width.
*
* @param imageWidth
* the new image width
*/
public void setImageWidth(final float imageWidth) {
this.imageWidth = imageWidth;
}
/**
* Gets the reflection gap.
*
* @return the reflection gap
*/
public float getReflectionGap() {
return reflectionGap;
}
/**
* Sets the reflection gap.
*
* @param reflectionGap
* the new reflection gap
*/
public void setReflectionGap(final float reflectionGap) {
this.reflectionGap = reflectionGap;
}
/**
* Checks if is with reflection.
*
* @return true, if is with reflection
*/
public boolean isWithReflection() {
return withReflection;
}
/**
* Sets the with reflection.
*
* @param withReflection
* the new with reflection
*/
public void setWithReflection(final boolean withReflection) {
this.withReflection = withReflection;
}
/**
* Sets the image reflection ratio.
*
* @param imageReflectionRatio
* the new image reflection ratio
*/
public void setImageReflectionRatio(final float imageReflectionRatio) {
this.imageReflectionRatio = imageReflectionRatio;
}
/**
* Gets the image reflection ratio.
*
* @return the image reflection ratio
*/
public float getImageReflectionRatio() {
return imageReflectionRatio;
}
public CoverFlow(final Context context) {
super(context);
this.setStaticTransformationsEnabled(true);
}
public CoverFlow(final Context context, final AttributeSet attrs) {
this(context, attrs, android.R.attr.galleryStyle);
}
public CoverFlow(final Context context, final AttributeSet attrs, final int defStyle) {
super(context, attrs, defStyle);
parseAttributes(context, attrs);
this.setStaticTransformationsEnabled(true);
}
/**
* Get the max rotational angle of the image.
*
* @return the mMaxRotationAngle
*/
public int getMaxRotationAngle() {
return mMaxRotationAngle;
}
/**
* Sets the.
*
* @param adapter
* the new adapter
*/
@Override
public void setAdapter(final SpinnerAdapter adapter) {
if (!(adapter instanceof AbstractCoverFlowImageAdapter)) {
throw new IllegalArgumentException("The adapter should derive from "
+ AbstractCoverFlowImageAdapter.class.getName());
}
final AbstractCoverFlowImageAdapter coverAdapter = (AbstractCoverFlowImageAdapter) adapter;
coverAdapter.setWidth(imageWidth);
coverAdapter.setHeight((float)(imageHeight*(1.2)));
if (withReflection) {
final ReflectingImageAdapter reflectAdapter = new ReflectingImageAdapter(coverAdapter);
reflectAdapter.setReflectionGap(reflectionGap);
reflectAdapter.setWidthRatio(imageReflectionRatio);
reflectAdapter.setWidth(imageWidth);
reflectAdapter.setHeight(imageHeight * (1 + imageReflectionRatio));
super.setAdapter(reflectAdapter);
} else {
super.setAdapter(adapter);
}
}
/**
* Set the max rotational angle of each image.
*
* @param maxRotationAngle
* the mMaxRotationAngle to set
*/
public void setMaxRotationAngle(final int maxRotationAngle) {
mMaxRotationAngle = maxRotationAngle;
}
/**
* Get the Max zoom of the centre image.
*
* @return the mMaxZoom
*/
public int getMaxZoom() {
return mMaxZoom;
}
/**
* Set the max zoom of the centre image.
*
* @param maxZoom
* the mMaxZoom to set
*/
public void setMaxZoom(final int maxZoom) {
mMaxZoom = maxZoom;
}
/**
* Get the Centre of the Coverflow.
*
* @return The centre of this Coverflow.
*/
private int getCenterOfCoverflow() {
return (getWidth() - getPaddingLeft() - getPaddingRight()) / 2 + getPaddingLeft();
}
/**
* Get the Centre of the View.
*
* @return The centre of the given view.
*/
private static int getCenterOfView(final View view) {
return view.getLeft() + view.getWidth() / 2;
}
/**
* {@inheritDoc}
*
* @see #setStaticTransformationsEnabled(boolean)
*/
@Override
protected boolean getChildStaticTransformation(final View child, final Transformation t) {
mCoveflowCenter = getCenterOfCoverflow();
final int childCenter = getCenterOfView(child)
+ offsetChildrenLeftAndRight();
final int childWidth = child.getWidth();
int rotationAngle = 0;
t.clear();
t.setTransformationType(Transformation.TYPE_MATRIX);
// FacyLog.writeToLog("mCoveflowCenter : "+mCoveflowCenter+" , childCenter:"+childCenter+" , difference : "+(mCoveflowCenter
// - childCenter)+" , ");
if ((mCoveflowCenter - childCenter) < 45
&& (mCoveflowCenter - childCenter) > -45) {
transformImageBitmap((ImageView) child, t, 0);
Log.i("rotation angel", "rotation angel : 0");
// FacyLog.writeToLog("rotation angel : 0");
} else {
rotationAngle = (int) (((float) (mCoveflowCenter - childCenter) / childWidth) * mMaxRotationAngle);
if (Math.abs(rotationAngle) > mMaxRotationAngle) {
rotationAngle = (rotationAngle < 0) ? -mMaxRotationAngle
: mMaxRotationAngle;
}
transformImageBitmap((ImageView) child, t, rotationAngle);
Log.i("rotation angel", "rotation angel : " + rotationAngle);
// FacyLog.writeToLog("rotation angel : "+rotationAngle);
}
// FacyLog.writeToLog("\n");
return true;
}
private int offsetChildrenLeftAndRight() {
int offset = 0;
for (int i = getChildCount() - 1; i >= 0; i--) {
getChildAt(i).offsetLeftAndRight(offset);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN)
getChildAt(i).invalidate();
}
return offset;
}
/**
* This is called during layout when the size of this view has changed. If
* you were just added to the view hierarchy, you're called with the old
* values of 0.
*
* @param w
* Current width of this view.
* @param h
* Current height of this view.
* @param oldw
* Old width of this view.
* @param oldh
* Old height of this view.
*/
@Override
protected void onSizeChanged(final int w, final int h, final int oldw, final int oldh) {
mCoveflowCenter = getCenterOfCoverflow();
super.onSizeChanged(w, h, oldw, oldh);
}
/**
* Transform the Image Bitmap by the Angle passed.
*
* @param imageView
* ImageView the ImageView whose bitmap we want to rotate
* @param t
* transformation
* @param rotationAngle
* the Angle by which to rotate the Bitmap
*/
private void transformImageBitmap(final ImageView child, final Transformation t, final int rotationAngle) {
mCamera.save();
final Matrix imageMatrix = t.getMatrix();
final int height = child.getLayoutParams().height;
final int width = child.getLayoutParams().width;
final int rotation = Math.abs(rotationAngle);
mCamera.translate(0.0f, 0.0f, 100.0f);
// As the angle of the view gets less, zoom in
if (rotation < mMaxRotationAngle) {
final float zoomAmount = (float) (mMaxZoom + rotation * 1.5);
mCamera.translate(0.0f, 0.0f, zoomAmount);
}
mCamera.rotateY(rotationAngle);
mCamera.getMatrix(imageMatrix);
imageMatrix.preTranslate(-(width / 2.0f), -(height / 2.0f));
imageMatrix.postTranslate((width / 2.0f), (height / 2.0f));
mCamera.restore();
}
/**
* Parses the attributes.
*
* @param context
* the context
* @param attrs
* the attrs
*/
private void parseAttributes(final Context context, final AttributeSet attrs) {
final TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.CoverFlow);
try {
imageWidth = a.getDimension(R.styleable.CoverFlow_imageWidth, 480);
imageHeight = a.getDimension(R.styleable.CoverFlow_imageHeight, 320);
withReflection = a.getBoolean(R.styleable.CoverFlow_withReflection, false);
imageReflectionRatio = a.getFloat(R.styleable.CoverFlow_imageReflectionRatio, 0.4f);
reflectionGap = a.getDimension(R.styleable.CoverFlow_reflectionGap, 4);
setSpacing(-20);
setAlwaysDrawnWithCacheEnabled(true);
} finally {
a.recycle();
}
}
}