简体   繁体   中英

Android Studio: save image in SD Card

I keep a school project dealing with a ListView filled with images hosted on a server.
When someone selects an image from the list, this is shown by "original" size in another layout and even here everything went well.
But also ask when the image display have the option to save it to the SD Card and that's the part I can not do.

This is the code I did:

public class MainActivity extends AppCompatActivity {

private ListView listView;
private ProgressDialog progressDialog;
ArrayList asuntos=new ArrayList();
ArrayList imagen=new ArrayList();

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    Toolbar toolBar = (Toolbar) findViewById(R.id.toolbar);
    setSupportActionBar(toolBar);
    listView=(ListView) findViewById(R.id.list);
    progressDialog = new ProgressDialog(this);
    progressDialog.setCancelable(false);
    lista o=new lista();
    o.obtenerAvisos();
}

public class lista {

    public void obtenerAvisos() {

        asuntos.clear();
        imagen.clear();

        String tag_string_req = "req_data";

        progressDialog.setMessage("Conectando...");
        showDialog();

        StringRequest strReq = new StringRequest(Request.Method.POST, AppURLs.URL, new Response.Listener<String>() {

            public void onResponse(String response) {

                hideDialog();

                try {

                    JSONArray jsonArray = new JSONArray(response);

                    for (int i = 0; i < jsonArray.length(); i++) {
                        asuntos.add(jsonArray.getJSONObject(i).getString("asunto"));
                        imagen.add(jsonArray.getJSONObject(i).getString("publicacion"));
                    }

                    listView.setAdapter(new ImagenAdaptador(getApplicationContext()));
                } catch (JSONException e) {
                    e.printStackTrace();
                }
            }
        }, new Response.ErrorListener() {

            public void onErrorResponse(VolleyError error) {

                Toast.makeText(getApplicationContext(), error.getMessage(), Toast.LENGTH_LONG).show();
                hideDialog();
            }
        }) {

            protected Map<String, String> getParams() {

                Map<String, String> params = new HashMap<String, String>();
                params.put("tag", "data");
                return params;
            }

        };
        AppController.getInstance().addToRequestQueue(strReq, tag_string_req);
    }
}

private void showDialog() {

    if (!progressDialog.isShowing())
        progressDialog.show();
}

private void hideDialog() {

    if (progressDialog.isShowing())
        progressDialog.dismiss();
}

public class ImagenAdaptador extends BaseAdapter {

    Context ctx;
    LayoutInflater layoutInflater;
    SmartImageView smartImageView;
    TextView tvasunto;

    public ImagenAdaptador(Context applicationContext) {

        this.ctx=applicationContext;
        layoutInflater=(LayoutInflater)ctx.getSystemService(LAYOUT_INFLATER_SERVICE);
    }

    public int getCount() {
        return imagen.size();
    }

    public Object getItem(int position) {
        return position;
    }


    public long getItemId(int position) {
        return position;
    }


    public View getView(int position, View convertView, ViewGroup parent) {

        ViewGroup viewGroup=(ViewGroup) layoutInflater.inflate(R.layout.activity_main_items,null);
        smartImageView=(SmartImageView)viewGroup.findViewById(R.id.imagen1);
        tvasunto=(TextView) viewGroup.findViewById(R.id.tvAsunto);
        final String urlfinal="http://192.168.43.45/InfoTec/publicaciones/"+imagen.get(position).toString();
        Rect rect=new Rect(smartImageView.getLeft(), smartImageView.getTop(), smartImageView.getRight(), smartImageView.getBottom());
        smartImageView.setImageUrl(urlfinal, rect);
        tvasunto.setText(asuntos.get(position).toString());

        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {

            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                Intent intent = new Intent(MainActivity.this, Visor.class);
                intent.putExtra("arg", asuntos.get(position).toString());
                intent.putExtra("arg2",imagen.get(position).toString());
                startActivity(intent);
            }
        });
        return viewGroup;
    }
}
}

This part works, but this class is the problem:

public class Visor extends AppCompatActivity {

TextView tvasunto2;
SmartImageView smartImageView2;
Button descarga;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_visor);
    String original=getIntent().getStringExtra("arg");
    String imgOriginal=getIntent().getStringExtra("arg2");
    tvasunto2=(TextView) findViewById(R.id.tvAsunto2);
    smartImageView2=(SmartImageView) findViewById(R.id.imagen2);
    descarga=(Button) this.findViewById(R.id.button);

    tvasunto2.setText(original);
    String url="http://192.168.43.45/InfoTec/publicaciones/"+imgOriginal;
    Rect rect=new Rect(smartImageView2.getLeft(), smartImageView2.getTop(), smartImageView2.getRight(), smartImageView2.getBottom());
    smartImageView2.setImageUrl(url,rect);

    descarga.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {

        }
    });
}
}

If the selected image is displayed, but not now how to handle the data in the event the download button.
What would be the solution?

First, you need to get your Bitmap. You can already have it as an object Bitmap, or you can try to get it from the ImageView such as:

BitmapDrawable drawable = (BitmapDrawable) mImageView1.getDrawable();
Bitmap bitmap = drawable.getBitmap();

Then you must get to directory (a File object) from SD Card such as:

File sdCardDirectory = Environment.getExternalStorageDirectory();

Next, create your specific file for image storage:

File image = new File(sdCardDirectory, "test.png");

After that, you just have to write the Bitmap thanks to its method compress such as:

boolean success = false;

// Encode the file as a PNG image.
FileOutputStream outStream;
try {

    outStream = new FileOutputStream(image);
    bitmap.compress(Bitmap.CompressFormat.PNG, 100, outStream); 
    /* 100 to keep full quality of the image */

    outStream.flush();
    outStream.close();
    success = true;
} catch (FileNotFoundException e) {
    e.printStackTrace();
} catch (IOException e) {
    e.printStackTrace();
}

Finally, just deal with the boolean result if needed. Such as:

if (success) {
    Toast.makeText(getApplicationContext(), "Image saved with success",
            Toast.LENGTH_LONG).show();
} else {
    Toast.makeText(getApplicationContext(),
            "Error during image saving", Toast.LENGTH_LONG).show();
}

Don't forget to add the following permission in your Manifest:

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>

It will be better to create a Dialog to let the user select where they want the photo to be store at. Remember there are a ton of android devices and they might vary.

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