Autore Topic: Copiare un file in Background?  (Letto 470 volte)

Offline x69asterix2

  • Utente junior
  • **
  • Post: 127
  • Respect: +1
    • Mostra profilo
Copiare un file in Background?
« il: 15 Settembre 2014, 10:57:04 CEST »
0
Ciao a tutti,
ho un problema da risolvere, cerco di spiegare al meglio:
Allora da una mia app, carico un file su di un server esterno, il file inviato a sua volta lo copio in una mia cartella, solo che al momento del salvataggio del file sul dispositivo questo blocca l'app per un certo periodo e la cosa non và bene, come lo risolvo creando un thread che si occupa del salvataggio?

Offline tonno16

  • Utente storico
  • *****
  • Post: 1228
  • Respect: +59
    • Mostra profilo
  • Dispositivo Android:
    moto g
  • Play Store ID:
    Diego Tonini
  • Sistema operativo:
    OpenSuse
Re:Copiare un file in Background?
« Risposta #1 il: 15 Settembre 2014, 12:31:10 CEST »
0
USA un asynktask

Offline x69asterix2

  • Utente junior
  • **
  • Post: 127
  • Respect: +1
    • Mostra profilo
Re:Copiare un file in Background?
« Risposta #2 il: 15 Settembre 2014, 13:50:31 CEST »
0
Ciao tonno16,
hai un piccolo esempio da mostrarmi?

Offline tonno16

  • Utente storico
  • *****
  • Post: 1228
  • Respect: +59
    • Mostra profilo
  • Dispositivo Android:
    moto g
  • Play Store ID:
    Diego Tonini
  • Sistema operativo:
    OpenSuse
Re:Copiare un file in Background?
« Risposta #3 il: 15 Settembre 2014, 13:51:41 CEST »
+1
Non ho il PC. Cerca su google tutorial asynktask

Offline Illogica

  • Nuovo arrivato
  • *
  • Post: 32
  • Respect: +4
    • Google+
    • Mostra profilo
    • Illogica Software
  • Dispositivo Android:
    Caterpillar B15Q / Asus Padfone Infinity / Htc Pyramid / Samsung Galaxy *
  • Play Store ID:
    Illogica Software
  • Sistema operativo:
    Ubuntu 14.04
Re:Copiare un file in Background?
« Risposta #4 il: 15 Settembre 2014, 19:52:21 CEST »
0
Conviene usare AsyncTask o creare un Service.
Probabilmente un AsyncTask è una soluzione più elegante:

Codice: [Seleziona]
public class AsyncTaskActivity extends Activity implements OnClickListener {

    Button btn;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);  //creare in /res il file di layout main.xml
        btn = (Button) findViewById(R.id.button1); //dichiarare nel layout il bottone con android:id="button1"
        btn.setOnClickListener(this); //visto che implementiamo OnClickListener usiamo l'activity per
                                                     //gestire i click
    }

    public void onClick(View view) {
        // gestione degli eventi "click"
        switch (view.getId()) {
        case R.id.button1:
            new LongOperation().execute("<percorso del file da scaricare>");
            break;
        }
    }

    //Asynctask dichiarato come classe interna
    private class LongOperation extends AsyncTask<String, Void, String> {

        @Override
        protected String doInBackground(String... params) {
            scaricaFileDalServer(params [0]) //funzione che scarica il file
            return "Executed";
        }

        @Override
        protected void onPostExecute(String result) {
            //esegui quello che vuoi qui dentro quando lo scaricamento è terminato
        }

        @Override
        protected void onPreExecute() {}

        @Override
        protected void onProgressUpdate(Void... values) {}
    }
}

Offline x69asterix2

  • Utente junior
  • **
  • Post: 127
  • Respect: +1
    • Mostra profilo
Re:Copiare un file in Background?
« Risposta #5 il: 16 Settembre 2014, 07:39:41 CEST »
0
Ciao,
prima di tutto grazie, una piccola precisazione il file non deve essere scaricato dal server, ma bensì copiato da una cartella ad un'altra.
Detto questo ancora non ho avuto modo di testare il tuo codice lo farò più tardi.

In
Codice: [Seleziona]
new LongOperation().execute("<percorso del file da scaricare>");passo fullPath + filename?

Codice: [Seleziona]
   @Override
        protected String doInBackground(String... params) {
            saveImageToExternalStorage(params [0]); //funzione che scarica il file

            return "Executed";
        }

Codice: [Seleziona]
    public boolean saveImageToExternalStorage(String img_name) {
        Bitmap image = BitmapFactory.decodeFile(imagePath);

        String fullPath = Environment.getExternalStorageDirectory().getAbsolutePath() + APP_PATH_SD_CARD + "/_Foto";
        try {
            File dir = new File(fullPath);
            if (!dir.exists()) {
                dir.mkdirs();
            }

            if (isFileExsist(img_name).equals(true)) {

            } else {
                OutputStream fOut = null;
                File file = new File(fullPath, img_name);
                file.createNewFile();
                fOut = new FileOutputStream(file);
                image.compress(Bitmap.CompressFormat.PNG, 100, fOut);
                fOut.flush();
                fOut.close();
            }

            return true;
        } catch (Exception e) {
            Log.e("saveToExternalStorage()", e.getMessage());
            return false;
        }
    }
« Ultima modifica: 16 Settembre 2014, 08:06:04 CEST da x69asterix2 »

Offline Illogica

  • Nuovo arrivato
  • *
  • Post: 32
  • Respect: +4
    • Google+
    • Mostra profilo
    • Illogica Software
  • Dispositivo Android:
    Caterpillar B15Q / Asus Padfone Infinity / Htc Pyramid / Samsung Galaxy *
  • Play Store ID:
    Illogica Software
  • Sistema operativo:
    Ubuntu 14.04
Re:Copiare un file in Background?
« Risposta #6 il: 16 Settembre 2014, 08:43:04 CEST »
0
Forse il codice che hai postato non è completo... o sono io che non capisco cosa fa...
A che usi quel "Bitmap image" che dichiari all'inizio?
E questo non è molto leggibile, cosa succede se la condizione dell'if è vera?:
Codice: [Seleziona]
if (isFileExsist(img_name).equals(true)) {
            } else {

Comunque si, la funzione doInBackground accetta un array di Stringhe, quindi devi passare il percorso completo del file come stringa.

Ho visto che usi percorsi assoluti per gestire la Scheda SD. Sai vero che da Android 4.4 (KitKat) in poi questo meccanismo funziona solo in lettura? Le app di terze parti (cioè tutte quelle che facciamo noi) non possono più scrivere direttamente su memorie esterne.

Offline x69asterix2

  • Utente junior
  • **
  • Post: 127
  • Respect: +1
    • Mostra profilo
Re:Copiare un file in Background?
« Risposta #7 il: 16 Settembre 2014, 08:52:02 CEST »
0
il codice è questo
Codice: [Seleziona]
            if (!isFileExsist(img_name).equals(true)) {
                OutputStream fOut = null;
                File file = new File(fullPath, img_name);
                file.createNewFile();
                fOut = new FileOutputStream(file);
           
                fOut.flush();
                fOut.close();
            }

chiedo venia... era un'altra cosa.
Si l'ho notato.........

Offline Illogica

  • Nuovo arrivato
  • *
  • Post: 32
  • Respect: +4
    • Google+
    • Mostra profilo
    • Illogica Software
  • Dispositivo Android:
    Caterpillar B15Q / Asus Padfone Infinity / Htc Pyramid / Samsung Galaxy *
  • Play Store ID:
    Illogica Software
  • Sistema operativo:
    Ubuntu 14.04
Re:Copiare un file in Background?
« Risposta #8 il: 16 Settembre 2014, 11:20:10 CEST »
0
Se posso darti un consiglio, quell'if è proprio brutto  ;-)
Immagino che la funzione  isFileExsist l'abbia scritta tu, quindi ti consiglierei di fare un refactor (cioè rinominare) della funzione per correggere l'ortografia, per esempio chiamala "fileExists";
sembra una pignoleria ma 1)ti abitui all'inglese corretto e 2)metti che un giorno qualcun'altro legge il tuo codice...

In ogni caso, visto che immagino la funzione ritorni un valore booleano l'if può essere semplificato in
Codice: [Seleziona]
if (!isFileExsist) {
                OutputStream fOut = null;
                File file = new File(fullPath, img_name);
                file.createNewFile();
                fOut = new FileOutputStream(file);
           
                fOut.flush();
                fOut.close();
            }


Offline x69asterix2

  • Utente junior
  • **
  • Post: 127
  • Respect: +1
    • Mostra profilo
Re:Copiare un file in Background?
« Risposta #9 il: 16 Settembre 2014, 11:48:27 CEST »
0
ok..
questo è isFileExsist:

Codice: [Seleziona]
   public Boolean isFileExsist(String fileName) {
        String fullPath = Environment.getExternalStorageDirectory().getAbsolutePath() + APP_PATH_SD_CARD + "/_Foto/";
        String sFile = fullPath + "/" + filepath;
        java.io.File file = new java.io.File(sFile);
        return file.exists();
    }
Codice: [Seleziona]
public boolean saveImageToExternalStorage(String img_name) {

        String fullPath = Environment.getExternalStorageDirectory().getAbsolutePath() + APP_PATH_SD_CARD + "/_Foto";
        try {
            File dir = new File(fullPath);
            if (!dir.exists()) {
                dir.mkdirs();
            }
 
                OutputStream fOut = null;
                File file = new File(fullPath, img_name);
                file.createNewFile();
                fOut = new FileOutputStream(file);
                fOut.flush();
                fOut.close();
 
            return true;
        } catch (Exception e) {
            Log.e("saveToExternalStorage()", e.getMessage());
            return false;
        }
    }
e questo è il codice dentro un bottone:
Codice: [Seleziona]
  if (!isFileExsist(fileName)) {
                    new LongOperation().execute(fileName);
                }else{
                    progressDialog = ProgressDialog.show(MyActivity.this, "Invio in corso",
                            "Trasferimento Immagine...", true);
                    _sendF();
                }
Codice: [Seleziona]
private class LongOperation extends AsyncTask<String, Void, String> {
        @Override
        protected String doInBackground(String... params) {
            saveImageToExternalStorage(params[0]); //funzione che scarica il file
            return "Executed";
        }

        @Override
        protected void onPostExecute(String result) {
            //esegui quello che vuoi qui dentro quando lo scaricamento è terminato
            _sendF();
        }

        @Override
        protected void onPreExecute() {
            progressDialog = ProgressDialog.show(MyActivity.this, "Invio in corso",
                    "Trasferimento Immagine...", true);
        }

        @Override
        protected void onProgressUpdate(Void... values) {

        }
    }
« Ultima modifica: 16 Settembre 2014, 11:56:02 CEST da x69asterix2 »

Offline Illogica

  • Nuovo arrivato
  • *
  • Post: 32
  • Respect: +4
    • Google+
    • Mostra profilo
    • Illogica Software
  • Dispositivo Android:
    Caterpillar B15Q / Asus Padfone Infinity / Htc Pyramid / Samsung Galaxy *
  • Play Store ID:
    Illogica Software
  • Sistema operativo:
    Ubuntu 14.04
Re:Copiare un file in Background?
« Risposta #10 il: 16 Settembre 2014, 15:11:43 CEST »
0
Ho provato a mettere insieme i pezzi che hai postato ma non tornano tante cose. A te compila quello che hai scritto? Potresti postare tutta l'activity?