I'm new to Android, and I would like to know how to draw this blue shape:
Without using images, of course.
Thanks!
The easy way would be your suggested solution, ie. drawing all circles with no alpha to a bitmap, then draw that bitmap to another one using the desired alpha.
The hard way would be using blend modes, specifically PorterDuff.Mode in Android. An example can be found here.
Also Check this http://softwyer.wordpress.com/2012/01/21/1009/
An example
Bitmap bitmap = Bitmap.createBitmap(b.getWidth(), b.getHeight(), b.getConfig());
Canvas canvas = new Canvas(bitmap);
Paint p = new Paint(Paint.ANTI_ALIAS_FLAG);
p.setColor(Color.BLACK);
canvas.drawRoundRect(new RectF(0, 0, b.getWidth(), b.getHeight()), borderRadius, borderRadius, p);
p.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
canvas.drawBitmap(b, 0, 0, p);
Related
I am drawing text on a canvas. I would like to draw a solid circle of color over the text, and only have the circle be painted where it intersects the text. Example:
and what I want to do:
I'm not sure if this is possible, my draw code is simply:
public void onDraw(Canvas canvas) {
canvas.drawText("Hello", x, y, paint);
paint.setColor(orange);
canvas.drawOval(...);
}
I suppose I would need to apply some masking, but not sure how to get started.
follow this tutorial from a googler...
android-shaders-filters
BitmapShader may help you
You can use PorterDuffXfermode in Android to achieve this.
If you use below code it will work fine:
Bitmap original = Bitmap.createBitmap(canvas.getWidth(), canvas.getHeight(),
Bitmap.Config.ARGB_8888); // Created from Canvas
Bitmap mask =
Bitmap.createBitmap(getContext().getResources(),R.drawable.mask_image);
Bitmap result = Bitmap.createBitmap(mask.getWidth(), mask.getHeight(),
Config.ARGB_8888);
Canvas tempCanvas = new Canvas(result);
Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
tempCanvas.drawBitmap(original, 0, 0, null);
paint.setXfermode(new PorterDuffXfermode(Mode.DST_IN));
tempCanvas.drawBitmap(mask, 0, 0, paint);
paint.setXfermode(null);
canvas.drawBitmap(result, 0, 0, new Paint());
What does PorterDuff.Mode mean in android graphics.What does it do?
I need to textured some bitmap in ImageView. I use code bellow:
Bitmap original - texture;
Bitmap mask - image that I must textured;
Bitmap result - result image;
Canvas mCanvas = new Canvas(result);
Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_IN));
mCanvas.drawBitmap(original, 0, 0, null);
mCanvas.drawBitmap(mask, 0, 0, paint);
paint.setXfermode(null);
imgView.setImageBitmap(result);
imgView.setScaleType(ScaleType.CENTER);
it's work but I have
mask
and
texture
result image
But I need black borders and circuit of the image. Anybody know solution how to do that?
Solution my problem was very simple. Instead
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_IN));
Need to use
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.MULTIPLY));
And everything work like charm.
I'm using the mask a bitmap with another. The operation succeeds well, unfortunately the result of masking seen a slight black border, as you can see in the image:
How do I remove this border? in the source image is not there.
I'll post the code I'm using:
public Bitmap mask(Bitmap source) {
Bitmap targetBitmap = Bitmap.createBitmap(getWidth(),getHeight(),
Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(targetBitmap);
Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_IN));
paint.setAntiAlias(true);
paint.setDither(true);
canvas.drawBitmap(source, 0, 0, null);
canvas.drawBitmap(getMask(), 0, 0, paint);
paint.setXfermode(null);
return targetBitmap;
}
where getMask () returns the Bitmap that represents the figure of the Puzzle.
I hope to receive your help, thank you all
Sorry for my english :-)
UPDATE:
the black border is what I point out in this picture:
UPDATE:
place the sequence of transformation. The third image would be identical to the first but without color. The problem is the black edge of the puzzle.
I hope to be more clear:
The way I draw images with mask is kind of the other way around from what you do.
public Bitmap mask(Bitmap source) {
Bitmap targetBitmap = Bitmap.createBitmap(getWidth(),getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(targetBitmap);
Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
// paint.setAntiAlias(true); // you've already set this in the constructor
paint.setDither(true);
canvas.drawBitmap(getMask(), 0, 0, null);
canvas.drawBitmap(source, 0, 0, paint);
// paint.setXfermode(null); // no need for this
return targetBitmap;
}
Note that PorterDuff.Mode is set to SRC_IN (not DST_in) and that the mask is drawn first and then the image on top of that mask. With this approach you can also draw the previous source as the base mask, add the new (puzzle) mask and then draw the final source/image on top of that with SRC_IN paint to add new puzzle pieces each time.
If that doesn't solve the black border, check that your mask doesn't have feathered (transparent) edges that might be causing these problems.
Also, ANTI_ALIAS_FLAG doesn't do anything on textures. If you want smoothly scaled textures use paint.setFilterBitmap(true);
Is it possible to create a composite XML consisting of a combination of shapes?
Essentially I want to create an arrow using xml shapes -- is it possible?
If so, what's the best approach?
I'm assuming you're drawing that shape on a Canvas. You can do it in XML but it would become pretty hard to maintain.
Here is a simpler solution in Java code
Paint paint = new Paint();
paint.setStyle(Paint.Style.STROKE);
paint.setStrokeWidth(2);
paint.setColor(BLACK);
Path path = new Path();
path.moveTo(0, -10);
path.lineTo(5, 0);
path.lineTo(-5, 0);
path.close();
path.offset(10, 40);
canvas.drawPath(path, paint);
path.offset(50, 100);
canvas.drawPath(path, paint);
// offset is cumlative
// next draw displaces 50,100 from previous
path.offset(50, 100);
canvas.drawPath(path, paint);
If you want even more simpler solution, use a bitmap and use Matrix to rotate it in order to point in a specific direction
ImageView image = (ImageView) findViewById(R.id.bitmap_image);
Bitmap bMap = BitmapFactory.decodeResource(getResources(), R.drawable.test);
Matrix mat = new Matrix();
mat.postRotate(90);
Bitmap bMapRotate = Bitmap.createBitmap(bMap, 0, 0, bMap.getWidth(), bMap.getHeight(), mat, true);
image.setImageBitmap(bMapRotate);
I need to overlay two images in live wallpaper. The overlay images is the jpg which needs to be set to "additive" overlay. it adds the pixel value rather than calculating the transparency. how can i achieve this in android ?
You can make use of Android's Bitmap and Drawable classes mixed with Canvas, and try something like in this snippet:
public static Drawable mergeImage(Drawable orig, Drawable over, int left, int top) {
Bitmap original = ((BitmapDrawable)orig).getBitmap();
Bitmap overlay = ((BitmapDrawable)over).getBitmap();
Bitmap result = Bitmap.createBitmap(original.getWidth(), original.getHeight(), Config.ARGB_8888);
Canvas canvas = new Canvas(result);
Paint paint = new Paint();
paint.setAntiAlias(true);
canvas.drawBitmap(original, 0, 0, paint);
canvas.drawBitmap(overlay, left, top, paint);
return new BitmapDrawable(result);
}
I've coded a photo image gridview overlayered with "online status" using the above lines. Hope that it works for you too.
A more general approach may be to create a PorterDuffXfermode with your wanted PorterDuffMode and then set it on the Paint object that you use with your canvas, as referenced in mthama's answer but substituting some lines. This allows you to use other Porter-Duff modes as wanted/needed.
Paint paint = new Paint();
paint.setAntiAlias(true);
canvas.drawBitmap(original, 0, 0, paint);
paint.setXferMode(new PorterDuffXferMode(PorterDuff.Mode.OVERLAY));
canvas.drawBitmap(overlay, left, top, paint);
Mind you, I haven't tried this, so go with mthama's answer. :)