【问题标题】:Android: Upload image just taken bij cameraAndroid:上传刚刚拍摄的bij相机图像
【发布时间】:2017-03-07 15:25:06
【问题描述】:

我正在尝试制作一个使用相机拍照并将其发送到我的 NAS 的应用程序,我设法通过教程创建了一个应用程序,该教程拍摄照片,保存照片并将其显示在屏幕上。另一个教程向我展示了如何通过按屏幕上的“额外”按钮上传“选定”图像,只是我想摆脱这一步而不是显示图片,而是直接将图片发送到我的 NAS。

我创建的当前应用:

package com.deshpande.camerademo;

public class MainActivity extends AppCompatActivity {

    private Button takePictureButton;
    private ImageView imageView;
    private Uri file;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        takePictureButton = (Button) findViewById(R.id.button_image);
        imageView = (ImageView) findViewById(R.id.imageview);

        if (ContextCompat.checkSelfPermission(this, Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED) {
            takePictureButton.setEnabled(false);
            ActivityCompat.requestPermissions(this, new String[] { Manifest.permission.CAMERA, Manifest.permission.WRITE_EXTERNAL_STORAGE }, 0);
        }
    }

    @Override
    public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
        if (requestCode == 0) {
            if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED
                    && grantResults[1] == PackageManager.PERMISSION_GRANTED) {
                takePictureButton.setEnabled(true);
            }
        }
    }

    public void takePicture(View view) {
        Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
        file = Uri.fromFile(getOutputMediaFile());
        intent.putExtra(MediaStore.EXTRA_OUTPUT, file);

        startActivityForResult(intent, 100);
    }

    private static File getOutputMediaFile(){
        File mediaStorageDir = new File(Environment.getExternalStoragePublicDirectory(
                Environment.DIRECTORY_PICTURES), "WedCam");

        if (!mediaStorageDir.exists()){
            if (!mediaStorageDir.mkdirs()){
                Log.d("WedCam", "failed to create directory");
                return null;
            }
        }

        String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
        return new File(mediaStorageDir.getPath() + File.separator +
                    "IMG_"+ timeStamp + ".jpg");
    }

    @Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (requestCode == 100) {
        if (resultCode == RESULT_OK) {

            try {

                final FTPClient client = new FTPClient();
                final File image = new File(file.getPath());
                final FileInputStream fis = new FileInputStream(image);

                Thread thread = new Thread(new Runnable() {

                    @Override
                    public void run() {
                        try  {

                            client.connect("ftp://127.0.0.1:2221");
                            client.login("francis", "francis");

                            client.storeFile(image.getName(), fis);
                            client.logout();

                        } catch (Exception e) {
                            e.printStackTrace();
                        }
                    }
                });

                thread.start();

            } catch (IOException e) {
                e.printStackTrace();
            }
                }
            }
        }
    }
}

感谢@Matthias F。我成功了,这家伙很棒!

【问题讨论】:

  • 只需将这两个教程结合起来。先拍摄一张图片,然后将创建的文件上传到onActivityResult。
  • 两个教程都有不同的方法,上传教程使用php,我想我更喜欢ftp。虽然我可以找到相当多的 ftp 示例,但我似乎无法正确使用它们。我已经有一个 ftp 服务器,我只需要一个使用创建的文件并上传到我的 IP 地址的示例代码。如果我理解正确,我需要替换“imageView.setImageURI(file);”
  • 是的,没错。您在onActivityResult-Method 中创建了文件。因此,此时您需要启动上传过程。 Here 是如何将文件上传到 ftp 服务器的示例。
  • 我确定我做错了,我复制了示例并将其添加到我的代码中。可能我创建 InputStream 并声明要上传的文件的地方是错误的。查看更新的代码

标签: android image upload camera photo


【解决方案1】:

您需要将相机中保存的 URI 用于 FileInputStream。试试这个:

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (requestCode == 100) {
        if (resultCode == RESULT_OK) {

            try {

                final FTPClient client = new FTPClient();
                final File image = new File(file.getPath());
                final FileInputStream fis = new FileInputStream(image);

                Thread thread = new Thread(new Runnable() {

                    @Override
                    public void run() {
                        try  {

                            client.connect("127.0.0.1", 2221);
                            client.login("francis", "francis");
                            client.setFileType(FTP.BINARY_FILE_TYPE);

                            client.storeFile(image.getName(), fis);
                            client.logout();

                        } catch (Exception e) {
                            e.printStackTrace();
                        }
                    }
                });

                thread.start(); 

            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

现在FileInputStream 指向创建的图像。

编辑: 问题是上传是在 ui 线程上执行的,这在 android 中是不允许的。现在为上传过程创建了一个新的thead。另外我忘了说您需要访问 android 权限才能使用网络功能。 So you need to set <uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> 在AndroidManifest.xml。

【讨论】:

  • 谢谢,但在“client.storeFile(filename, fis);”它无法解析文件名。
  • 应用程序现在可以正常安装,但在我获取图像并接受后,应用程序崩溃了。它确实将图片保存到内部存储中,所以我认为上传部分仍然存在问题。错误代码添加到原始帖子中。
  • 我想我们快到了,当使用你的代码时,它说“fis”和“client”需要声明为final,因为它是从内部类中访问的。将它们声明为 final 后,我在 "fis = new FileInputStream(image);" 行上收到 "Error:(101, 33) error: cannot assign a value to final variable fis"
  • 我得到两次“错误:找不到符号变量 fis”和一次“错误:找不到符号变量客户端”。这一切都在代码的底部。
  • 新错误; “变量 fis 可能尚未初始化”和“变量客户端可能尚未初始化”
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-09-28
  • 2021-09-06
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多