# This source code is public domain
import numpy
import matplotlib.pyplot as plt
import imageio
x = numpy.array([1,2,3,4,5,6,7])
y = numpy.array([2.0,2.5,2.5,3.4,3.7,6.6,3])
images = []
for nPoly in range(1,8):
phi = numpy.array([x**i for i in range(nPoly)])
A = phi @ phi.T
b = phi @ y
c = numpy.linalg.solve(A, b)
yPoly = c @ phi
residuen = []
for i in range(len(x)): residuen+=[[x[i],x[i]],[y[i],yPoly[i]],'g-']
xneu = numpy.linspace(0, 8, num=100)
yneu = numpy.sum([c[i]*xneu**i for i in range(len(c))],axis=0)
plt.clf()
fig = plt.figure(figsize=(4.2, 3.2), dpi=120)
fig.subplotpars.bottom=0.13
y0 = plt.plot(*residuen[:-3])
plt.setp(y0, color='#80d080', linewidth=1.5)
y0, = plt.plot(*residuen[-3:],label='Residuen')
plt.setp(y0, color='#80d080', linewidth=1.5)
y2, = plt.plot(xneu,yneu,'r-',label='Modellfunktion')
y1, = plt.plot(x,y,'o', label='Messpunkte')
plt.xlabel('x')
plt.ylabel('y')
order = y1,y2,y0
leg = plt.legend(order,[p.get_label() for p in order], frameon=True, loc='lower right')
plt.grid(True, alpha=0.7)
plt.axis([0, 8, 0, 8])
plt.text(1,7, "Polynomgrad "+str(nPoly-1),bbox = dict(boxstyle="square,pad=0.5",color='white',ec='black',fill=True))
plt.tight_layout()
# plt.savefig('MDKQ_anim%i.png'%N)
fig.canvas.draw()
s, (width, height) = fig.canvas.print_to_buffer()
images.append(numpy.array(list(s), numpy.uint8).reshape((height, width, 4)))
fig.clf()
plt.close('all')
# Save GIF animation
fileOut = 'MDKQ_animation.gif'
imageio.mimsave(fileOut, images, duration=[1,1,1,1,1,1,3])
# Optimize GIF size
from pygifsicle import optimize
optimize(fileOut, colors=16)