如何$一个PNG加载ImageView的透明部分P $ pvent的onClick方法加载、透明、部分、方法

2023-09-04 23:28:53 作者:二货的世界你不懂

我目前正在开发堆积在彼此顶部的Andr​​oid应用程序,显示多个图像(的ImageView 为)。下面是如何层层当前配置的:

在背景层:缩放整个屏幕,必须点击 前景层:缩放整个屏幕,必须点击, 包含透明度允许用户看到一些的 背景层

我所面临的问题与前景层。我分配的onClick()方法ImageView的,但该方法被称为他们是否击中,这是有形的形象,以及其中包含的透明部分的部分。我只想前景ImageView的的onClick()方法被调用,当用户点击该ImageView的是不是透明的部分。

这是什么样的情景是这样的:

的对角线重新present的前景图像的透明部分。如果用户触摸这个空间,我想它来访问的前景图像的背景图像代替。谢谢你的任何可以提供帮助。

下面是我实现的解决方案(感谢回答下面):的

  // ontouchlistener  - 从事件得到X和Y
私人无效setClick(查看视图)
{
    view.setOnTouchListener(新View.OnTouchListener()
    {
        公共布尔onTouch(视图V,MotionEvent事件)
        {
            INT imageId = getImageId((int)的event.getX(),(int)的event.getY());
            如果(imageId> = 0)
                performActions(imageId);
            返回false;
        }
    });
}

//获得第一的ImageView的ID(从前台开始,
//工作向后),它包含一个非透明像素
私人诠释getImageId(INT X,int y)对
{
    ViewGroup中父=(ViewGroup中)findViewById(R.id.relative_layout);
    对(INT一个= parent.getChildCount() -  1 a取代; = 0; A--)
    {
        如果(parent.getChildAt(一)的instanceof ImageView的)
            如果(!checkPixelTransparent((ImageView的)parent.getChildAt(一)中,x,y))为
                返回parent.getChildAt(一).getId();
    }
    返回-1;
}

//得到ImageView的位图,获得从x像素,y坐标
//检查是否像素是透明
私人布尔checkPixelTransparent(ImageView的四,诠释的x,int y)对
{
    位图的位图=((BitmapDrawable)iv.getDrawable())getBitmap()。
    如果(Color.alpha(bitmap.getPixel(X,Y))== 0)
        返回true;
    其他
        返回false;
}
 

解决方案 利用PS绘制彩色的玻璃透明球

如果您的前景图像不只是一个矩形而是一个复杂的形象,你真正需要的触摸基于像素precise,您可以使用

http://developer.android.com/reference/android/查看/ View.OnTouchListener.html

  foregroundImage.setOnTouchListener(新View.OnTouchListener(){...});
 

MotionEvent 在回调将包含什么样的行动发生的事情(如触摸向上)和确切位置。

如果您知道的前景图像的确切大小,因为它显示出来,你可以找出其中它的像素被点击,然后检查是否该像素的Alpha值为0。或者,您可能需要应用一些缩放如果图像是缩放。这可能会因为根据屏幕尺寸和比例的图像可能已被缩放/不同地定位相当棘手。这也取决于你正在使用的布局。

有关的像素值的检查你可能需要保持在内存中的位图对象包含您前景的图像数据也是如此。

坦率地说,我怀疑你真的需要所有的precision除非你的前景图像是一个非常不规则的形状真的。

I am currently developing an Android app that displays multiple images (as ImageView's) stacked on top of each other. Here is how the layers are currently configured:

Background layer: scales the entire screen, must be clickable Foreground layer: scales the entire screen, must be clickable, contains transparency which allows the user to see some of the background layer

The problem I face is with the foreground layer. I am assigning the onClick() method to the imageview, but the method is being called whether they hit the portion of the image which is visible as well as the part which contains transparency. I only want the foreground ImageView onClick() method to be called when the user clicks a portion of that imageview that is not transparent.

This is what the scenario looks like:

The diagonal lines represent the transparent portion of the Foreground image. If a user touches this space, I want it to access the Background image instead of the Foreground image. Thank you for any assistance you can provide.

Here is the solution I implemented (Thanks to answer below):

//ontouchlistener - gets X and Y from event
private void setClick(View view)
{
    view.setOnTouchListener(new View.OnTouchListener() 
    {
        public boolean onTouch(View v, MotionEvent event) 
        {
            int imageId = getImageId((int)event.getX(), (int)event.getY());
            if (imageId >= 0)
                performActions(imageId);
            return false;
        }
    });
}

//get the ID of the first imageview (starting from foreground, 
//working backwards) which contains a non-transparent pixel
private int getImageId(int x, int y)
{
    ViewGroup parent = (ViewGroup) findViewById(R.id.relative_layout);
    for (int a = parent.getChildCount()-1; a >= 0; a--)
    {
        if (parent.getChildAt(a) instanceof ImageView)
            if (!checkPixelTransparent((ImageView)parent.getChildAt(a), x, y))
                return parent.getChildAt(a).getId();
    }
    return -1;
}

//get bitmap from imageview, get pixel from x, y coord
//check if pixel is transparent
private boolean checkPixelTransparent(ImageView iv, int x, int y)
{
    Bitmap bitmap = ((BitmapDrawable) iv.getDrawable()).getBitmap();
    if (Color.alpha(bitmap.getPixel(x, y)) == 0)
        return true;
    else
        return false;
}

解决方案

If your foreground image is not just a rect but a complex image and you really need that the touch is pixel-precise, you may use

http://developer.android.com/reference/android/view/View.OnTouchListener.html

foregroundImage.setOnTouchListener(new View.OnTouchListener(){...});

The MotionEvent in the callback will contain what kind of action happened (e.g. Touch up) and the exact location.

If you know the exact size of the foreground image as it is displayed, you can figure out which pixel of it was clicked, then check if that pixel's alpha is 0. Or you may need to apply some scaling if the image was scaled. This may get quite tricky since depending on the screen size and proportions the image may have been scaled/positioned differently. This also depends on the layouts your were using.

For the check of the pixel value you'd probably need to keep in memory the Bitmap object containing your foreground's image data as well.

Frankly, I doubt you'd really need all that precision unless your foreground image is really of a very irregular shape.