» »

[Android] Service

[Android] Service

icurk ::

V moji aplikaciji uporabljam service za download podatkov(*.zip datotek) na telefon. Za prenos posamezne datoteke, uporabnik klikne na to datoteko, ki se nato začne prenašati v service in na koncu se zapišejo podatki o datoteki tudi v bazo. Te podatke dodam kot bundle pri kreiranju intenta.

Vse dela lepo če prenašam eno pa po eno datoteko. Če pa začnem prenašat prvo datoteko in kliknem na prenos druge datoteke, preden se prva konča, se sicer obe preneseta, vendar se v bazo shranijo podatki druge datoteke in to 2x.
Torej ko drugič pokličem startService() se podatki v bundlu prepišejo v prvem startService().

Kodo nevem katero lahko priložim, da vam bo v pomoč, zato kar povejte kaj naj prilepim... V spodnji kodi se v DownloadFileAsync().execute() datoteka prenese in posodobi bazo.
@Override
	public int onStartCommand(Intent intent, int flags, int startId) {
		book = intent.getExtras().getString("book");
		url = intent.getExtras().getString("url");
		page = intent.getExtras().getString("pages");
		id = intent.getExtras().getInt("id");

		new DownloadFileAsync().execute();
		
		return START_NOT_STICKY;
	}

usoban ::

DownloadFileAsync pokazi.

icurk ::

DownloadFileAsync
public class DownloadFileAsync extends AsyncTask<Void, Integer, String> {
		@Override
		protected void onPreExecute() {
			super.onPreExecute();
			Log.i("service", "preExecute");
		}

		@Override
		protected String doInBackground(Void... arg0) {
			int count;

			try {
				URL urlKnjige = new URL(url);
				URLConnection con = urlKnjige.openConnection();
				con.connect();

				int lenghtOfFile = con.getContentLength();

				InputStream input = new BufferedInputStream(
						urlKnjige.openStream());
				Log.d("book", book + ".zip");

				file = Environment.getExternalStorageDirectory();
				File dir = new File(file.getAbsolutePath() + "/ebooks");
				dir.mkdirs();

				File fajl = new File(dir, book + ".zip");
				FileOutputStream output = new FileOutputStream(fajl);

				byte data[] = new byte[1024];

				long total = 0;

				while ((count = input.read(data)) != -1) {
					total += count;
					publishProgress((int) ((total * 100) / lenghtOfFile));
					output.write(data, 0, count);
				}
				output.flush();
				output.close();
				input.close();

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

		@Override
		protected void onPostExecute(String unused) {
			// Zaženemo odzipanje
			new unzip().execute();
		}
	}


unzip
public class unzip extends AsyncTask<Void, Void, Void> {
		@Override
		protected void onPreExecute() {
			super.onPreExecute();
		}

		@Override
		protected Void doInBackground(Void... params) {
			/* == Odzipanje == */
			// ustvarimo direktorij, kamor bomo odzipali
			File dirZip = new File(file.getAbsolutePath() + "/ebooks/" + book);
			dirZip.mkdirs();

			// Unzip
			Unzip _file = new Unzip(dirZip.toString() + ".zip",
					file.getAbsolutePath() + "/ebooks/" + book + "/");
			_file.unzip();

			/* == Izbrišemo zip file iz kartice == */
			File zip = new File(dirZip.toString() + ".zip");
			new DeleteFiles().DeleteRecursive(zip);

			/* == Posodobitev SQLite baze == */
			ListOfBooks lb_db = new ListOfBooks(getApplicationContext());
			lb_db.open();
			lb_db.createEntry(book, page);
			lb_db.close();

			return null;
		}

		@Override
		protected void onPostExecute(Void result) {
			// TODO Auto-generated method stub
			super.onPostExecute(result);
		}

	}

usoban ::

Mi sicer ni cisto jasno kako je to scopano, da ti v posamezni instanci DownloadFileAsync vidis book, url, page in id, in verjetno je to problem ... mislim da bi moral podati te spremenljivke kot argumente metodi execute ... popravit moras definicijo AsyncTaskov, da prejmejo String kot parametre v metodi doInBackground:

public class DownloadFileAsync extends AsyncTask<String, Integer, String> {
  private String book;
  private String url;
  private String page;
  private int id;

  protected Void doInBackground(String... params) {
   book = params[0];
   url = params[1];
   page = params[2];
   id = Integer.valueOf(params[3]);

   // .....
  }

  @Override
  protected void onPostExecute(String unused) {
    // Zaženemo odzipanje
    new unzip().execute(book, page);
  }
}

public class unzip extends AsyncTask<String, Void, Void> {
 
  @Override
  protected Void doInBackground(String... params) {
    String book = params[0];
    String page = params[1];

    // ...
  }
}
new DownloadFileAsync(book, url, page, String.valueOf(id)); // iz servica pa poklici tako

Zgodovina sprememb…

  • spremenil: usoban ()

icurk ::

Ja to je blo scopano tako, da so ble te spremenljivke polja za ta service. Sem pa čist pozabu, da bi lahko posredoval te spremenljivke kot argumente za asynctask.
No glavno, da zdej deluje tako kot mora :)


Vredno ogleda ...

TemaSporočilaOglediZadnje sporočilo
TemaSporočilaOglediZadnje sporočilo
»

[Android] setText iz AsyncTask

Oddelek: Programiranje
7844 (761) golobich
»

[android] java.lang.RuntimeException

Oddelek: Programiranje
141078 (770) piki12
»

Android threadi in asynctaski

Oddelek: Programiranje
231576 (1222) Kocka
»

[android] vstavljanje slike

Oddelek: Programiranje
71240 (1137) messi
»

[Android] končanje threada

Oddelek: Programiranje
6926 (776) Mavrik

Več podobnih tem