简体   繁体   中英

How to get an image from FirebaseStorage and convert it into a Bitmap

I'm launching an asynchronous function to get a StorageReference , get the StreamDownloadTask from it and trying to create a Bitmap from its InputStream

userRepository.getUserImg(id).stream
            .addOnSuccessListener { // StreamDownloadTask.TaskSnapshot!
                val picture = BitmapFactory.decodeStream(it.stream) // it.stream reported to return an InputStream
                user.value!!.img = picture
            }
            .addOnFailureListener { exception ->
                Log.e(TAG, exception.toString())
            }

however when I launch this function I get this error:

W/System.err: android.os.NetworkOnMainThreadException
W/System.err:     at android.os.StrictMode$AndroidBlockGuardPolicy.onNetwork(StrictMode.java:1565)
        at com.google.android.gms.org.conscrypt.Platform.blockGuardOnNetwork(:com.google.android.gms@200414022@20.04.14 (040700-294335909):0)
        at com.google.android.gms.org.conscrypt.ConscryptFileDescriptorSocket$SSLInputStream.read(:com.google.android.gms@200414022@20.04.14 (040700-294335909):2)
        at com.android.okhttp.okio.Okio$2.read(Okio.java:138)
        at com.android.okhttp.okio.AsyncTimeout$2.read(AsyncTimeout.java:213)
        at com.android.okhttp.okio.RealBufferedSource.read(RealBufferedSource.java:51)
        at com.android.okhttp.internal.http.Http1xStream$FixedLengthSource.read(Http1xStream.java:395)
W/System.err:     at com.android.okhttp.okio.RealBufferedSource$1.read(RealBufferedSource.java:372)
        at com.google.firebase.storage.StreamDownloadTask$StreamProgressWrapper.read(com.google.firebase:firebase-storage@@19.1.1:408)
        at java.io.BufferedInputStream.fill(BufferedInputStream.java:248)
        at java.io.BufferedInputStream.read1(BufferedInputStream.java:288)
        at java.io.BufferedInputStream.read(BufferedInputStream.java:347)
        at android.graphics.BitmapFactory.nativeDecodeStream(Native Method)
        at android.graphics.BitmapFactory.decodeStreamInternal(BitmapFactory.java:790)
        at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:765)
        at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:806)
        at it.polito.phony.lab3.user.profile.ShowProfileViewModel$loadUser$4.onSuccess(ShowProfileViewModel.kt:49)
        at it.polito.phony.lab3.user.profile.ShowProfileViewModel$loadUser$4.onSuccess(ShowProfileViewModel.kt:18)
        at com.google.firebase.storage.StorageTask.lambda$new$0(com.google.firebase:firebase-storage@@19.1.1:123)
        at com.google.firebase.storage.StorageTask$$Lambda$1.raise(Unknown Source:6)
        at com.google.firebase.storage.TaskListenerImpl.lambda$onInternalStateChanged$2(com.google.firebase:firebase-storage@@19.1.1:90)
        at com.google.firebase.storage.TaskListenerImpl$$Lambda$3.run(Unknown Source:6)
        at android.os.Handler.handleCallback(Handler.java:883)
        at android.os.Handler.dispatchMessage(Handler.java:100)
        at android.os.Looper.loop(Looper.java:214)
        at android.app.ActivityThread.main(ActivityThread.java:7356)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930)

I have also tried to get a Bitmap by getting the ByteArray from the StorageReference but the BitmapFactory is not able to create the Bitmap because it expect to receive a byte[] instead of a ByteArray as a parameter from my understanding.

I don't know the MVVM method , but it might give you an idea that will solve the problem in this way.

You can try this:

         Glide.with(getApplicationContext()).asBitmap().load(imgUrl).into(new CustomTarget<Bitmap>() {

                            @Override
                            public void onResourceReady(@NonNull Bitmap resource, @Nullable Transition<? super Bitmap> transition) {
                                img_icon.setImageBitmap(resource);

                            }

                            @Override
                            public void onLoadCleared(@Nullable Drawable placeholder) {


                            }
                        });

Once i did it with piccasso something like below (assuming that you know how to get the image uri from firebase, tell me if you want that code too)

    Thread thread = new Thread() {
                        public void run() {
                            try {
                                Bitmap bitmap = Picasso.with(getActivity())
                                        .load(uri).get();
                            } catch (Exception e) {
                               e.printStackTrace();
                            }
                        }
                    };
                    thread.start();
                })

for some reason the get() method can not be called on the main thread

have a good day Antonio Santoro

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM