从android客户端通过套接字发送后收到黑色图像

Posted

技术标签:

【中文标题】从android客户端通过套接字发送后收到黑色图像【英文标题】:Black image is received after being sent over socket from android client 【发布时间】:2022-01-04 23:03:14 【问题描述】:

我的 android 应用程序和台式电脑之间有一个 TCP 连接,我想通过套接字发送 ImageView。我的问题是图像显然已成功发送,因为它有 9.7KiB。但是,当我尝试可视化此图像时,我得到一个黑色图像,并且在 Android Studio IDE 中没有抛出明显的错误。

发送图片的安卓应用:

private ImageView mImageView;
mImageView = (ImageView) findViewById(R.id.frame_image);
private final OnClickListener mOnClickListener = new OnClickListener() 
    @Override
    public void onClick(View view) 
        switch (view.getId()) 
            case R.id.button_camera:
                if (!Check.isFastClick()) 
                     return;
                  
                  if (mCameraHandler != null) 
                     if (mCameraHandler.isOpened()) 
                          if (checkPermissionWriteExternalStorage()) 
                            Drawable drawable = mImageView.getDrawable();
                            Bitmap bitmap = getBitmapFromDrawable(drawable);
                            ByteArrayOutputStream baos = new  ByteArrayOutputStream();
                            bitmap.compress(Bitmap.CompressFormat.PNG, 0, baos);
                            byte[] array = baos.toByteArray();
                            SendImageClient sendImageClient = new SendImageClient();
                            sendImageClient.execute(array);
                              
                        
                 
            break;
        ;

public Bitmap getBitmapFromDrawable(Drawable drawable)
    Bitmap bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(),drawable.getIntrinsicHeight(), Bitmap.Config.ARGB_8888);
    Canvas canvas = new Canvas(bitmap);
    canvas.drawColor(Color.WHITE);
    drawable.draw(canvas);
    return bitmap;




    public class SendImageClient extends AsyncTask<byte[], Void, Void> 
          @Override
           protected Void doInBackground(byte[]... voids) 
        
                try 
                    Socket socket= new Socket("192.168.0.14",9999);
        
                    OutputStream out = socket.getOutputStream();
                    DataOutputStream dataOutputStream= new DataOutputStream(out);
                    dataOutputStream.write(voids[0],0,voids[0].length);
                    dataOutputStream.close();
                    out.close();
                    socket.close();
        
                 catch (IOException e) 
                    e.printStackTrace();
                
                return null;
            
        

activity_main.xml

<com.serenegiant.widget.UVCCameraTextureView
    android:id="@+id/camera_view"
    android:layout_
    android:layout_
    android:layout_centerHorizontal="true"
    android:layout_centerVertical="true"
    android:layout_toRightOf="@id/menu_layout" />

<com.serenegiant.widget.AutoFitTextureView
    android:id="@+id/textureView"
    android:layout_
    android:visibility="invisible"
    android:layout_toRightOf="@id/menu_layout"
    android:layout_ />

<ImageView
    android:id="@+id/frame_image"
    android:layout_
    android:layout_
    android:layout_alignBottom="@id/camera_view"
    android:layout_alignLeft="@id/camera_view"
    android:layout_alignRight="@id/camera_view"
    android:layout_alignTop="@id/camera_view" />

服务器脚本.py

from socket import *

port = 9999
s = socket(AF_INET, SOCK_STREAM)
s.bind(('', port))
s.listen(1)
conn, addr = s.accept()
print("Connected by the ",addr)


with open('/home/pi/Desktop/frames_saved/image.jpg', 'wb') as file:
    while True:
        data = conn.recv(1024*8)
        if not data: break
        file.write(data)


conn.close() 

为什么我得到一个黑色的图像,我如何才能将 ImageView 中显示的实际图像发送到桌面?

【问题讨论】:

【参考方案1】:

此代码只创建一个空位图

Bitmap bitmap = Bitmap.createBitmap(mImageView.getWidth(), mImageView.getHeight(), Bitmap.Config.ARGB_8888);

从 ImageView 中获取位图

ImageView mImageView = findViewById(R.id.image);
Drawable drawable = mImageView .getDrawable();

Bitmap bitmap = getBitmapFromDrawable(drawable);
public Bitmap getBitmapFromDrawable(Drawable drawable)
        Bitmap bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(),drawable.getIntrinsicHeight(), Bitmap.Config.ARGB_8888);
        Canvas canvas = new Canvas(bitmap);
        canvas.drawColor(Color.WHITE);
        drawable.draw(canvas);
        return bitmap;
    

【讨论】:

它给了我这个:java.lang.NullPointerException: Attempt to call virtual method 'android.graphics.Bitmap android.graphics.drawable.BitmapDrawable.getBitmap()' on an null object reference at com. MyApp.MainActivity$14.onClick(MainActivity.java:1379) 我已经编辑了我的答案。它可以帮助你。 对我来说不幸的是,它仍然在这一行给出相同的错误:Bitmap bitmap = getBitmapFromDrawable(drawable);。错误再次是 java.lang.NullPointerException: Attempt to invoke virtual method 'android.graphics.Bitmap android.graphics.drawable.BitmapDrawable.getBitmap()' on an null object reference。但是,我已经根据您的参考编辑了我的代码 确保你的 imageView 有数据。你可以在你的xml中添加app:srcCompat="@android:drawable/xxxx" /&gt;&lt;ImageView/&gt;ImageView.setImageResource(R.drawable.xxx) 我确实尝试过研究,但添加任何一行都会出错。添加 app:srcCompat="@android:drawable/xxxx" /> 将给出无法解析符号 '@android:drawable/xxx.而 mImageView.setImageResource(test);其中 test =1 将给出 android.content.res.Resources$NotFoundException: Resource ID #0xa

以上是关于从android客户端通过套接字发送后收到黑色图像的主要内容,如果未能解决你的问题,请参考以下文章

通过套接字从客户端发送缓冲图像到服务器

Android - 客户端关闭连接发送图像,然后接收回字符串

从内存中打开 PNG 文件并通过 TCP 套接字发送

如何通过套接字发送和接收图像

在 Flutter 中显示图像,通过套接字连接发送

套接字编程/通过无线发送二进制图像数据