解决方案 »

  1.   

    我宁可自己在onDraw中绘制三个区域
      

  2.   

    这是不是要做拼图啊,你百度下拼图的案例,其实重点是在写layout,如果把这个不规则的layout写出来,我感觉是自定义了layout才能把这样的不规则图形画出来的
      

  3.   

    自绘制的话,是这样: 定义View的一个子类,重写 onDraw(), onTouch()等方法
      

  4.   

    这个有点麻烦的,费时费力。基本上要用自定义控件,重写onDraw和onTouch,
    onDraw主要处理绘制出来的区域。
    onTouch主要是处理触控事件。
    我这简单的实现了onDraw,没时间弄。
    代码一会贴在下面
      

  5.   


    import java.io.IOException;import android.content.Context;
    import android.graphics.Bitmap;
    import android.graphics.BitmapFactory;
    import android.graphics.Canvas;
    import android.graphics.Matrix;
    import android.graphics.Paint;
    import android.graphics.Path;
    import android.util.AttributeSet;
    import android.view.View;public class ImageClipView extends View { private Bitmap leftImage;
    private Bitmap rightImage;
    private Bitmap downImage;
    private Matrix leftMatrix;
    private Matrix rightMatrix;
    private Matrix downMatrix;
    private float padding = 10;
    private Path left;
    private Path right;
    private Path down;
    private Paint paint;

    private int state = -1;
    private final int START = 1;

    public ImageClipView(Context context, AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
    } public ImageClipView(Context context, AttributeSet attrs) {
    super(context, attrs);
    } public ImageClipView(Context context) {
    super(context);
    } private void init(){
    try {
    leftImage = BitmapFactory.decodeStream(getContext().getAssets().open("clip_image.png"));
    rightImage = BitmapFactory.decodeStream(getContext().getAssets().open("right.png"));
    downImage = BitmapFactory.decodeStream(getContext().getAssets().open("down.png"));
    } catch (IOException e) {
    e.printStackTrace();
    } paint = new Paint();
    paint.setAntiAlias(true);
    initMatrix();
    initPath();
    }

    @Override
    protected void onDraw(Canvas canvas) {
    super.onDraw(canvas);
    if(leftImage != null){
    canvas.save();
    canvas.clipPath(left);
    canvas.drawBitmap(leftImage, leftMatrix, paint);
    canvas.restore();
    canvas.save();
    canvas.clipPath(right);
    canvas.drawBitmap(rightImage, rightMatrix, paint);
    canvas.restore();
    canvas.save();
    canvas.clipPath(down);
    canvas.drawBitmap(downImage, downMatrix, paint);
    canvas.restore();
    }
    }

    @Override
    protected void onLayout(boolean changed, int left, int top, int right,
    int bottom) {
    super.onLayout(changed, left, top, right, bottom);
    if(state > 0){
    return;
    }
    state = START;
    init();
    }

    private void initMatrix(){
    leftMatrix = new Matrix();
    rightMatrix = new Matrix();
    downMatrix = new Matrix();

    float w = getWidth();
    float h = getHeight();

    //第一个图片
    float scale = 1;
    float scaleX = w / leftImage.getWidth();
    float scaleY = h / leftImage.getHeight();
    scale = scaleX > scaleY ? scaleX : scaleY;
    leftMatrix.setScale(scale, scale);
    //第二个图片
    scaleX = w / rightImage.getWidth();
    scaleY = h / rightImage.getHeight();
    scale = scaleX > scaleY ? scaleX : scaleY;
    rightMatrix.setScale(scale, scale);
    //第三个图片
    scaleX = w / downImage.getWidth();
    scaleY = h / downImage.getHeight();
    scale = scaleX > scaleY ? scaleX : scaleY;
    downMatrix.setScale(scale, scale);

    }

    private void initPath(){

    float cpad = padding / 2;//padding = 10

    float w = getWidth();
    float h = getHeight();
    float bx = w / 2;
    float by = h / 2;

    left = new Path();
    right = new Path();
    down = new Path();

    left.moveTo(padding, padding);
    left.lineTo(bx - cpad, padding);
    left.lineTo(bx - cpad, by);
    left.lineTo(padding, h - 1.7f * padding);
    left.lineTo(padding, padding);
    left.close();

    right.moveTo(bx + cpad, padding);
    right.lineTo(w - padding, padding);
    right.lineTo(w - padding, h - 1.7f * padding);
    right.lineTo(bx + cpad, by);
    right.lineTo(bx + cpad, padding);
    right.close();

    down.moveTo(bx, by + 0.7f * padding);
    down.lineTo(padding * 1.41f, h - padding);
    down.lineTo(w - padding* 1.41f, h - padding);
    down.lineTo(bx, by + 0.7f * padding);
    down.close();

    }

    }
      

  6.   

    Quote: 引用 7 楼 lxfhjjsfq 的回复:

    这个有点麻烦的,费时费力。基本上要用自定义控件,重写onDraw和onTouch,
    onDraw主要处理绘制出来的区域。
    onTouch主要是处理触控事件。
    我这简单的实现了onDraw,没时间弄。
    好的,我尝试下
      

  7.   

    你这个是不是哪里有问题,我用你的代码试了下,老是报空指针呀!initMatrix方法的leftImage是空的
      

  8.   

    leftImage = BitmapFactory.decodeStream(getContext().getAssets().open("clip_image.png"));
                rightImage = BitmapFactory.decodeStream(getContext().getAssets().open("right.png"));
                downImage = BitmapFactory.decodeStream(getContext().getAssets().open("down.png"));
    替换成你的图片
      

  9.   

    你好,那个错,是我的图片放在res文件夹下面,是我的失误,不好意思啦!^_^  但是我发现,你这个只支持小米哦,在别的手机就不行了。
      

  10.   

    华为三星应该都没问题,不太可能出现哪个机型不支持的问题,毕竟是比较早的api了
      

  11.   

    恩,但是问题就是这样了,搞不懂,你能方便把你demo发给我吗?邮箱:[email protected]
      

  12.   


    import java.io.IOException;
    import android.annotation.SuppressLint;
    import android.content.Context;
    import android.graphics.Bitmap;
    import android.graphics.BitmapFactory;
    import android.graphics.Canvas;
    import android.graphics.Matrix;
    import android.graphics.Paint;
    import android.graphics.Path;
    import android.util.AttributeSet;
    import android.view.MotionEvent;
    import android.view.View;@SuppressLint("NewApi") 
    public class ImageClipView extends View { private Bitmap leftImage;
    private Bitmap rightImage;
    private Bitmap downImage;
    private Matrix leftMatrix;
    private Matrix rightMatrix;
    private Matrix downMatrix;
    private float padding = 10;
    private Path left;
    private Path right;
    private Path down;
    private Paint paint;

    private int state = -1;
    private final int START = 1;

    public ImageClipView(Context context, AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
    } public ImageClipView(Context context, AttributeSet attrs) {
    super(context, attrs);
    } public ImageClipView(Context context) {
    super(context);
    } private void init(){
    setLayerType(View.LAYER_TYPE_SOFTWARE, null);
    try {
    leftImage = BitmapFactory.decodeStream(getContext().getAssets().open("clip_image.png"));
    rightImage = BitmapFactory.decodeStream(getContext().getAssets().open("right.png"));
    downImage = BitmapFactory.decodeStream(getContext().getAssets().open("down.png"));
    } catch (IOException e) {
    e.printStackTrace();
    } paint = new Paint();
    paint.setAntiAlias(true);
    initMatrix();
    initPath();
    }

    @Override
    protected void onDraw(Canvas canvas) {
    super.onDraw(canvas);
    if(leftImage != null){
    canvas.save();
    canvas.clipPath(left);
    canvas.drawBitmap(leftImage, leftMatrix, paint);
    canvas.restore();
    canvas.save();
    canvas.clipPath(right);
    canvas.drawBitmap(rightImage, rightMatrix, paint);
    canvas.restore();
    canvas.save();
    canvas.clipPath(down);
    canvas.drawBitmap(downImage, downMatrix, paint);
    canvas.restore();
    }
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {

    switch(event.getAction()){
    case MotionEvent.ACTION_DOWN:
    if(isInsideLeft(event)){
    Bitmap temp = leftImage;
    leftImage = rightImage;
    rightImage = temp;

    Matrix tm = leftMatrix;
    leftMatrix = rightMatrix;
    rightMatrix = tm;
    }
    else if(isInsideRight(event)){
    Bitmap temp = rightImage;
    rightImage = downImage;
    downImage = temp;

    Matrix tm = rightMatrix;
    rightMatrix = downMatrix;
    downMatrix = tm;
    }else if(isInsideDown(event)){
    Bitmap temp = downImage;
    downImage = leftImage;
    leftImage = temp;

    Matrix tm = downMatrix;
    downMatrix = leftMatrix;
    leftMatrix = tm;
    }
    break;
    }
    invalidate();
    return super.onTouchEvent(event);
    }

    @Override
    protected void onLayout(boolean changed, int left, int top, int right,
    int bottom) {
    super.onLayout(changed, left, top, right, bottom);
    if(state > 0){
    return;
    }
    state = START;
    init();
    }

    private void initMatrix(){
    leftMatrix = new Matrix();
    rightMatrix = new Matrix();
    downMatrix = new Matrix();

    float w = getWidth();
    float h = getHeight();

    //第一个图片
    float scale = 1;
    float scaleX = w / leftImage.getWidth();
    float scaleY = h / leftImage.getHeight();
    scale = scaleX > scaleY ? scaleX : scaleY;
    leftMatrix.setScale(scale, scale);
    //第二个图片
    scaleX = w / rightImage.getWidth();
    scaleY = h / rightImage.getHeight();
    scale = scaleX > scaleY ? scaleX : scaleY;
    rightMatrix.setScale(scale, scale);
    //第三个图片
    scaleX = w / downImage.getWidth();
    scaleY = h / downImage.getHeight();
    scale = scaleX > scaleY ? scaleX : scaleY;
    downMatrix.setScale(scale, scale);

    }

    private void initPath(){

    float cpad = padding / 2;//padding = 10

    float w = getWidth();
    float h = getHeight();
    float bx = w / 2;
    float by = h / 2;

    left = new Path();
    right = new Path();
    down = new Path();

    left.moveTo(padding, padding);
    left.lineTo(bx - cpad, padding);
    left.lineTo(bx - cpad, by);
    left.lineTo(padding, h - 1.7f * padding);
    left.lineTo(padding, padding);
    left.close();

    right.moveTo(bx + cpad, padding);
    right.lineTo(w - padding, padding);
    right.lineTo(w - padding, h - 1.7f * padding);
    right.lineTo(bx + cpad, by);
    right.lineTo(bx + cpad, padding);
    right.close();

    down.moveTo(bx, by + 0.7f * padding);
    down.lineTo(padding * 1.41f, h - padding);
    down.lineTo(w - padding* 1.41f, h - padding);
    down.lineTo(bx, by + 0.7f * padding);
    down.close();

    }

    private boolean isInsideLeft(MotionEvent event){
    float x = event.getX();
    float y = event.getY();
    float w = getWidth();
    float h = getHeight();
    float bx = w / 2;
    float by = h / 2;

    if(x < 0 || x > bx || y < 0 || y > h){
    return false;
    }
    if(x + y - w < 0){
    return true;
    }
    return false;
    }

    private boolean isInsideRight(MotionEvent event){
    float x = event.getX();
    float y = event.getY();
    float w = getWidth();
    float h = getHeight();
    float bx = w / 2;
    float by = h / 2;

    if(x < bx || x > w || y < 0 || y > h){
    return false;
    }
    if(x > y){
    return true;
    }
    return false;
    }

    private boolean isInsideDown(MotionEvent event){
    float x = event.getX();
    float y = event.getY();
    float w = getWidth();
    float h = getHeight();
    float bx = w / 2;
    float by = h / 2;

    if(y < by || y > h){
    return false;
    }
    if(x < y && x + y - w > 0){
    return true;
    }
    return false;
    }
    }
    里面实现了点击替换图片的功能,也是说说点击的区域判断完成了。至于要缩放什么的就要你自己在onTouch中细化逻辑了,有时间的话就结贴吧。或者再等等有没有更好的方案。
      

  13.   

    果然是那个东西(setLayerType(View.LAYER_TYPE_SOFTWARE, null);)刚才查了下这个,也好难理解。算了,先不去理解了,你现在给的代码,我还得花时间好好研究下,等会我加上缩放试试看行不行,这次真的是太感谢你的帮助了!对于我来讲,就是起到了一个启蒙的作用。不然还真不知道用什么方式去实现这样的布局。真心感谢!