Animaties

Hoewel een grafiek heel handig kan zijn om een simulatie te visualiseren is het soms inzichtelijker een animatie te maken. Python biedt je de mogelijkheid om een figuur steeds opnieuw te tekenen. Dat geeft je verschillende mogelijkheden om een beweging aan te geven. We bouwen hier een kort voorbeeld, waarin we een lijn (en punt) volgens $f(x)=sin(x)$ over het scherm laten bewegen. We bouwen de functie op in 3 stappen waarbij we telkens 1 element toevoegen. Met behulp van deze functionaliteit kun je een groot scala aan animaties maken.

Een bewegend stipje

Als je een punt tekent (één $x$-waarde en één $y$-waarde) waarvan je $x$ en $y$ steeds verandert dan lijkt het of het punt over het scherm beweegt. In de code hieronder nemen we steeds stapjes in $x$, rekenen $y$ uit en tekenen het punt op het scherm. We gebruiken ook de commando’s xlim en ylim om in de plot aan te geven welke $x$-waardes en $y$-waardes we willen zien.

import matplotlib
matplotlib.use('TkAgg')

import math
import numpy as np
import matplotlib.pyplot as plt

# neem kleine stappen in x tussen 0 en 2pi
for x in np.arange(0,2 * math.pi, 0.05):

    y = math.sin(x)

    # plot grafiek
    plt.plot(x, y, 'bo', markersize = 10)  # blauwe punt
    plt.xlim(0,2 * math.pi)
    plt.ylim(-1, 1)
    plt.draw()           # update grafiek
    plt.pause(0.001)
    plt.clf()            # clear grafiek

Je ziet dat we in de code de functie pause() aanroepen. Dat doen we om pyplot de gelegenheid te geven de nieuwe figuur op het scherm te tekenen. Dit wordt alleen gedaan tijdens de pauzes die we geven.

Animaties in de CS50 IDE

Omdat de CS50 IDE normaal gesproken geen scherm heeft om de animaties in te tonen, zal je bij het opstarten van bovenstaand programma in eerste instantie een error te zien krijgen. Gelukkig hebben we daar een oplossing voor! Voer voordat je je programma opstart eerst het commando gui50 uit. Je krijgt dan een link waar je op kan klikken om een speciale GUI te openen. Wanneer je vervolgens in de CS50 IDE in een nieuwe terminal je programma opstart, krijg je de animatie te zien in het andere tabblad.

gui50 is op dit moment nog in beta. Mogelijk moet je af en toe de pagina opnieuw openen of op ‘Connect’ klikken. Mocht het niet werken, stel je vraag dan via Ed.

Een bewegende lijn

Een grafiek tekenen we met behulp van lijsten: een lijst met $x$-waardes en een lijst met $y$-waardes. Als je die lijsten steeds uitbreidt dan krijg je het onderstaande effect: de functie $f(x) = sin(x)$ getekend met een rode lijn.

import matplotlib
matplotlib.use('TkAgg')

import math
import numpy as np
import matplotlib.pyplot as plt

L_x = []
L_y = []

# take small steps in x
for x in np.arange(0,2 * math.pi, 0.05):

    y = math.sin(x)

    L_x.append(x)
    L_y.append(y)

    # plot grafiek
    plt.plot(L_x, L_y, 'r-')   # rode lijn
    plt.xlim(0,2 * math.pi)
    plt.ylim(-1, 1)
    plt.draw()           # update grafiek
    plt.pause(0.001)
    plt.clf()            # clear grafiek

Zoals je ziet is de code maar drie regels veranderd ten opzichte van voorbeeld 1. Het resultaat ziet er als volgt uit:

Een stip, een lijn en tekst

Je kan de stip en de lijn ook tegelijk tekenen en op het scherm ook informatie weergeven over de $(x,y)$ positie van het punt op het scherm.

import matplotlib
matplotlib.use('TkAgg')

import math
import numpy as np
import matplotlib.pyplot as plt

L_x = []
L_y = []

# take small steps in x
for x in np.arange(0,2*math.pi,0.05):

    y = math.sin(x)

    L_x.append(x)
    L_y.append(y)

    # plot grafiek
    plt.plot(L_x, L_y, 'r-')               # rode lijn
    plt.plot(x, y, 'bo', markersize = 10)  # blauwe stip
    plt.xlim(0,2 * math.pi)
    plt.ylim(-1,1)

    # text op scherm      
    plt.text( 0.25, -0.8, "(%.2f,%.2f)" % (x,y) )  

    plt.draw()           # update grafiek
    plt.pause(0.001)
    plt.clf()            # clear grafiek