目标是绘制一个位图,并在某物的顶部,绘制消除位图底层区域的形状。
我有一个概念证明来尝试和理解我应该如何去做这件事。我发现了许多关于使用的提示:
android.graphics.PorterDuff.Mode.CLEAR
下面的代码创建了一个蓝色背景的屏幕,并添加了一个自定义视图。该视图在画布上从下到上绘制:粉色背景,一个带有轻微插入以显示粉色背景的位图,以及每个PorterDuffXfermode的黄色圆圈。
import android.app.Activity;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.PorterDuffXfermode;
import android.graphics.Paint.Style;
import android.graphics.PorterDuff.Mode;
import android.graphics.RectF;
import android.os.Bundle;
import android.view.View;
import android.view.Window;
import android.widget.RelativeLayout;
public class Test extends Activity {
Drawing d = null;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
RelativeLayout.LayoutParams rlp = null;
// Create the view for the xfermode test
d = new Drawing(this);
rlp = new RelativeLayout.LayoutParams(600, 900);
rlp.addRule(RelativeLayout.CENTER_IN_PARENT);
d.setLayoutParams(rlp);
RelativeLayout rl = new RelativeLayout(this);
rl.setBackgroundColor(Color.rgb(0, 0, 255));
rl.addView(d);
// Show the layout with the test view
setContentView(rl);
}
public class Drawing extends View {
Paint[] pDraw = null;
Bitmap bm = null;
public Drawing(Context ct) {
super(ct);
// Generate bitmap used for background
bm = BitmapFactory.decodeFile("mnt/sdcard/Pictures/test.jpg");
// Generate array of paints
pDraw = new Paint[16];
for (int i = 0; i<pDraw.length; i++) {
pDraw[i] = new Paint();
pDraw[i].setARGB(255, 255, 255, 0);
pDraw[i].setStrokeWidth(20);
pDraw[i].setStyle(Style.FILL);
}
// Set all transfer modes
pDraw[0].setXfermode(new PorterDuffXfermode(Mode.CLEAR));
pDraw[1].setXfermode(new PorterDuffXfermode(Mode.DARKEN));
pDraw[2].setXfermode(new PorterDuffXfermode(Mode.DST));
pDraw[3].setXfermode(new PorterDuffXfermode(Mode.DST_ATOP));
pDraw[4].setXfermode(new PorterDuffXfermode(Mode.DST_IN));
pDraw[5].setXfermode(new PorterDuffXfermode(Mode.DST_OUT));
pDraw[6].setXfermode(new PorterDuffXfermode(Mode.DST_OVER));
pDraw[7].setXfermode(new PorterDuffXfermode(Mode.LIGHTEN));
pDraw[8].setXfermode(new PorterDuffXfermode(Mode.MULTIPLY));
pDraw[9].setXfermode(new PorterDuffXfermode(Mode.SCREEN));
pDraw[10].setXfermode(new PorterDuffXfermode(Mode.SRC));
pDraw[11].setXfermode(new PorterDuffXfermode(Mode.SRC_ATOP));
pDraw[12].setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
pDraw[13].setXfermode(new PorterDuffXfermode(Mode.SRC_OUT));
pDraw[14].setXfermode(new PorterDuffXfermode(Mode.SRC_OVER));
pDraw[15].setXfermode(new PorterDuffXfermode(Mode.XOR));
}
@Override
public void onDraw(Canvas canv) {
// Background colour for canvas
canv.drawColor(Color.argb(255, 255, 0, 255));
// Draw the bitmap leaving small outside border to see background
canv.drawBitmap(bm, null, new RectF(15, 15, getMeasuredWidth() - 15, getMeasuredHeight() - 15), null);
float w, h;
w = getMeasuredWidth();
h = getMeasuredHeight();
// Loop, draws 4 circles per row, in 4 rows on top of bitmap
// Drawn in the order of pDraw (alphabetical)
for(int i = 0; i<4; i++) {
for(int ii = 0; ii<4; ii++) {
canv.drawCircle((w / 8) * (ii * 2 + 1), (h / 8) * (i * 2 + 1), w / 8 * 0.8f, pDraw[i*4 + ii]);
}
}
}
}
}
这是测试的结果:
CLEAR模式是左上角,显示为黑色。
在另一个我试图使用这个的例子中,我有一个对话片段,其中CLEAR模式擦除了整个对话片段,以便可以看到下面的活动。因此,我在这个测试中使用了许多不同的背景颜色。
这可能会像另一个例子让我相信的那样清除整个活动的像素吗?我本以为只有画布上与视图相关的像素可以被擦除,但在我的另一个示例中,自定义视图、基础图像视图和DialogFragment背景的像素都被清除了。
有人能帮我弄明白到底是怎么回事吗?
编辑:我复制了一个例子来证实我的怀疑。在DialogFragment中添加这个精确的自定义视图时,底层活动变得可见。
对我来说,这似乎是一个非常明确的指标,模式。CLEAR
也在以某种方式抹去下面视图的画布?我猜第一个例子中的黑色是顶层视图吗?
正如罗曼·盖伊在这里指出的:谷歌一下你需要在位图上写的东西,而不是你试图清除的带有圆圈的画布,然后把它设置在你视图中的主画布上。所以,做这样的事情:
// Generate bitmap used for background
bm = BitmapFactory.decodeFile("mnt/sdcard/Pictures/test.jpg");
// Create the paint and set the bitmap
Canvas temp = new Canvas(bm.getHeight(), bm.getWidth, Config.ARGB_8888);
// in onDraw()
temp.drawCircle((w / 8) * (ii * 2 + 1), (h / 8) * (i * 2 + 1), w / 8 * 0.8f, pDraw[i*4 + ii]);
// After loop
canvas.drawBitmap(....);
希望这有帮助。
我没有看到任何意想不到的东西。在Mode. CLEAR
的特定情况下,目标的颜色和alpha都被清除,这允许黑色背景显示。该实用程序允许人们尝试各种模式、颜色和alpha值,源可能会提供一些见解。在下面(有些过时)的图像中,CLEAR
区域显示了平台的PanelUI
委托提供的微弱细条纹灰色。
问题是硬件加速。对于您正在使用CLEAR绘制的特定视图,请将其关闭。如果您使用自定义视图,请在构造函数中执行此操作:
if (android.os.Build.VERSION.SDK_INT >= 11)
{
setLayerType(View.LAYER_TYPE_SOFTWARE, null);
}
也可以在视图引用上调用setLayerType。
问题内容: 目标只是绘制一个位图,并在其顶部绘制擦除该位图基础区域的形状。 我创建了简单的概念证明代码,以尝试了解该如何做。在这里的各种线程中,我发现了许多有关使用的提示: 下面的代码仅创建一个带有蓝色背景的屏幕并添加一个自定义视图。此视图在其画布上绘制粉红色背景,位图图像 (带有细边框显示粉红色背景)以及代表每个PorterDuffXfermode的黄色重叠圆圈。 清除模式在左上方,显示为黑色。
我有一个如下定义的表视图 当用户单击时,我使用单击的项目详细信息重新加载表。在我重新加载之前,我对表项调用清除 现在,当我单击另一个项目并尝试重新加载表格时,它看起来像下面这样。这是非常奇怪的,因为应该只有一行,但行的大小是一样的,就像从以前的点击,其余的行是空的,除了图标。当我点击图标时,没有任何反应。任何人以前都面临过这种情况。有人知道这是什么原因吗? 我的工具定义如下。它们只是2 的
拆除 Ceph 守护进程并卸载软件包后,此主机上可能还有集群中的数据, purge 和 purgedata 命令提供了一种清理主机的简便方法。 purgedata 如果只想清除 /var/lib/ceph 下的数据、并保留 Ceph 安装包,可以用 purgedata 命令: ceph-deploy purgedata {hostname} [{hostname} ...] purge 要清理掉
几周前,我在Laravel5.1中遇到了同样的问题,我可以用这个解决方案解决这个问题。 然而,现在我在Lumen中面临着同样的问题,但是我不能调用来清除缓存的文件。还有别的办法吗? 谢谢!
问题内容: 我想看看使用循环如何绘制不同值的图形。我想在同一情节上看到它。但我不想保留图中的前一个图。在MATLAB中,可以通过创建图形并在同一图形上绘图来实现。循环结束时将其关闭。 喜欢, 我在matplotlib中找不到与此等效的文件。通常,所有问题都与在同一图上绘制不同系列有关,这似乎在matplotlib上很自然,方法是使用来绘制多个序列,最后使用来显示所有序列。但是我想刷新剧情。 问题答
问题内容: 我有一个图像非常大的文件:例如9000x9000。 由于堆大小,我无法在内存中加载位图。但是我只需要显示此位图的一小部分,例如rect width = 100-200和height = 200-400(子位图的大小= 100x200) 如何从文件中检索此位图? 注意:我不想在100x200的图像中失去质量 谢谢 问题答案: 是否有解决方案? 例如,BitmapRegionDecoder