1. La fractale est redessinée dans la fenêtre retaillée. Cela fonctionne parce que les trois points de base du triangle sont recalculés au début de la méthode paint en fonction de la taille courante du composant SiepCanvas.

  2. On regroupe tout sans se préocuper de relier le GraphicCounter et le SiepCanvas
    import java.awt.* ;
    import java.awt.event.*;

    class Siep extends Frame {
      
    Siep (String title, int n) {
        
    super(title) ;

        
    Counter c = new Counter(n) ;
        
    GraphicCounter gc = new GraphicCounter(c) ;
        
    SiepCanvas sc = new SiepCanvas(c) ;
        
    Button quit = new QuitButton () ;


        add("North", gc) ;
        add("Center",sc) ;
        add("South", quit) ;
        setSize (450, 480);
        setLocation(100,100) ;
      }

       
    public static void main (String[] args) {
         
    int n = 3 ;
         
    if (args.length > 0) n = Integer.parseInt(args[0]) ;
         
    new Siep("Sierpinsky", n).show() ;
       }
    }
    Dès lors, il n'y a aucune raison que la fractale se redessine quand la valeur du compteur change.

  3. Un idée est de redéfinir les deux méthodes qui changent l'état du compteur, afin qu'elles invoquent la méthode repaint du canevas après le changement d'état du compteur.
    class OtherCounter extends Counter {
      
    private Siep s ;

      
    OtherCounter(int n, Siep s) {  super(n) ; this.s = s ; }

      
    void incr() { super.incr() ; s.sc.repaint() }

      
    void decr() { super.decr() ; s.sc.repaint() }
    }
    Il faut ensuite modifier Siep ainsi :
    class Siep extends Frame {
      
    SiepCanvas sc ;

      
    Siep (String title, int n) {
        …
        
    Counter c = new OtherCounter(n, this) ;
        
    GraphicCounter gc = new GraphicCounter(c) ;
        sc = 
    new SiepCanvas(c) ;
        …
      }
    }
    C'est en fait assez tordu, il n'y a pas de raison que le compteur connaisse quelque chose du graphisme. La technique de la question suivante semble plus cohérente, à condition d'avoir doté les compteurs graphiques d'une méthode addActionListener (ce que nous avons fait).

  4. Voici la réponse finale, selon le modèle des ActionListener. Une classe Siep.
    import java.awt.* ;
    import java.awt.event.*;

    class Siep extends Frame {
      
    Siep (String title, int n) {
        
    super(title) ;

        
    Counter c = new Counter(n) ;
        
    GraphicCounter gc = new GraphicCounter(c) ;
        
    SiepCanvas sc = new SiepCanvas(c) ;
        
    Button quit = new QuitButton () ;


        add("North", gc) ;
        add("Center",sc) ;
        add("South", quit) ;
        gc.addActionListener (
    new RepaintListener (sc)) ;

        setSize (450, 480);
        setLocation(100,100) ;
      }

       
    public static void main (String[] args) {
         
    int n = 3 ;
         
    if (args.length > 0) n = Integer.parseInt(args[0]) ;
         
    new Siep("Sierpinsky", n).show() ;
       }
    }

    class RepaintListener implements ActionListener {
      
    Component comp ;

      
    RepaintListener(Component comp) { this.comp = comp ; }

      
    public void actionPerformed(ActionEvent e) {
        comp.repaint() ;
      }
    }
    Un aspect notable est que l'espion fonctionne avec n'importe quel composant.

    Il est sans doute temps de revenir à la définition de la class Op pour voir ce qui est fait du champ listener du compteur graphique.