Why Future isDone() block the program like Future get()?

Viewed 3517

I'm writing a program for generating fractal and fractal animation, the problem is on the animation...

I have a main thread that generate a List<Callable<Long>> tasks where each element has the information and resources for generate one frame; then i use an ExecutorService to submit the work.

The problem is in the impossibility to cancel these secondary thread if the user want to stop the calculus. Here is the code:

public class Animation extends Task<Long> {
protected Long call() throws Exception {
    long startTime = System.currentTimeMillis();

    WritableImage[] frames = new WritableImage[frameNumber];
    List<Callable<Long>> tasks = new ArrayList<>();

    updateProgress(count.incrementAndGet(), maxCount);
    if (isCancelled()) {
        return System.currentTimeMillis() - startTime;;
    }

    for (int k = 0; k < frameNumber; k++) {
        frames[k] = new WritableImage(
                (int) start.getCartesianPlane().getWidth(),
                (int) start.getCartesianPlane().getHeight());

        CartesianFractal tmp = FractalFactory.bulidFractal(
                selectedFractal, nextDataBox(k), colorPalette);

        tmp.setOnFinish(t -> {
            updateProgress(count.incrementAndGet(), maxCount);
            return null;
        });

        tasks.add((Callable<Long>) tmp);
        if (isCancelled()) {
            return System.currentTimeMillis() - startTime;;
        }
    }

    executor = Executors.newFixedThreadPool(4);
    updateProgress(count.incrementAndGet(), maxCount);
    if (isCancelled()) {
        return System.currentTimeMillis() - startTime;
    }
    try {
        result = executor.invokeAll(tasks);
    }
    catch (InterruptedException ex) {
        System.err.println(ex.toString());
    }

    // Check if all tasks are finished
    boolean finished = false;
    while (!finished) {
        finished = true;
        // Check if it is all done
        for (Future<Long> r : result) {
            finished = finished && r.isDone(); // THE PROGRAM BLOCKS HERE
            // Check if the task was cancelled
            if (isCancelled()) {
                // Cancell all task
                tasks.stream().forEach((t) -> {
                    ((CartesianFractal)t).myCancel();
                });
                // Turnoff the executor
                executor.shutdown();
                return System.currentTimeMillis() - startTime;
            }
        }
    }

    // Turnoff the executor
    executor.shutdown();
    updateProgress(count.incrementAndGet(), maxCount);

    makeAnimation();
    updateProgress(count.incrementAndGet(), maxCount);

    return System.currentTimeMillis() - startTime;
}
}

I really don't understood why Future.isDone() block the program like Future.get() !

This is my first question, so i hope it's all ok.

2 Answers
Related