0

my progress bar is update only to 100%. i check with printing and it's seems everything run as it should be but the UI does not update according to the parameters in the printing check!

here is my Panel class. the main class create frame the adding the MyPanel i create:

public class MyPanel extends JPanel {

    File[] DFLIST;
    File DF[];
    File INP;
    File LOG;
    JButton chooseDF = new JButton("Choose defect file");
    JButton chooseLog = new JButton("Choose log file");
    JButton chooseInp = new JButton("Choose inp file");
    JButton analayze = new JButton("Analayze");
    DefectFileReader[] dfReader;
    Document[] docArray;
    boolean DFloaded = false;
    boolean LOGloaded = false;
    boolean INPloaded = false;
    Checkbox recipeName;
    Checkbox inspectionDuration;
    Checkbox area;
    Checkbox numberOfDefects;
    Checkbox numberOfDefectsPerDetector;
    Checkbox sensetivityName;
    Checkbox SlicesDetected;
    private static int rowIndex = 2;
    private static int cellIndex = 4;
    FileOutputStream fos;
    XSSFWorkbook workbook = new XSSFWorkbook();
    XSSFSheet sheet = workbook.createSheet("analyze_result");
    Row row = sheet.createRow(rowIndex);
    Cell cell = row.createCell(cellIndex);
    XSSFCellStyle csForFirstWrite = workbook.createCellStyle();
    XSSFCellStyle csForSecondWrite = workbook.createCellStyle();
    XSSFFont fontForBold = workbook.createFont();
    XSSFFont fontNotForBold = workbook.createFont();
    String totalDuration = "00:00:00";
    private int currentFolder = 0;
    //TwoRoot t;
    JProgressBar pBar = new JProgressBar();
    Frame frame = new Frame("Progress Bar");
    MyprogressBar taskBar;



    /* creating the main panel of the frame - divided to 3 parts. in the north pictures , in the west checkbox , in the east the file chooser */

    public MyPanel(){ 
        this.setLayout(new BorderLayout());
        this.add(pictureInNorth() , BorderLayout.NORTH);
        this.add(checkBoxPanel() , BorderLayout.WEST);
        this.add(chooseFilesPanel() , BorderLayout.EAST);
        //pBar.setForeground(Color.black);
        //pBar.setStringPainted(true);
        //this.add(pBar , BorderLayout.SOUTH);

    }


    /* creating the north panel with the picture */
private JPanel pictureInNorth(){
    JPanel toReturn = new JPanel();
    toReturn.setBackground(Color.black);
    JButton analayzerPic = new JButton(new ImageIcon(new ImageIcon("C:/Users/uvalerx073037/workspace/Analayzer_GUI_Ver2/src/Images/vXqyQkOv.jpeg")
                            .getImage().getScaledInstance(600, 30,
                                    java.awt.Image.SCALE_SMOOTH)));
    analayzerPic.setBackground(Color.black);
    toReturn.add(analayzerPic);
    return toReturn;

}

    /* creating the checkBox in the west */

private JPanel checkBoxPanel(){
    recipeName = new Checkbox("Recipe Name" , false);
    inspectionDuration = new Checkbox("Inspection Duration" , false);
    area = new Checkbox("Area" , false);
    numberOfDefects = new Checkbox("Number Of Defects" , false);
    numberOfDefectsPerDetector = new Checkbox("Number Of Defects Per Detector", false);
    sensetivityName = new Checkbox("Sensetivity Name", false);
    SlicesDetected = new Checkbox("Slices were detected" , false);
    JPanel toReturn = new JPanel();
    toReturn.setLayout(new BoxLayout(toReturn, BoxLayout.Y_AXIS));
    toReturn.add(recipeName);
    toReturn.add(inspectionDuration);
    toReturn.add(numberOfDefects);
    toReturn.add(numberOfDefectsPerDetector);
    toReturn.add(sensetivityName);
    toReturn.add(SlicesDetected);
    toReturn.add(area);

    return toReturn;

}

    /*creating the file chooser in the east */

private Box chooseFilesPanel(){
    MyActionListener lis = new MyActionListener();
    chooseDF.addActionListener(lis);
    chooseInp.addActionListener(lis);
    chooseLog.addActionListener(lis);
    analayze.addActionListener(lis);
    analayze.setForeground(Color.BLUE);
    Box toReturn = Box.createVerticalBox();
    toReturn.add(Box.createGlue());
    toReturn.add(chooseDF);
    toReturn.add(Box.createGlue());
    toReturn.add(chooseLog);
    toReturn.add(Box.createGlue());
    toReturn.add(chooseInp);
    toReturn.add(Box.createGlue());
    toReturn.add(analayze).setSize(50,50);

    return toReturn;

}

/* function to check after the user clicked on the analyze button if all the conditions are OK */

public Boolean isValidToStart(){
    if(DFloaded == false && LOGloaded == false && INPloaded == false){
        JOptionPane.showMessageDialog(null, "NO FILE WAS LOADED!!!", "User Error" , JOptionPane.ERROR_MESSAGE);
        return false;
    }
    if(recipeName.getState() == false && inspectionDuration.getState() == false && area.getState() == false && 
            numberOfDefects.getState() == false && numberOfDefectsPerDetector.getState() == false && sensetivityName.getState() == false){
        JOptionPane.showMessageDialog(null , "NO CHECK BOX WAS MARKED!!!" + "\n" + "WHAT DATA WOULD YOU LIKE TO COLLECT?" , "User Error" , JOptionPane.ERROR_MESSAGE );
        return false;
    }
    if(area.getState() == true && (LOGloaded == false || DFloaded == false || INPloaded == false)){
        JOptionPane.showMessageDialog(null , "IF YOU WANT TO COLLECT AERA YOU NEED TO CHOOSE INP + LOG + DEF" , "User Error" , JOptionPane.ERROR_MESSAGE );
        return false;
    }
    if(SlicesDetected.getState() == true && LOGloaded == false){
        JOptionPane.showMessageDialog(null , "You need to load the LOG in order to get the amount of slices were detected!" , "User Error" , JOptionPane.ERROR_MESSAGE );
        return false;
    }
    else
        return true;

}

/* build the row of the titles , only what the user marked in the check box */ 

private void firstWriteToExcel(DefectFileReader curDF , XSSFSheet sheet , XSSFWorkbook workbook , FileOutputStream fos) throws Exception{

    fontForBold.setBold(true);
    csForFirstWrite.setFont(fontForBold);
    csForFirstWrite.setFillForegroundColor(new XSSFColor(java.awt.Color.lightGray));
    csForFirstWrite.setFillPattern(CellStyle.SOLID_FOREGROUND);
    csForFirstWrite.setBorderBottom(XSSFCellStyle.BORDER_MEDIUM);
    csForFirstWrite.setBorderTop(XSSFCellStyle.BORDER_MEDIUM);
    csForFirstWrite.setBorderRight(XSSFCellStyle.BORDER_MEDIUM);
    csForFirstWrite.setBorderLeft(XSSFCellStyle.BORDER_MEDIUM);


    if(recipeName.getState() == true){
        row = sheet.createRow(rowIndex - 1);
        row.createCell(cellIndex).setCellValue("Recipe Name: " + curDF.getRecipeName());
        sheet.autoSizeColumn(cellIndex);
    }
    row = sheet.createRow(rowIndex++);
    row.createCell(cellIndex).setCellValue("inspection index");
    sheet.autoSizeColumn(cellIndex);
    cellIndex++;
    if(numberOfDefects.getState() == true){
        row.createCell(cellIndex).setCellValue("Total Defects");
        sheet.autoSizeColumn(cellIndex);
        cellIndex++;
    }
    if(numberOfDefectsPerDetector.getState() == true){
        ArrayList<String> toOtherFunc = new ArrayList<String>();
        toOtherFunc = curDF.getDetectorNames();
        for(int i=0; i < toOtherFunc.size() ; i++){
            row.createCell(cellIndex).setCellValue(toOtherFunc.get(i)); 
            sheet.autoSizeColumn(cellIndex);
            cellIndex++;
        }
    }
    if(sensetivityName.getState() == true){
        row.createCell(cellIndex).setCellValue("sensetivity Name");
        sheet.autoSizeColumn(cellIndex);
        cellIndex++;
    }
    if(LOGloaded == true){
        row.createCell(cellIndex).setCellValue("Slices were detected");
        sheet.autoSizeColumn(cellIndex);
        cellIndex++;

    }
    if(inspectionDuration.getState()==true){
        row.createCell(cellIndex).setCellValue("Inspection Duration");
        sheet.autoSizeColumn(cellIndex);
        cellIndex++;
    }


    for (Row row : sheet){
        for (Cell cell_local : row){
            cell_local.setCellStyle(csForFirstWrite);
        }


    }

    System.out.println("row index is: " + rowIndex + "cell index is: " + cellIndex);

}


/* fill the excel in the data were collected */

private void writeToExcel(DefectFileReader curDF , XSSFSheet sheet , XSSFWorkbook workbook , FileOutputStream fos) throws Exception{

        fontNotForBold.setBold(false);
        csForSecondWrite.setFont(fontNotForBold);
        csForSecondWrite.setFillForegroundColor(new XSSFColor(java.awt.Color.white));
        csForSecondWrite.setFillPattern(CellStyle.SOLID_FOREGROUND);
        csForSecondWrite.setBorderBottom(XSSFCellStyle.BORDER_THIN);
        csForSecondWrite.setBorderTop(XSSFCellStyle.BORDER_THIN);
        csForSecondWrite.setBorderRight(XSSFCellStyle.BORDER_THIN);
        csForSecondWrite.setBorderLeft(XSSFCellStyle.BORDER_THIN);
    cellIndex = 4;
    row = sheet.createRow(rowIndex++);
    row.createCell(cellIndex++).setCellValue("inspection_" + (rowIndex - 3));
    if(numberOfDefects.getState() == true)
        row.createCell(cellIndex++).setCellValue(curDF.getTotalDefects());
    if(numberOfDefectsPerDetector.getState() == true){
        ArrayList<String> toOtherFunc = new ArrayList<String>();
        int[] toPrintNumber = new int[toOtherFunc.size()];
        toOtherFunc = curDF.getDetectorNames();
        System.out.println(toOtherFunc);
        toPrintNumber = curDF.getDefectPerDetector(toOtherFunc);
        for(int i=0; i < toOtherFunc.size() ; i++)
            row.createCell(cellIndex++).setCellValue(toPrintNumber[i]); 
    }
    if(sensetivityName.getState() == true)
        row.createCell(cellIndex++).setCellValue(curDF.getSensetivityName());
    if(LOGloaded == true){
        LogFileReader logReader = new LogFileReader(LOG , curDF.getInspectionEndTime());
        ArrayList<String> toLog = curDF.getRunsIndex();
        String toPrint = "";
        for(int i=0 ; i < toLog.size() ; i = i+2)
            toPrint += toLog.get(i) + ": " + logReader.diagnozeLog(toLog.get(i+1)) + " ";
        if(toPrint.equals(""))
            row.createCell(cellIndex).setCellValue("The data of this run is not in this log!");
        else
            row.createCell(cellIndex).setCellValue(toPrint);
        sheet.autoSizeColumn(cellIndex);
        cellIndex++;

    }
    if(inspectionDuration.getState()==true)
        row.createCell(cellIndex++).setCellValue(curDF.inspectionDuration());


    for (Row row : sheet){
        if( row.getRowNum() > 2){
        for (Cell cell_local : row){
            cell_local.setCellStyle(csForSecondWrite);
        }
        }


    }


    System.out.println("row index is: " + rowIndex + " cell index is: " + cellIndex);


}

/* adding the inspection time of the current run to the total time */

public String sumTimes(String time1) {
    PeriodFormatter formatter = new PeriodFormatterBuilder()
            .minimumPrintedDigits(2)
            .printZeroAlways()
            .appendHours()
            .appendLiteral(":")
            .appendMinutes()
            .appendLiteral(":")
            .appendSeconds()
            .toFormatter();

    org.joda.time.Period period1 = formatter.parsePeriod(time1);
    org.joda.time.Period period2 = formatter.parsePeriod(totalDuration);
    return formatter.print(period2.plus(period1).normalizedStandard());
}

public void initializeFrame(){
    frame.setSize(300, 100);
    pBar.setForeground(Color.black);
    pBar.setStringPainted(true);
    frame.add(pBar);
    frame.setLocationRelativeTo(null);
    frame.setVisible(true);
}

class MyprogressBar extends SwingWorker<Void, Integer> {

    JProgressBar pBar;
    int max;
    int currentFolder;

    public MyprogressBar(JProgressBar curBar , int max , int currentFolder){
        this.pBar = curBar;
        this.max = max;
        this.currentFolder = currentFolder;
    }
    public void done(){

    }


    @Override
    protected Void doInBackground() throws Exception {
            System.out.println("i'm in background");
            double i = currentFolder;
            double t = DFLIST.length;
            double toSetInDouble = (i/t);
            int toSet = (int) (toSetInDouble * 100);
            pBar.setValue(toSet); 
            System.out.println(toSet);
            repaint();
            Thread.sleep(10); 
            publish(toSet);

        return null;
    }

}

    /* adding listener to all of the buttons and check boxes */

public class MyActionListener implements ActionListener  
{
    public void actionPerformed(ActionEvent click) 
    {
        if(click.getSource() == chooseDF){
            File directory;
            FilenameFilter f = new FilenameFilter() {
                public boolean accept(File dir, String name) {
                    return name.length()<=2;
                }
            };
            FilenameFilter def = new FilenameFilter() {
                public boolean accept(File dir, String name) {
                    return name.endsWith(".def");
                }
            };
            JFileChooser chooser = new JFileChooser(System.getProperties().getProperty("user.dir"));
            chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
            if(chooser.showOpenDialog(null) == JFileChooser.APPROVE_OPTION){
                DFloaded = true;
                directory = chooser.getSelectedFile();
                File[] fileList = directory.listFiles(f);
                Arrays.sort(fileList , new NaturalOrderComparator());
                DFLIST = new File[fileList.length];
                for(int i = 0 ; i<fileList.length ; i++){
                    File[] tmp = fileList[i].listFiles(def);
                    for(int j=0 ; j<tmp.length ; j++)
                        DFLIST[i] = tmp[j];
                }
            }

        }

        if(click.getSource() == chooseInp){
            JFileChooser fc2 = new JFileChooser();
            if (fc2.showOpenDialog(null) == JFileChooser.APPROVE_OPTION){
                INPloaded = true;
                INP = fc2.getSelectedFile();
            }
        }

        if(click.getSource() == chooseLog){
            JFileChooser fc3 = new JFileChooser();
            if(fc3.showOpenDialog(null) == JFileChooser.APPROVE_OPTION){
                LOGloaded = true;
                LOG = fc3.getSelectedFile();


            }
        }

        if(click.getSource() == analayze){
            Boolean valid = isValidToStart();
            if(valid == true){
                try{
                fos = new FileOutputStream("c:/temp/analayze.xlsx");
            if(DFloaded == true){
                try {
                    initializeFrame();
                    DF = new File[DFLIST.length];
                    dfReader = new DefectFileReader[DFLIST.length];
                    docArray = new Document[DFLIST.length];
                    for( ; currentFolder < DFLIST.length ; currentFolder++){
                        new MyprogressBar(pBar, 100, currentFolder + 1).execute();
                        frame.repaint();
                        System.out.println("i'm sending the file down here to parse from file to document");
                        System.out.println(DFLIST[currentFolder].getAbsoluteFile());
                        DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
                        DocumentBuilder db = dbf.newDocumentBuilder();
                        docArray[currentFolder] = (Document) db.parse(DFLIST[currentFolder]);
                        docArray[currentFolder].getDocumentElement().normalize();
                        dfReader[currentFolder] = new DefectFileReader(DFLIST[currentFolder] , docArray[currentFolder]);
                        dfReader[currentFolder].getRunsIndex();
                        totalDuration = sumTimes(dfReader[currentFolder].inspectionDuration());
                        if(currentFolder==0){
                            firstWriteToExcel(dfReader[0], sheet, workbook, fos);
                            writeToExcel(dfReader[0], sheet, workbook, fos);
                        }
                        if(currentFolder!=0)
                            writeToExcel(dfReader[currentFolder] , sheet ,  workbook , fos );
                        repaint();
                    if(INPloaded == true){

                    }
                    DFLIST[currentFolder] = null;
                    dfReader[currentFolder].clearDfReader();
                    docArray[currentFolder] = null;
                    System.gc();
                   }
                }
                   catch(Exception e ) {
                      System.out.println(e);
                      System.exit(0);
                   }
            }

            row = sheet.createRow(rowIndex);
            totalDuration = sumTimes("00:00:00");
            if(inspectionDuration.getState() == true){
            row.createCell(cellIndex - 1).setCellValue(totalDuration);
            row.getCell(cellIndex - 1).setCellStyle(csForFirstWrite);
            }
            ((Workbook) workbook).write(fos);
            workbook.close();
            JOptionPane.showMessageDialog(null, "Your data has been analyze!\n you can find the result in c:\\temp");
            System.exit(0);

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

    }
}


}
}



}
orangerblue
  • 65
  • 10
Udi
  • 598
  • 8
  • 19
  • 1
    You're violating the single thread rules of Swing, see [Concurrency in Swing](http://docs.oracle.com/javase/tutorial/uiswing/concurrency/) for more details and [Worker Threads and SwingWorker](http://docs.oracle.com/javase/tutorial/uiswing/concurrency/worker.html) for a possible solution – MadProgrammer Jul 21 '15 at 01:04
  • The `for( ; currentFolder < DFLIST.length ; currentFolder++){` is likely blocking the EDT – MadProgrammer Jul 21 '15 at 01:06
  • Thanks! i tried working with swingWorker and find it very confusing. is this the only way to do it? – Udi Jul 21 '15 at 01:22
  • 1
    It's not the only way to do, it's a preferred, simpler and cleaner way to do...as an [example](http://stackoverflow.com/questions/23125642/swingworker-in-another-swingworkers-done-method/23126410#23126410) – MadProgrammer Jul 21 '15 at 01:23
  • the problem is that i find it diffuclt to use is this framework (swingworker) to update the real values from my for loop. any advice? – Udi Jul 21 '15 at 01:30
  • Use more then one? Create a custom `Worker` which does the jobs that you need? Change what you are doing to better fit within the constraints of the API you're using? Provide a a [runnable example](https://stackoverflow.com/help/mcve) which demonstrates your problem. This is not a code dump, but an example of what you are doing which highlights the problem you are having. This will result in less confusion and better responses – MadProgrammer Jul 21 '15 at 01:32
  • thanks man! i will go over it and try to solve it again. if i couldn't i will publish more clearly question – Udi Jul 21 '15 at 01:40

1 Answers1

1

@Udi it would have been really great if you could have pasted a structured code. However, with whatever code you pasted, here is an indicative solution using swingworker. You just need to call your whole actionPerformed() code from doInBackground() of swingworker. Hope it helps.

Moreover, I find the java docs of swingworker a very useful to understand how it works. Examples are very simple yet well explained. https://docs.oracle.com/javase/8/docs/api/javax/swing/SwingWorker.html

    // use this code inside actionPerformed()
    new SwingWorker(){

        @Override
        protected Object doInBackground() throws Exception {

            // all your code goes here

            for( ; currentFolder < DFLIST.length ; currentFolder++){
                                 double f = currentFolder + 1;
                                double t = DFLIST.length;
                                double currentPercentInDouble = (f / t);
                                int currentPercent = (int) (currentPercentInDouble * 100);

                                // send the current progress to progress bar. This needs to be updated to progress bar in process() method
                                publish(currentPercent)

            }

            // rest of the code
        }


        @Override 
        protected void process(List<V> chunks) {
                // update the progress bar here
        }

    }.execute();
Rahul Winner
  • 430
  • 3
  • 16
  • thanks for the help but i didn't manage to solve this issue. @Rahul can you check now when i paste the whole code? – Udi Jul 21 '15 at 06:27
  • 1
    @Udi problem with your code that you are still doing your work in event-dispatcher thread. If you read my answer closely, I stated that you need to do everything in doInBackground() what you are doing in actionPerformed() method. And updating the progress bar will go in process() method of swingworker. Frankly speaking your code is pretty huge with many dependencies and correcting that would be a cumbersome task. I would recommend you to do it by your own. You may refer javadocs of swing worker do read more on it. – Rahul Winner Jul 21 '15 at 06:36
  • keep your code as it is. Just create a swing worker inside actionPerformed() and place everything inside doInBackground() ..send percent to publish() method of swingworker. And update the progress bar in process() swingworker. – Rahul Winner Jul 21 '15 at 06:38
  • rahul. thanks man! after sitting on it more , I made it. in general I did what you say and it helped me a lot. Publish the final code (only the relevant ) soon. – Udi Jul 24 '15 at 02:55