2016-10-14 10 views
0

내 프로그램은 JavaFX의 작업을 사용하여 파일을 다운로드 및 압축 해제하고 updateProgress(workDone, max) 방법 및 progressProperty().bind(observable) 방법을 사용하여 화면에 진행률을 표시합니다.Java - 압축 해제 및 진행률 막대

package com.franckyi.lan.installer; 

import java.io.InputStream; 
import java.io.OutputStream; 
import java.net.URL; 
import java.net.URLConnection; 
import java.nio.file.Files; 
import java.nio.file.Paths; 

import javafx.concurrent.Task; 

public class DownloadTask extends Task<Void> { 

    private String file; 
    private String url; 

    public DownloadTask(String dir, String fileurl) { 
     file = dir; 
     url = fileurl; 
    } 

    @Override 
    protected Void call() throws Exception { 
     URLConnection connection = new URL(url).openConnection(); 
     long fileLength = connection.getContentLengthLong(); 

     try (InputStream is = connection.getInputStream(); 
       OutputStream os = Files.newOutputStream(Paths.get(file))) { 

      long nread = 0L; 
      byte[] buf = new byte[1024]; 
      int n; 
      while ((n = is.read(buf)) > 0) { 
       os.write(buf, 0, n); 
       nread += n; 
       updateProgress(nread, fileLength); 
      } 
     } 
     return null; 
    } 

    @Override 
    protected void succeeded(){ 
     System.out.println("Download succeeded"); 
    } 

} 

을하지만 압축을 풉니 다 잘 작동하지 않습니다 : 그것은 다운로드를 위해 작동하는 파일이 제대로 압축을 풀면하지만 잘못된 ProgressBar의 (마지막에 빈)을 얻는다.

Download succeeded 
1024/91804 
2048/91804 
2815/91804 
362/91804 
326/91804 
290/91804 
386/91804 
257/91804 
250/91804 
588/91804 
1101/91804 
1613/91804 
2128/91804 
2646/91804 
3159/91804 
3672/91804 
4185/91804 
4701/91804 
5214/91804 
5731/91804 
6243/91804 
6755/91804 
7272/91804 
7793/91804 
8326/91804 
8862/91804 
9379/91804 
9897/91804 
10411/91804 
10927/91804 
11442/91804 
11956/91804 
12437/91804 
447/91804 
437/91804 
978/91804 
1525/91804 
2040/91804 
454/91804 
1056/91804 
1568/91804 
2089/91804 
2672/91804 
3198/91804 
3728/91804 
4282/91804 
4826/91804 
5377/91804 
5891/91804 
6413/91804 
6941/91804 
7480/91804 
8027/91804 
8565/91804 
9088/91804 
9609/91804 
9794/91804 
507/91804 
1019/91804 
1531/91804 
2043/91804 
2239/91804 
134/91804 
548/91804 
1292/91804 
2316/91804 
2584/91804 
507/91804 
837/91804 
135/91804 
486/91804 
1001/91804 
1514/91804 
2027/91804 
2545/91804 
3057/91804 
3571/91804 
4086/91804 
4599/91804 
5113/91804 
5627/91804 
6144/91804 
6655/91804 
7166/91804 
7679/91804 
8196/91804 
8710/91804 
9229/91804 
9745/91804 
10259/91804 
10773/91804 
11288/91804 
11802/91804 
12321/91804 
12834/91804 
13348/91804 
13864/91804 
14378/91804 
14893/91804 
15407/91804 
15918/91804 
16431/91804 
16944/91804 
17458/91804 
17971/91804 
18484/91804 
18997/91804 
19508/91804 
20021/91804 
20535/91804 
21047/91804 
21560/91804 
22072/91804 
22584/91804 
23096/91804 
23609/91804 
24122/91804 
24638/91804 
25149/91804 
25664/91804 
26176/91804 
26689/91804 
27203/91804 
27715/91804 
28227/91804 
28739/91804 
29251/91804 
29764/91804 
30277/91804 
30789/91804 
31301/91804 
31813/91804 
32325/91804 
32838/91804 
33306/91804 
33819/91804 
34333/91804 
34846/91804 
35357/91804 
35869/91804 
36381/91804 
36894/91804 
37407/91804 
37922/91804 
38435/91804 
38948/91804 
39460/91804 
39972/91804 
40488/91804 
41002/91804 
41514/91804 
42028/91804 
42540/91804 
43052/91804 
43566/91804 
44079/91804 
44594/91804 
45105/91804 
45619/91804 
46132/91804 
46644/91804 
47156/91804 
47668/91804 
48180/91804 
48692/91804 
49204/91804 
49716/91804 
50228/91804 
50741/91804 
51252/91804 
51765/91804 
52277/91804 
52790/91804 
53305/91804 
53821/91804 
54335/91804 
54852/91804 
55365/91804 
55881/91804 
56396/91804 
56442/91804 
545/91804 
1287/91804 
2311/91804 
2584/91804 
507/91804 
845/91804 
4/91804 
Unzip succeeded 

누군가가 나를 도울 수 :

package com.franckyi.lan.installer; 

import java.io.BufferedInputStream; 
import java.io.BufferedOutputStream; 
import java.io.File; 
import java.io.FileInputStream; 
import java.io.FileOutputStream; 
import java.io.IOException; 
import java.io.OutputStream; 
import java.util.zip.ZipEntry; 
import java.util.zip.ZipInputStream; 

import javafx.concurrent.Task; 

public class UnZipTask extends Task<Void>{ 

    private File zipfile; 
    private File folder; 

    public UnZipTask(File zipfile, File folder){ 
     this.zipfile = zipfile; 
     this.folder = folder; 
    } 

    @Override 
    protected Void call() throws Exception { 
     ZipInputStream zis = new ZipInputStream(
      new BufferedInputStream(new FileInputStream(zipfile.getCanonicalFile()))); 
     ZipEntry ze = null; 
     try { 
      while ((ze = zis.getNextEntry()) != null) { 
       File f = new File(folder.getCanonicalPath(), ze.getName()); 
       if (ze.isDirectory()) { 
        f.mkdirs(); 
        continue; 
       } 
       f.getParentFile().mkdirs(); 
       OutputStream fos = new BufferedOutputStream(new FileOutputStream(f)); 
       try { 
        try { 
         final byte[] buf = new byte[1024]; 
         int bytesRead; 
         long nread = 0L; 
         long length = zipfile.length(); 

         while (-1 != (bytesRead = zis.read(buf))){ 
          fos.write(buf, 0, bytesRead); 
          nread += bytesRead; 
          System.out.println(nread + "/" + length); 
          updateProgress(nread, length); 
         } 
        } finally { 
         fos.close(); 
        } 
       } catch (final IOException ioe) { 
        f.delete(); 
        throw ioe; 
       } 
      } 
     } finally { 
      zis.close(); 
     } 
     return null; 
    } 

    @Override 
    protected void succeeded(){ 
     System.out.println("Unzip succeeded"); 
    } 

} 

이것은 내가 콘솔에서 얻을 무엇인가?

+0

그러면 거의 100 %에서 0 %로 내려갑니다. 이 일을해서는 안됩니까? 당신이 게시 한 콘솔 출력은 숫자가 카운트 다운되고 업되지 않으므로'nread'가 카운트 다운되는 곳에서 updateProgress (nread, length)를 호출합니다. 또한 여러 항목을 처리하고 있기 때문에'nread'가 위아래로 움직이는 것처럼 보입니다. 그래서 진도 표시 줄이 위아래로 가고, 어쩌면 너무 빠르게 볼 것을 기대합니다. – DavidS

+0

@DavidS 네, 맞아요. 너무 빨리, 어떻게 변하는 지 알 수 없습니다. 나는 진도를 늦추는 어떤 것을 시도하고있다. 편집 : 올라간 것처럼 보이지만 여러 번 다시 설정됩니다. – Franckyi

+0

나는 네가 옳다는 것을 알지만, 그것은 올라가고 있지만 여러 번 리셋하고있다. 제임스 _D의 대답은 아마도 그것을 고칠 것입니다. – DavidS

답변

1

압축 zipFile의 길이를 최대로 사용하고 크기가 압축되지 않은 zipEntry 각각에서 postion으로 사용되기 때문입니다. 압축 파일의 크기는 대부분 압축되지 않은 압축 파일의 크기와 다릅니다. zip 패키지의 여러 파일 -이 경우 각 프로그램에 대해 프로그램이 0에서 일부 값 (압축 된 zip 파일 길이가 아닌 실제 zipEntry의 크기)으로 이동합니다.

updateProgress(channel.position(), length); 

이 진행 상황을 업데이트합니다 : 그것은 PROGRES 할 업데이트에 관해서 다음 FileInputStream#getChannel();

: zip 파일의 실제 위치를하려면이 방법을 사용하여 FileInputStream에서 FileChannel에 대한 참조를 얻을 zipFile (압축되지 않은 콘텐츠의 크기가 아님)에서 읽은 실제 위치에 따라 같은

그것은있을 수있는 일 ". 파일이 제대로 압축을 풀면하지만 난 (끝에 빈) 잘못하여 ProgressBar를 얻을"

package com.franckyi.lan.installer; 

import java.io.BufferedInputStream; 
import java.io.BufferedOutputStream; 
import java.io.File; 
import java.io.FileInputStream; 
import java.io.FileOutputStream; 
import java.io.IOException; 
import java.io.OutputStream; 
import java.util.zip.ZipEntry; 
import java.util.zip.ZipInputStream; 

import javafx.concurrent.Task; 

public class UnZipTask extends Task<Void>{ 

    private File zipfile; 
    private File folder; 

    public UnZipTask(File zipfile, File folder){ 
     this.zipfile = zipfile; 
     this.folder = folder; 
    } 

    @Override 
    protected Void call() throws Exception { 
     FileInputStream is = new FileInputStream(zipfile.getCanonicalFile()); 
     FileChannel channel = is.getChannel(); 
     ZipInputStream zis = new ZipInputStream(new BufferedInputStream(is)); 
     ZipEntry ze = null; 
     try { 
      while ((ze = zis.getNextEntry()) != null) { 
       File f = new File(folder.getCanonicalPath(), ze.getName()); 
       if (ze.isDirectory()) { 
        f.mkdirs(); 
        continue; 
       } 
       f.getParentFile().mkdirs(); 
       OutputStream fos = new BufferedOutputStream(new FileOutputStream(f)); 
       try { 
        try { 
         final byte[] buf = new byte[1024]; 
         int bytesRead; 
         long nread = 0L; 
         long length = zipfile.length(); 

         while (-1 != (bytesRead = zis.read(buf))){ 
          fos.write(buf, 0, bytesRead); 
          nread += bytesRead; 
          System.out.println(nread + "/" + length); 
          updateProgress(channel.position(), length); 
         } 
        } finally { 
         fos.close(); 
        } 
       } catch (final IOException ioe) { 
        f.delete(); 
        throw ioe; 
       } 
      } 
     } finally { 
      zis.close(); 
     } 
     return null; 
    } 

    @Override 
    protected void succeeded(){ 
     System.out.println("Unzip succeeded"); 
    } 

} 
+0

그게 작동합니다, 고마워요! – Franckyi

+0

당신은 환영합니다 :) –