Join FlipAndroid.COM Telegram Group: https://t.me/joinchat/F_aqThGkhwcLzmI49vKAiw


Utilizar Glide para cargar mapa de bits en ImageView

¿Cómo puedo usar la biblioteca Glide para cargar Bitmap en mi ImageView? Quiero crear una imagen personalizada con texto y cargarla en la imagen con Glide.

Este es mi método para crear bitmap personalizado con texto

public Bitmap imageWithText(String text) { TextView tv = new TextView(context); tv.setText(text); tv.setTextColor(Color.WHITE); tv.setBackgroundColor(Color.BLACK); tv.setTypeface(null, Typeface.BOLD); tv.setGravity(Gravity.CENTER); tv.setTextSize(20); tv.setPadding(0, 25, 0, 0); Bitmap testB = Bitmap.createBitmap(100, 100, Bitmap.Config.ARGB_8888); Canvas c = new Canvas(testB); tv.layout(0, 0, 100, 100); tv.draw(c); return testB; } 

Pero cuando intento cargar este mapa de bits usando glide estoy recibiendo error

 Glide.with(getContext()).load(imageWithText("Random text")).into(holder.imgPhoto); 

  • Comparación de imágenes de mapa de bits en Android
  • ¿Necesita hacer un cierre adicional en un FileOutputStream al utilizar Bitmap.compress ()?
  • Cómo convertir una imagen Drawable de recursos a un mapa de bits
  • InDither obsoleto en android N
  • Uso óptimo de BitmapFactory.Options.inSampleSize para la velocidad
  • BitmapFactory.Options da 0 ancho y altura
  • Imagen de mapa de bits con esquinas redondeadas con trazo
  • JNI operaciones de mapa de bits, para ayudar a evitar OOM cuando se utilizan imágenes grandes
  • 3 Solutions collect form web for “Utilizar Glide para cargar mapa de bits en ImageView”

    @rookiedev tiene razón, no hay load(Bitmap) en Glide , por una razón: la adquisición de un Bitmap suele tomar tiempo ya veces bloquear E / S. Por lo tanto, no es una buena práctica llamar a imageWithText en el subproceso de la interfaz de usuario. Actualización : Dicho esto, he propuesto esta característica hace un tiempo; Y mientras que los hacks son más fáciles de hacer que usted puede encontrar el "Glide way" a continuación, que recomiendo encarecidamente.

    Glide está diseñado para ser flexible y este problema demuestra que el rasgo extremadamente bien. La siguiente implementación puede parecer larga, pero todas las piezas tienen su razón de existir. Dada la ganancia de rendimiento, esta cantidad de código para adaptarse a su generador en el mundo de Glide no es mucho. Traté de darle formato a corto, colapso partes irrelevantes y el uso de importaciones estáticas para ser más corto (ver el final de las importaciones).

    El código también incluye la interfaz de usuario generada mediante programación, por lo que sólo puede copiar y pegar todo el código a continuación en GlideGeneratedImageListFragment.java y ejecutarlo; La única dependencia externa es RecyclerView de lib de soporte.

     class GeneratingAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> { // See https://docs.google.com/drawings/d/1KyOJkNd5Dlm8_awZpftzW7KtqgNR6GURvuF6RfB210g/edit?usp=sharing // ModelType/A, DataType/T, ResourceType/Z, TranscodeType/R private final GenericRequestBuilder<GenerateParams, GenerateParams, Bitmap, GlideDrawable> generator; public GeneratingAdapter(final Context context) { generator = Glide // this part should be cleaner in Glide 4.0, but that's not released yet .with(context) .using(new GenerateParamsPassthroughModelLoader(), GenerateParams.class) // custom class .from(GenerateParams.class) .as(Bitmap.class) .transcode(new BitmapToGlideDrawableTranscoder(context), GlideDrawable.class) // builtin .decoder(new GenerateParamsBitmapResourceDecoder(context)) // custom class .encoder(new BitmapEncoder(Bitmap.CompressFormat.PNG, 0/*ignored for lossless*/)) // builtin .cacheDecoder(new FileToStreamDecoder<Bitmap>(new StreamBitmapDecoder(context))) // builtin //.placeholder(new ColorDrawable(Color.YELLOW)) // you can pre-set placeholder and error .error(new ColorDrawable(Color.RED)) // so it's easier when binding //.diskCacheStrategy(DiskCacheStrategy.NONE) // only for debugging to always regenerate //.skipMemoryCache(true) // only for debugging to always regenerate ; } @Override public int getItemCount() { return 1000; } private final float[] colorCache = new float[] {0, 1.0f, 0.5f}; private final float[] bgCache = new float[] {0, 0.5f, 1.0f}; @Override public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) { colorCache[0] = bgCache[0] = (position * 15) % 360; // just to have a fancy example :) GenerateParams params = new GenerateParams( // omit position to see Glide caching in action (every 24th item / 12th row is the same) "android text"/* + " #" + position*/, Color.HSVToColor(colorCache), Color.HSVToColor(bgCache) ); generator/*.clone() in case you see weird behavior*/.load(params).into((ImageView)holder.itemView); } @Override public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { int height = parent.getContext().getResources().getDisplayMetrics().heightPixels / 3; ImageView view = new ImageView(parent.getContext()); view.setLayoutParams(new RecyclerView.LayoutParams(MATCH_PARENT, height)); view.setScaleType(ImageView.ScaleType.FIT_CENTER); return new RecyclerView.ViewHolder(view) {}; // anon class for brevity } } public class GlideGeneratedImageListFragment extends Fragment { @Override public @Nullable View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { RecyclerView view = new RecyclerView(container.getContext()); view.setLayoutParams(new MarginLayoutParams(MATCH_PARENT, MATCH_PARENT)); view.setLayoutManager(new GridLayoutManager(container.getContext(), 2 /*columns*/)); view.setAdapter(new GeneratingAdapter(view.getContext())); return view; } } /** Extracted params from imageWithText, but left some hardcoded values like 20sp/bold/center in {@link Generators}. */ class GenerateParams { final String text; final int color; final int background; public GenerateParams(String text, int color, int bg) { this.text = text; this.color = color; this.background = bg; } public String getId() { // TODO make sure it's unique for every possible instance of GenerateParams // because it will affect how the resulting bitmap is cached // the below is correct correct for the current fields, if those change this has to change return String.format(Locale.ROOT, "%s-%08x-%08x", text, color, background); } } /** Boilerplate because of the degeneration in ModelType == DataType, but important for caching. * @see GeneratingAdapter#generator */ class GenerateParamsPassthroughModelLoader implements ModelLoader<GenerateParams, GenerateParams> { @Override public DataFetcher<GenerateParams> getResourceFetcher(final GenerateParams model, int width, int height) { return new DataFetcher<GenerateParams>() { @Override public GenerateParams loadData(Priority priority) throws Exception { return model; } @Override public void cleanup() { } @Override public String getId() { return model.getId(); } @Override public void cancel() { } }; } } /** Handles pooling to reduce/prevent GC lagging from too many {@link Bitmap#createBitmap}s */ class GenerateParamsBitmapResourceDecoder implements ResourceDecoder<GenerateParams, Bitmap> { private final Context context; public GenerateParamsBitmapResourceDecoder(Context context) { this.context = context; } @Override public Resource<Bitmap> decode(GenerateParams source, int width, int height) throws IOException { BitmapPool pool = Glide.get(context).getBitmapPool(); Bitmap bitmap = pool.getDirty(width, height, Bitmap.Config.ARGB_8888); if (bitmap == null) { bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888); } Generators.imageWithTextNoLayout(context, bitmap, source); return BitmapResource.obtain(bitmap, pool); } @Override public String getId() { // be careful if you change the Generator implementation you have to change this // otherwise the users may see a cached image; or clear cache on app update return "com.example.MyImageGenerator"; } } class Generators { /** OP's original implementation fixed for real centering */ public static Bitmap imageWithText(Context context, Bitmap bitmap, GenerateParams params) { TextView view = new TextView(context); view.setText(params.text); view.setTextColor(params.color); view.setBackgroundColor(params.background); view.setTypeface(null, Typeface.BOLD); view.setGravity(Gravity.CENTER); view.setTextSize(20 /*sp*/); Canvas canvas = new Canvas(bitmap); view.measure(makeMeasureSpec(canvas.getWidth(), EXACTLY), makeMeasureSpec(canvas.getHeight(), EXACTLY)); view.layout(0, 0, canvas.getWidth(), canvas.getHeight()); view.draw(canvas); return bitmap; } /** Generate centered text without creating a View, more lightweight. * Consider https://stackoverflow.com/a/8369690/253468 for multiline support. */ public static Bitmap imageWithTextNoLayout(Context context, Bitmap bitmap, GenerateParams params) { Paint paint = new Paint(); paint.setColor(params.color); paint.setTextAlign(Paint.Align.CENTER); // text's anchor for the x given in drawText paint.setTextSize(applyDimension(COMPLEX_UNIT_SP, 20, context.getResources().getDisplayMetrics())); paint.setTypeface(Typeface.DEFAULT_BOLD); Canvas canvas = new Canvas(bitmap); canvas.drawColor(params.background); canvas.drawText(params.text, canvas.getWidth() / 2, canvas.getHeight() / 2, paint); return bitmap; } } // Here are the imports in case you need it; // didn't want to put it in the beginning to keep the relevant code first. import java.io.IOException; import java.util.Locale; import android.content.Context; import android.graphics.*; import android.graphics.drawable.ColorDrawable; import android.os.Bundle; import android.support.annotation.Nullable; import android.support.v4.app.Fragment; import android.support.v7.widget.*; import android.view.*; import android.view.ViewGroup.MarginLayoutParams; import android.widget.*; import static android.util.TypedValue.*; import static android.view.View.MeasureSpec.*; import static android.view.ViewGroup.LayoutParams.*; import com.bumptech.glide.*; import com.bumptech.glide.load.ResourceDecoder; import com.bumptech.glide.load.data.DataFetcher; import com.bumptech.glide.load.engine.Resource; import com.bumptech.glide.load.engine.bitmap_recycle.BitmapPool; import com.bumptech.glide.load.model.ModelLoader; import com.bumptech.glide.load.resource.bitmap.*; import com.bumptech.glide.load.resource.drawable.GlideDrawable; import com.bumptech.glide.load.resource.file.FileToStreamDecoder; import com.bumptech.glide.load.resource.transcode.BitmapToGlideDrawableTranscoder; 

    Así es como se ve (el desplazamiento real es mucho más suave, GIF es muy bajo FPS):

    Introduzca aquí la descripción de la imagen

    Observe cómo carga los primeros elementos y luego carga gradualmente el resto. Se necesita un poco que la caché de memoria y piscina se calienta, pero puede utilizar un preloader si desea incluso más suave pantalla. Después de que se calienta se desplaza muy bien. El botón Eliminar de la barra de acciones llama a Glide.clearDiskCache() y Glide.clearMemory() para que empiece a regenar los elementos de nuevo.

    No sé el rendimiento, pero puede probar esto:

    En primer lugar, transformar su mapa de bits como matriz de bytes []:

     private byte[] bitmapToByte(Bitmap bitmap){ ByteArrayOutputStream stream = new ByteArrayOutputStream(); bitmap.compress(Bitmap.CompressFormat.JPEG, 100, stream); byte[] byteArray = stream.toByteArray(); return byteArray; } 

    A continuación, utilice el deslizamiento de esta manera:

     Glide.with(holder.imagePhoto.getContext()).load(bitmapToByte(yourBitmap)).asBitmap().override(300, 300).fitCenter().into(holder.imagePhoto); 

    En tu caso:

     Glide.with(holder.imagePhoto.getContext()).load(bitmapToByte(yourBitmap)).asBitmap().into(holder.imagePhoto); //>>not tested 

    De acuerdo con la documentación, no creo que el método load () puede tomar un Bitmap como parámetro. La fuente de la imagen (es decir, el parámetro) podría ser una URL, un recurso dibujable y un archivo.

    Sin embargo, si desea cargar un mapa de bits en un ImageView, no necesita utilizar la biblioteca Glide. Sólo use la siguiente declaración

     holder.imgPhoto.setImageBitmap(imageWithText("Random text")); 
    FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.