superponer dos imágenes en Android para establecer una imagen

Estoy intentando superponer dos imágenes en mi aplicación, pero parecen bloquearse en mi línea canvas.setBitmap() . ¿Qué estoy haciendo mal?

 private void test() { Bitmap mBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.t); Bitmap mBitmap2 = BitmapFactory.decodeResource(getResources(), R.drawable.tt); Bitmap bmOverlay = Bitmap.createBitmap(mBitmap.getWidth(), mBitmap.getHeight(), mBitmap.getConfig()); Canvas canvas = new Canvas(); canvas.setBitmap(bmOverlay); canvas.drawBitmap(mBitmap, new Matrix(), null); canvas.drawBitmap(mBitmap2, new Matrix(), null); testimage.setImageBitmap(bmOverlay); } 

Puede omitir la compleja manipulación del canvas y hacer esto completamente con Drawables, utilizando LayerDrawable . Tiene una de dos opciones: puede definirla en XML, luego simplemente establecer la imagen, o puede configurar un LayerDrawable dinámicamente en el código.

Solución n. ° 1 (a través de XML):

Cree un nuevo archivo XML extraíble, llamémoslo layer.xml :

     

Ahora configura la imagen usando ese Drawable:

 testimage.setImageDrawable(getResources().getDrawable(R.layout.layer)); 

Solución n. ° 2 (dinámica):

 Resources r = getResources(); Drawable[] layers = new Drawable[2]; layers[0] = r.getDrawable(R.drawable.t); layers[1] = r.getDrawable(R.drawable.tt); LayerDrawable layerDrawable = new LayerDrawable(layers); testimage.setImageDrawable(layerDrawable); 

(No he probado este código por lo que puede haber un error, pero este esquema general debería funcionar).

ok para que sepas que hay un progtwig que se llama DroidDraw. Puede ayudarte a dibujar objetos y probarlos uno encima del otro. Probé tu solución pero tenía animación debajo de la imagen más pequeña, así que no funcionó. Pero luego traté de colocar una imagen en una disposición relativa que se supone que debe estar debajo de la primera y luego, sobre ella, dibujé la otra imagen que se supone que se superpone y todo funcionó de maravilla. Así que RelativeLayout, DroidDraw y eres bueno ir 🙂 Simple, no hay ningún tipo de pokemon jiggery 🙂 y aquí hay un poco de código para ti:

El logo va a estar encima de la imagen de fondo de shazam.

        

Puede usar el siguiente código para resolver el problema o descargar la demo aquí

Crea dos funciones para manejar cada una.

Primero, se dibuja el canvas y las imágenes se dibujan una encima de la otra desde el punto (0,0)

Al hacer clic en el botón

 public void buttonMerge(View view) { Bitmap bigImage = BitmapFactory.decodeResource(getResources(), R.drawable.img1); Bitmap smallImage = BitmapFactory.decodeResource(getResources(), R.drawable.img2); Bitmap mergedImages = createSingleImageFromMultipleImages(bigImage, smallImage); img.setImageBitmap(mergedImages); } 

Función para crear una superposición.

 private Bitmap createSingleImageFromMultipleImages(Bitmap firstImage, Bitmap secondImage){ Bitmap result = Bitmap.createBitmap(firstImage.getWidth(), firstImage.getHeight(), firstImage.getConfig()); Canvas canvas = new Canvas(result); canvas.drawBitmap(firstImage, 0f, 0f, null); canvas.drawBitmap(secondImage, 10, 10, null); return result; }public void buttonClick(View view){ 

}

Lee mas

Es una respuesta un poco tarde, pero cubre la fusión de imágenes de las URL con Picasso

MergeImageView

 import android.annotation.TargetApi; import android.content.Context; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.graphics.Canvas; import android.graphics.Color; import android.os.AsyncTask; import android.os.Build; import android.util.AttributeSet; import android.util.SparseArray; import android.widget.ImageView; import com.squareup.picasso.Picasso; import java.io.IOException; import java.util.List; public class MergeImageView extends ImageView { private SparseArray bitmaps = new SparseArray<>(); private Picasso picasso; private final int DEFAULT_IMAGE_SIZE = 50; private int MIN_IMAGE_SIZE = DEFAULT_IMAGE_SIZE; private int MAX_WIDTH = DEFAULT_IMAGE_SIZE * 2, MAX_HEIGHT = DEFAULT_IMAGE_SIZE * 2; private String picassoRequestTag = null; public MergeImageView(Context context) { super(context); } public MergeImageView(Context context, AttributeSet attrs) { super(context, attrs); } public MergeImageView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); } @TargetApi(Build.VERSION_CODES.LOLLIPOP) public MergeImageView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) { super(context, attrs, defStyleAttr, defStyleRes); } @Override public boolean isInEditMode() { return true; } public void clearResources() { if (bitmaps != null) { for (int i = 0; i < bitmaps.size(); i++) bitmaps.get(i).recycle(); bitmaps.clear(); } // cancel picasso requests if (picasso != null && AppUtils.ifNotNullEmpty(picassoRequestTag)) picasso.cancelTag(picassoRequestTag); picasso = null; bitmaps = null; } public void createMergedBitmap(Context context, List imageUrls, String picassoTag) { picasso = Picasso.with(context); int count = imageUrls.size(); picassoRequestTag = picassoTag; boolean isEven = count % 2 == 0; // if url size are not even make MIN_IMAGE_SIZE even MIN_IMAGE_SIZE = DEFAULT_IMAGE_SIZE + (isEven ? count / 2 : (count / 2) + 1); // set MAX_WIDTH and MAX_HEIGHT to twice of MIN_IMAGE_SIZE MAX_WIDTH = MAX_HEIGHT = MIN_IMAGE_SIZE * 2; // in case of odd urls increase MAX_HEIGHT if (!isEven) MAX_HEIGHT = MAX_WIDTH + MIN_IMAGE_SIZE; // create default bitmap Bitmap bitmap = Bitmap.createScaledBitmap(BitmapFactory.decodeResource(context.getResources(), R.drawable.ic_wallpaper), MIN_IMAGE_SIZE, MIN_IMAGE_SIZE, false); // change default height (wrap_content) to MAX_HEIGHT int height = Math.round(AppUtils.convertDpToPixel(MAX_HEIGHT, context)); setMinimumHeight(height * 2); // start AsyncTask for (int index = 0; index < count; index++) { // put default bitmap as a place holder bitmaps.put(index, bitmap); new PicassoLoadImage(index, imageUrls.get(index)).execute(); // if you want parallel execution use // new PicassoLoadImage(index, imageUrls.get(index)).(AsyncTask.THREAD_POOL_EXECUTOR); } } private class PicassoLoadImage extends AsyncTask { private int index = 0; private String url; PicassoLoadImage(int index, String url) { this.index = index; this.url = url; } @Override protected Bitmap doInBackground(String... params) { try { // synchronous picasso call return picasso.load(url).resize(MIN_IMAGE_SIZE, MIN_IMAGE_SIZE).tag(picassoRequestTag).get(); } catch (IOException e) { } return null; } @Override protected void onPostExecute(Bitmap output) { super.onPostExecute(output); if (output != null) bitmaps.put(index, output); // create canvas Bitmap.Config conf = Bitmap.Config.RGB_565; Bitmap canvasBitmap = Bitmap.createBitmap(MAX_WIDTH, MAX_HEIGHT, conf); Canvas canvas = new Canvas(canvasBitmap); canvas.drawColor(Color.WHITE); // if height and width are equal we have even images boolean isEven = MAX_HEIGHT == MAX_WIDTH; int imageSize = bitmaps.size(); int count = imageSize; // we have odd images if (!isEven) count = imageSize - 1; for (int i = 0; i < count; i++) { Bitmap bitmap = bitmaps.get(i); canvas.drawBitmap(bitmap, bitmap.getWidth() * (i % 2), bitmap.getHeight() * (i / 2), null); } // if images are not even set last image width to MAX_WIDTH if (!isEven) { Bitmap scaledBitmap = Bitmap.createScaledBitmap(bitmaps.get(count), MAX_WIDTH, MIN_IMAGE_SIZE, false); canvas.drawBitmap(scaledBitmap, scaledBitmap.getWidth() * (count % 2), scaledBitmap.getHeight() * (count / 2), null); } // set bitmap setImageBitmap(canvasBitmap); } } } 

xml

  

Ejemplo

 List urls = new ArrayList<>(); String picassoTag = null; // add your urls ((MergeImageView)findViewById(R.id.iv_thumb)). createMergedBitmap(MainActivity.this, urls,picassoTag);