Creating animated plot

Matplotlib was not designed as an animation package from the get-go, and thus it would appear sluggish in some advanced usages. For animation-centric applications, PyGame is a very good alternative (https://www.pygame.org) which supports OpenGL- and Direct3D-accelerated graphics for the ultimate speed in animating objects. Nevertheless, Matplotlib has acceptable performance most of the time, and we will guide you through the steps to create animations that are more engaging than static plots.

Before we start making animations, we need to install either FFmpeg, avconv, mencoder, or ImageMagick on our system. These additional dependencies are not bundled with Matplotlib, and thus we need to install them separately. We are going to walk you through the steps of installing FFmpeg.

For Debian-based Linux users, FFmpeg can be installed by simply issuing the following command in Terminal.

sudo apt-get install ffmpeg

For Mac users, Homebrew (https://brew.sh/) is the simplest way to search and install ffmpeg package. If you don't have Homebrew, you can paste the following code into your Terminal to install it.

/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"

After that, we can install FFmpeg by issuing the following command in the Terminal:

brew install ffmpeg

Alternatively, you may install FFmpeg by copying the binaries (https://evermeet.cx/ffmpeg/) to the system path (for example, /usr/local/bin).

The installation for Windows users is quite a bit more involved, but luckily there is a detailed guide on wikiHow (https://www.wikihow.com/Install-FFmpeg-on-Windows).

Matplotlib provides two main interfaces for creating animations: TimedAnimation and FuncAnimation. TimedAnimation is useful for creating time-based animation, while FuncAnimation can be used to create animation according to a custom-defined function. Given by the much higher level of flexibility offered by FuncAnimation, we will only explore the use of FuncAnimation in this section. Interested readers can refer to the official documentation (https://matplotlib.org/api/animation_api.html) for more information about TimedAnimation.

In the following example, we simulated the change in median weekly earnings by assuming a 5% annual increase. We are going to create a custom function—animate, which returns Matplotlib Artist objects that are changed in each frame. This function will be supplied to animation.FuncAnimation() together with a few more extra parameters:

import textwrap 
import matplotlib.pyplot as plt
import random
# Matplotlib animation module
from matplotlib import animation
# Used for generating HTML video embed code
from IPython.display import HTML

# Adapted from previous example, codes that are modified are commented
fig, ax = plt.subplots(figsize=(6,7))
ind = range(df.shape[0])
rects = ax.barh(ind, df["Median usual weekly earnings ($)"], height=0.5)
ax.set_xlabel('Median weekly earnings (USD)')
ylabels=[textwrap.fill(label,15) for label in df["Educational attainment"]]
ax.set_yticks(ind)
ax.set_yticklabels(ylabels)
fig.subplots_adjust(left=0.3)

# Change the x-axis range
ax.set_xlim(0,7600)

# Add a text annotation to show the current year
title = ax.text(0.5,1.05, "Median weekly earnings (USD) in 2017",
bbox={'facecolor':'w', 'alpha':0.5, 'pad':5},
transform=ax.transAxes, ha="center")

# Animation related stuff
n=30 #Number of frames

def animate(frame):
# Simulate 5% annual pay rise
data = df["Median usual weekly earnings ($)"] * (1.05 ** frame)

# Update the bar heights
for i, rect in enumerate(rects):
rect.set_width(data[i])

# Update the title
title.set_text("Median weekly earnings (USD) in {}".format(2016+frame))

return rects, title

# Call the animator. Re-draw only the changed parts when blit=True.
# Redraw all elements when blit=False
anim=animation.FuncAnimation(fig, animate, blit=False, frames=n)

# Save the animation in MPEG-4 format
anim.save('test.mp4')

# OR--Embed the video in Jupyter Notebook
HTML(anim.to_html5_video())

Here is the resultant video:

https://github.com/PacktPublishing/Matplotlib-for-Python-Developers-Second-Edition/blob/master/extra_ch9/ch09_animation.mp4

In the preceding example, we output animation in the form of MPEG-4 encoded videos. The video can also be embedded in Jupyter Notebook in the form of H.264 encoded video. All you need to do is to call the Animation.to_html5_video() method, and supply the returned object to IPython.display.HTML. Video encoding and HTML5 code generation will happen automagically behind the scenes.

Starting from version 2.2.0, Matplotlib supports the creation of animated GIF writing via the Pillow imaging library and ImageMagick. As the WWW is never tired of GIFs, let's learn how to create one!

Before we are able to create animated GIFs, we need to install ImageMagick first. The download links and the installation instructions for all major platforms can be found here: https://www.imagemagick.org/script/download.php.

Once the package is installed, we can generate animated GIFs by changing the line anim.save('test.mp4') to anim.save('test.gif', writer='imagemagick', fps=10). The fps parameter denotes the frame rate of the animation.

Here is the resultant animated GIF:

https://github.com/PacktPublishing/Matplotlib-for-Python-Developers-Second-Edition/blob/master/extra_ch9/ch%2009_GIF.gif

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.119.133.241