#!/usr/bin/env python
# coding: utf-8

# # Convolution Integral

# ### A *convolution*, $(h*x)(t)$, is a mathematical operator which manipulates two functions $x$ and $h$ and produces an output that represents the amount of overlap between $x$ and a reversed and translated version of $h$. </br>
# 
# ### In signal processing, one of the functions ($h$) is taken to be a fixed filter impulse response, and is known as a *kernel*.
# 
# $$  (x \ast h)(t) = \int_{-\infty}^{\infty}   x(\tau)h(t - \tau) \, d\tau$$
# 
# or
# 
# $$ (h \ast x)(t) = \int_{-\infty}^{\infty}   h(\tau)x(t - \tau) \, d\tau $$
# 
# Illustration: [1]

# In[188]:


from IPython.display import HTML
HTML('<iframe src=http://mathworld.wolfram.com/images/gifs/convrect.gif width=300 height=260></iframe>')


# In[189]:


from IPython.display import HTML
HTML('<iframe src=http://mathworld.wolfram.com/images/gifs/convgaus.gif width=300 height=260></iframe>')


# ### Steps </br>
# 
# ### 1. The impulse response $h(\tau)$ is flipped or time-reversed (that is, reflected about the origin) to obtain $h(-\tau)$ and then shifted by to form $h(t - \tau) = h[-(\tau - t)]$, which is a function of $\tau$ with parameter $t$.
# ### 2. The signal $x(\tau)$ and $h(t - \tau)$ are multiplied together for all values of $\tau$ with $t$ fixed at some value.
# ### 3. The product $x(\tau)h(t - \tau)$ is integrated over all $\tau$ to produce a single output value $y(t)$. 
# 
# </br>
# Ex.

# In[190]:


def step(t, t_0):
    return 1 * ((t - t_0) >= 0)


# In[191]:


get_ipython().run_line_magic('matplotlib', 'inline')
import matplotlib.pyplot as plt
import numpy as np


# ## Basic Example:
# 
# ## Calculate the convolution of a unit step input with a unit step response system.
# 
# 

# In[192]:


t = np.arange(-4.0, 4.0, 0.01)
x = step(t,0) 
h = step(t,0)

fig = plt.figure(figsize=(12,4))

plt.subplot(1, 2, 1)
plt.plot(t,x,'g-',linewidth=6);
plt.title('Input signal, $x(t)$')
plt.xlabel('t')

plt.subplot(1, 2, 2)
plt.plot(t,h,'r-',linewidth=6);
plt.title('Impulse response, $h(t)$')
plt.xlabel('t');


# $$  (x \ast h)(t) = \int_{-\infty}^{\infty}   u(\tau)u(t - \tau) \, d\tau$$

# ## Step 1: The impulse response $h(\tau)$ is flipped or time-reversed (that is, reflected about the origin) to obtain $h(-\tau)$ and then shifted by to form $h(t - \tau) = h[-(\tau - t)]$, which is a function of $\tau$ with parameter $t$.

# In[193]:


t = np.arange(-4.0, 4.0, 0.01)
h = step(-t, 0)
fig = plt.figure(figsize=(12,4))
plt.plot(t,h,'r-',linewidth=6);
plt.title('Impulse response, $h(-\u03c4)$ at t = 0')
plt.xlabel('T');


# ## Step 2-3 The signal $x(\tau)$ and $h(t - \tau)$ are multiplied together for all values of $\tau$ with $t$ fixed at some value. Then, the product $x(\tau)h(t - \tau)$ is integrated over all $\tau$ to produce a single output value $y(t)$. 

# In[194]:


t = np.arange(-4.0, 4.0, 0.01)
h = step(-t, -0.5)
x = step(t, 0)
fig = plt.figure(figsize=(12,4))
ax1 = fig.add_axes([0, 0, 1, 1])   # [left, bottom, width, height]

plt.plot(t,h,'r-',linewidth=6);
plt.plot(t,x,'g-',linewidth=6);
plt.title('Impulse response, $h(-\u03c4)$ at t = 0.5 with the input signal, $u(t)$')
plt.xlabel('T');
ax1.fill_between(t,0,h,where=x==h,color='black');
ax1.annotate('$t$', xy=(0.5, 0), xytext=(0.6, 0.1),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            )


# Notice that the time reversed Impulse response, $u(-\tau)$, starts intersecting the signal, which is also a unit step, $u(\tau)$, at $\tau = 0$ until $\tau = t$. 

# Thus, 
# 
# $$  (x \ast h)(t) = \int_{0}^{t}   x(\tau)h(t - \tau) \, d\tau$$  
# 
# $$  (x \ast h)(t) = \int_{0}^{t}   u(\tau)u(t - \tau) \, d\tau$$  
# 
# $$  (x \ast h)(t) = \int_{0}^{t}   (1)(1) \, d\tau$$ 
# 
# $$  (x \ast h)(t) = \left. \tau \right |_0^t  $$
# 
# $$  (x \ast h)(t) = t \, u(t) $$

# $$  (x \ast h)(t) = \begin{cases} 
#  0                 & \mbox{if } -\infty < t < 0 \\ 
#  t                 & \mbox{if }  \, 0 < t < \infty \\ 
# \end{cases} $$

# In[195]:


t = np.arange(-4.0, 4.0, 0.01)

# input
x = step(t,0)  

# impulse response
h = step(t,0) 

# result
result = np.zeros(len(t))
result = t * (step(t,0))

fig = plt.figure(figsize=(16,4))

plt.plot(t,x,'go-',linewidth=5, label='Input signal, $x(t)$');
plt.plot(t,h,'rd-',linewidth=1, label='Impulse response, $h(t)$');
plt.plot(t,result,'b-',linewidth=3, label='Output signal, $y(t)$');
plt.xlabel('t')
plt.grid()
legend = plt.legend(loc='upper left');


# In[196]:


t = np.arange(-4.0, 4.0, 0.01)
x = step(t,1) - step(t,3)
h = (t + 2)*(step(t,-2) - step(t,-1))

fig = plt.figure(figsize=(12,4))

plt.subplot(1, 2, 1)
plt.plot(t,x,'g-',linewidth=5);
plt.title('Input signal, $x(t)$')
plt.xlabel('t')

plt.subplot(1, 2, 2)
plt.plot(t,h,'r-',linewidth=3);
plt.title('Impulse response, $h(t)$')
plt.xlabel('t');


# ## Drill Problem 1: Compute the convolution, $(x \ast h)(t)$, of the signals represented in the figure above:

# ### Step 1: The impulse response $h(\tau)$ is flipped or time-reversed (that is, reflected about the origin) to obtain $h(-\tau)$ and then shifted by to form $h(t - \tau) = h[-(\tau - t)]$, which is a function of $\tau$ with parameter $t$.

# In[197]:


t = np.arange(-4.0, 4.0, 0.01)
h = (-t + 2)*(step(t,1) - step(t,2))
fig = plt.figure(figsize=(12,4))
plt.plot(t,h,'r-',linewidth=3);
plt.title('Impulse response, $h(-\u03c4)$ at t = 0')
plt.xlabel('T');


# Note: This is the $h(t - \tau)$ at $t = 0$ and the signal starts at $\tau = t + 1$ and ends at $\tau = t + 2$. 

# ## Step 2-3 The signal $x(\tau)$ and $h(t - \tau)$ are multiplied together for all values of $\tau$ with $t$ fixed at some value. Then, the product $x(\tau)h(t - \tau)$ is integrated over all $\tau$ to produce a single output value $y(t)$. 

# ## Case I: NO Overlap, $y(t) = 0$ at $-\infty \to t_1$, where $t_1 = -1$

# $$ y(t) = \int_{-\infty}^{-1} x(\tau)h(t - \tau) \, d\tau  = 0 $$

# In[198]:


t = np.arange(-4.0, 4.0, 0.01)
h_4 = (-t - 2)*(step(t,-3) - step(t,-2))
h_3 = (-t - 1)*(step(t,-2) - step(t,-1))
h_2 = (-t - 0)*(step(t,-1) - step(t,-0))
h_1 = (-t + 1)*(step(t,0) - step(t,1))
fig = plt.figure(figsize=(16,4))
plt.plot(t,h_4,'r-',linewidth=3, label="$t=-4$");
plt.plot(t,h_3,'c-',linewidth=3, label="$t=-3$");
plt.plot(t,h_2,'m-',linewidth=3, label="$t=-2$");
plt.plot(t,h_1,'y-',linewidth=3, label="$t=-1$");
plt.title('Impulse response, $h(-(\u03c4 - t))$ at t = -4,-3,-2,-1, with the input signal, $x(t)$')
plt.plot(t,x,'g-',linewidth=5, label="$x(t)$");
plt.xlabel('T');

legend = plt.legend() 


# ## Case II: Leading-edge overlap, at $t_1 \to t_2$ or at $ -1 < t < 0 $

# $$ y(t) = \int_{a}^{b} x(\tau)h(t - \tau) \, d\tau  $$

# In[199]:


t = np.arange(-4.0, 4.0, 0.01)
h_half = (-t + 1.5)*(step(t,0.5) - step(t,1.5))
fig = plt.figure(figsize=(12,2.5))
ax1 = fig.add_axes([0, 0, 1, 1])   # [left, bottom, width, height]
plt.plot(t,h_half,'r-',linewidth=3, label="$t=0.5$");
plt.title('Impulse response, $h(-(\u03c4 - t))$ at t = -0.5, with the input signal, $x(t)$')
plt.plot(t,x,'g-',linewidth=5, label="$x(t)$");
plt.xlabel('T');
ax1.fill_between(t,0,h_half,where=x>=h_half,color='black')
ax1.annotate('$t + 2$', xy=(1.5, 0), xytext=(1.6, 0.1),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            )
ax1.annotate('same \n length \n as \n base', xy=(1, 0.2), xytext=(0.55, 0.2),
            arrowprops=dict(facecolor='yellow'),
            )
ax1.annotate('t+2-1', xy=(1.25, 0), xytext=(1.1, -0.15),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            )
legend = plt.legend() 


# The overlap starts at $\tau = 1$ and ends at $\tau = t + 2$. Recall that the impulse response ends at $t+2$. Thus,  

# $$ y(t) = \int_{1}^{t+2} x(\tau)h(t - \tau) \, d\tau  $$  

# In the above interval, $x(\tau) = 1$ and $h(t - \tau) = - \tau + t + 2  $.

# $$ y(t) = \int_{1}^{t+2} (1)(- \tau + t + 2) \, d\tau  $$  

# $$ y(t) = \left. (t + 2) \tau - \dfrac{\tau^2}{2} \right |_1^{t+2} $$

# $$ y(t) = \left((t + 2)(t + 2) - \dfrac{(t+2)^2}{2}\right) - \left((t + 2) - \dfrac{1^2}{2}\right)  $$

# $$ y(t) = \dfrac{(t+2)^2}{2} - t - \dfrac{3}{2} $$

# $$ y(t) = \dfrac{t^2}{2} + \dfrac{4t}{2} + \dfrac{4}{2} -t - \dfrac{3}{2} $$

# $$ y(t) =  \dfrac{t^2}{2} + t + \dfrac{1}{2} $$ or $$  y(t) = \dfrac{1}{2} (t + 1)^2$$

# Alternatively, this can be evaluated by the triangle area:

# $$ A = \dfrac{1}{2} bh $$
# 
# $$ A = \dfrac{1}{2} (t+2-1)(t+1) $$
# 
# $$ A = \dfrac{1}{2}(t+1)^2 $$

# ## Case III: Full overlap, at $t = 0$ to $t = 1$ 

# $$ y(t) = \int_{a}^{b} x(\tau)h(t - \tau) \, d\tau  $$  

# In[200]:


t = np.arange(-4.0, 4.0, 0.01)
h_half = (-t + 2.5)*(step(t,1.5) - step(t,2.5))
fig = plt.figure(figsize=(12,2.5))
ax1 = fig.add_axes([0, 0, 1, 1])   # [left, bottom, width, height]
plt.plot(t,h_half,'r-',linewidth=3, label="$h$ at $t=0.5$");
plt.title('Impulse response, $h(-(\u03c4 - t))$ at t = -0.5, with the input signal, $x(t)$')
plt.plot(t,x,'g-',linewidth=5, label="$x(t)$");
plt.xlabel('T');
ax1.fill_between(t,0,h_half,where=x>=h_half,color='black')
legend = plt.legend(loc='center') 
ax1.annotate('$t + 2$', xy=(2.5, 0), xytext=(2.6, 0.1),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            )
ax1.annotate('$t + 1$', xy=(1.5, 0), xytext=(1.2, 0.1),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );


# The overlap starts at $\tau = t + 1$ and ends at $\tau = t + 2$.

# $$ y(t) = \int_{t+1}^{t+2} x(\tau)h(t - \tau) \, d\tau  $$  

# In the above interval, $x(\tau) = 1$ and $h(t - \tau) = - \tau + t + 2  $. Thus,

# $$ y(t) = \int_{t+1}^{t+2} (1) (- \tau + t + 2) \, d\tau  $$
# 
# $$ y(t) = \left. (t + 2) \tau - \dfrac{\tau^2}{2} \right |_{t+1}^{t+2} $$
# 
# $$ y(t) = \left((t + 2)(t + 2) - \dfrac{(t+2)^2}{2}\right) - \left((t + 2)(t+1) - \dfrac{(t+1)^2}{2}\right)  $$
# 

# $$ y(t) = \dfrac{(t+2)^2}{2} - (t + 1)(t+2 - \dfrac{t+1}{2}) $$
# 
# $$ y(t) =  \dfrac{(t^2 + 4t + 4)}{2} - (t + 1)(\dfrac{t}{2} + \dfrac{3}{2})$$
# 
# $$ y(t) = \dfrac{t^2}{2} + \dfrac{4t}{2} + \dfrac{4}{2} - \dfrac{t^2}{2} - \dfrac{4t}{2} - \dfrac{3}{2}$$

# $$ y(t) = \dfrac{1}{2} $$ 

# Alternatively, this can be evaluated by the triangle area:

# $$ A = \dfrac{1}{2} bh $$
# 
# $$ A = \dfrac{1}{2} (1)(1) $$
# 
# $$ A = \dfrac{1}{2} $$

# ## Case IV: Trailing edge overlap, at $1 < t < 2$ 

# $$ y(t) = \int_{a}^{b} x(\tau)h(t - \tau) \, d\tau  $$

# In[201]:


t = np.arange(-4.0, 4.0, 0.01)
h_half = (-t + 3.5)*(step(t,2.5) - step(t,3.5))
fig = plt.figure(figsize=(12,2.5))
ax1 = fig.add_axes([0, 0, 1, 1])   # [left, bottom, width, height]
plt.plot(t,h_half,'r-',linewidth=3, label="$h$ at $t=0.5$");
plt.title('Impulse response, $h(-(\u03c4 - t))$ at t = -0.5, with the input signal, $x(t)$')
plt.plot(t,x,'g-',linewidth=5, label="$x(t)$");
plt.xlabel('T');
ax1.fill_between(t,0,h_half,where=x>=h_half,color='black')
legend = plt.legend(loc='center') 
ax1.annotate('$t + 1$', xy=(2.5, 0), xytext=(2.2, 0.1),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );


# The overlap starts at $\tau = t + 1$ and ends at $\tau = 3$.

# $$ y(t) = \int_{t+1}^{3} x(\tau)h(t - \tau) \, d\tau  $$ 

# In the above interval, $x(\tau) = 1$ and $h(t - \tau) = - \tau + t + 2  $. Thus,
# 
# $$ y(t) = \int_{t+1}^{3} (1) (- \tau + t + 2) \, d\tau  $$
# 
# $$ y(t) = \left. (t + 2) \tau - \dfrac{\tau^2}{2} \right |_{t+1}^{3} $$
# 
# $$ y(t) =  \left((t + 2)(3) - \dfrac{(3)^2}{2}\right) - \left((t + 2)(t + 1) - \dfrac{(t+1)^2}{2}\right) $$

# $$ y(t) = \left(3t + 6 - \dfrac{9}{2}\right) - \left((t + 1)((t+2)- \dfrac{(t+1)}{2} )\right) $$ 
# 
# $$ y(t) = (3t + \dfrac{3}{2}) - (t + 1)(\dfrac{t}{2} + \dfrac{3}{2}) $$ 
# 
# $$ y(t) = 3t + \dfrac{3}{2} - \dfrac{t^2}{2} - \dfrac{4t}{2} -  \dfrac{3}{2} $$

# $$ y(t) = t - \dfrac{t^2}{2} $$ 
# 
# or
# 
# $$ y(t) = t (1 - \dfrac{t}{2}) $$ 

# Alternatively, this can be evaluated by subtracting the smaller triangle area, $A_t$, from the bigger triangle, $A_T$:

# $$ A = A_T - A_t$$
# 
# $$ A = \dfrac{1}{2} - \dfrac{1}{2} bh $$
# 
# $$ A = \dfrac{1}{2} -  \dfrac{1}{2} (t+2-3)(t+2-3) $$
# 
# $$ A = \dfrac{1}{2} -  \dfrac{1}{2}(t-1)^2 $$
# 
# $$ A = t - \dfrac{t^2}{2} $$

# ## Case V: No overlap, at $ t > 2$ 

# $$ y(t) = \int_{2}^{\infty} x(\tau)h(t - \tau) \, d\tau  = 0 $$

# In[202]:


t = np.arange(-4.0, 4.0, 0.01)
h_half = (-t + 4)*(step(t,3) - step(t,4))
fig = plt.figure(figsize=(12,2.5))
ax1 = fig.add_axes([0, 0, 1, 1])   # [left, bottom, width, height]
plt.plot(t,h_half,'r-',linewidth=3, label="$h$ at $t=2$");
plt.title('Impulse response, $h(-(\u03c4 - t))$ at t = -0.5, with the input signal, $x(t)$')
plt.plot(t,x,'g-',linewidth=5, label="$x(t)$");
plt.xlabel('T');
ax1.fill_between(t,0,h_half,where=x>=h_half,color='black')
legend = plt.legend(loc='center') 
ax1.annotate('No Overlap', xy=(3, 0.4), xytext=(2.2, 0.4),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );


# ## 1. Final Answer

# Therefore, the convolution result is:
# 
# 
# 
# $$ y(t) = \begin{cases} 
# 0                  & \mbox{if } -\infty < t < -1 \\ 
# \frac{1}{2}(t+1)^2 & \mbox{if } -1 < t < 0 \\  
# \frac{1}{2}        & \mbox{if }  \, 0 < t < 1 \\ 
# t - \frac{t^2}{2}  & \mbox{if }  \, 1 < t < 2 \\
#  0                 & \mbox{if }  \, 2 < t < \infty \\ 
# \end{cases} $$

# In[203]:


t = np.arange(-4.0, 4.0, 0.01)

# input
x = step(t,1) - step(t,3)

# impulse response
h = (t + 2)*(step(t,-2) - step(t,-1))

# result
result = np.zeros(len(t))
result = 0.5*(t+1)**2 * (step(t,-1)-step(t,0)) + 0.5* (step(t,0)-step(t,1)) + t * (1 - 0.5*t) * (step(t,1)-step(t,2))

fig = plt.figure(figsize=(14,4))

plt.plot(t,x,'g-',linewidth=5, label='Input signal, $x(t)$');
plt.plot(t,h,'r-',linewidth=3, label='Impulse response, $h(t)$');
plt.plot(t,result,'b-',linewidth=3, label='Output signal, $y(t)$');
plt.xlabel('t')
plt.grid()
legend = plt.legend(loc='upper left');


# In[204]:


t = np.arange(-2.0, 2.0, 0.01)
x = step(t,0) - step(t,1)
h = (-t + 1)*(step(t,0) - step(t,1))

fig = plt.figure(figsize=(15,3))

plt.subplot(1, 2, 1)
plt.plot(t,x,'g-',linewidth=5);
plt.title('Input signal, $x(t)$')
plt.xlabel('t')

plt.subplot(1, 2, 2)
plt.plot(t,h,'r-',linewidth=3);
plt.title('Impulse response, $h(t)$')
plt.xlabel('t');


# ## Drill Problem 2: Compute the convolution, $(h \ast x)(t)$, of the signals represented in the figure above:

# $$ y(t) = (h \ast x)(t) = \int_{-\infty}^{\infty}   h(\tau)x(t - \tau) \, d\tau $$

# Note: In this exercise, the signal is time-reversed.

# ### Step 1: The impulse response $h(\tau)$ is flipped or time-reversed (that is, reflected about the origin) to obtain $h(-\tau)$ and then shifted by to form $h(t - \tau) = h[-(\tau - t)]$, which is a function of $\tau$ with parameter $t$.

# In[205]:


t = np.arange(-2.0, 2.0, 0.01)
x = step(t,-1) - step(t,0)

fig = plt.figure(figsize=(12,3))
ax1 = fig.add_axes([0, 0, 1, 1])   # [left, bottom, width, height]

plt.plot(t,x,'g-',linewidth=5);
plt.title('Time-reversed input signal, $x(t-\u03c4)$')
plt.xlabel('T');
ax1.annotate('$t$', xy=(0, 0), xytext=(0.1, 0.1),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );
ax1.annotate('$t-1$', xy=(-1, 0), xytext=(-1.2, 0.1),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );


# Note: This rectangular pulse begins at $\tau = t-1$ and ends at $\tau = t$.

# ## Step 2-3 The signal $x(\tau)$ and $h(t - \tau)$ are multiplied together for all values of $\tau$ with $t$ fixed at some value. Then, the product $x(\tau)h(t - \tau)$ is integrated over all $\tau$ to produce a single output value $y(t)$. 

# In[ ]:





# In[206]:


t = np.arange(-2.0, 2.0, 0.01)
x_0 = step(t,-1) - step(t,0)
x__5 = step(t,-1.5) - step(t,-0.5)
x_1 = step(t,-2) - step(t,-1)
h = (-t + 1)*(step(t,0) - step(t,1))

fig = plt.figure(figsize=(12,3))
ax1 = fig.add_axes([1, 0, 1, 1])   # [left, bottom, width, height]

plt.plot(t,x_1,'cd-.',linewidth=5, label="x at $t=-1$");
plt.plot(t,x__5,'m--',linewidth=5, label="x at $t=-0.5$");
plt.plot(t,x_0,'g-',linewidth=3, label="x at $t=0$");
plt.title('Time-reversed input signal, $x(t-\tau)$ with the Impulse response, $h(t)$')
plt.plot(t,h,'r-',linewidth=3, label="h(t)");
plt.xlabel('T');

legend = plt.legend(loc='upper right');


# ## Case I: NO Overlap, $y(t) = 0$ at $-\infty \to t_1$, where $t_1 = 0$

# $$ (h \ast x)(t) = \int_{-\infty}^{0}   h(\tau)x(t - \tau) \, d\tau = 0 $$

# ## Case II: Leading-edge overlap, at $t_1 \to t_2$ or at $ 0 < t < 1 $

# $$ y(t) = \int_{a}^{b} x(\tau)h(t - \tau) \, d\tau  $$

# In[207]:


t = np.arange(-2.0, 2.0, 0.01)
x = step(t,-0.5) - step(t,0.5)
h = (-t + 1)*(step(t,0) - step(t,1))

fig = plt.figure(figsize=(12,3))
ax1 = fig.add_axes([1, 0, 1, 1])   # [left, bottom, width, height]

plt.plot(t,x,'g-',linewidth=5, label="x at $t=0.5$");
plt.title('Time-reversed input signal, $x(t-T)$ with the Impulse response, $h(t)$')
plt.plot(t,h,'r-',linewidth=3, label="h");
plt.xlabel('T');

ax1.annotate('$t$', xy=(0.5, 0), xytext=(0.6, 0.15),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );

ax1.fill_between(t,0,h,where=x>=h,color='black')
legend = plt.legend(loc='upper right');


# The overlap starts at $\tau = 0$ and ends at $\tau = t$. Thus,

# $$ y(t) = \int_{0}^{t}   h(\tau)x(t - \tau) \, d\tau = 0 $$

# In the above interval, $x(t -\tau) = 1$ and $h(\tau) = -\tau + 1  $.

# $$ y(t) = \int_{0}^{t}  (-\tau + 1) (1) \, d\tau $$
# 
# $$ y(t) = \left. \dfrac{-\tau^2}{2} + \tau \right |_{0}^{t} $$
# 
# $$ y(t) = \left( \dfrac{-t^2}{2} + t \right) - 0 $$

# $$ y(t) = t - \dfrac{t^2}{2} $$ or $$ y(t) = t  ( 1 - \dfrac{t}{2}) $$  

# ## Case III: Full overlap, at $t = 1$ 

# In[208]:


t = np.arange(-2.0, 2.0, 0.01)
x = step(t,0) - step(t,1)
h = (-t + 1)*(step(t,0) - step(t,1))

fig = plt.figure(figsize=(12,3))
ax1 = fig.add_axes([1, 0, 1, 1])   # [left, bottom, width, height]

plt.plot(t,x,'g-',linewidth=5, label="x at $t=0.5$");
plt.title('Time-reversed input signal, $x(t-T)$ with the Impulse response, $h(t)$')
plt.plot(t,h,'r-',linewidth=3, label="h");
plt.xlabel('T');

ax1.annotate('$t$', xy=(1, 0), xytext=(1.1, 0.15),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );

ax1.annotate('$t-1$', xy=(0, 0), xytext=(-0.2, 0.15),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );

ax1.fill_between(t,0,h,where=x>=h,color='black')
legend = plt.legend(loc='upper right');


# $$ y(t) = (h \ast x)(t) = \int_{t-1}^{t}   h(\tau)x(t - \tau) \, d\tau $$
# 
# $$ y(t) = \int_{t-1}^{t}  (-\tau + 1) (1) \, d\tau $$
# 
# $$ y(t) = \left. \dfrac{-\tau^2}{2} + \tau \right |_{t-1}^{t} $$

# $$ y(t) = \left( \dfrac{-t^2}{2} + t \right) - \left( \dfrac{-(t-1)^2}{2} + (t-1) \right) $$
# 
# $$ y(t) = \dfrac{-t^2}{2} + t - (t-1)(\dfrac{-(t-1)}{2} + 1) $$
# 
# $$ y(t) = \dfrac{-t^2}{2} + t - (t-1)(\dfrac{-t}{2} + \dfrac{1}{2} + 1) $$
# 
# $$ y(t) = \dfrac{-t^2}{2} + t - ( \dfrac{-t^2}{2} + \dfrac{4t}{2} - \dfrac{3}{2} ) $$
# 
# $$ y(t) = \dfrac{3}{2} - t $$

# at $t = 1$, $$ y(t) = (h \ast x)(t) = \int_{0}^{1}   h(\tau)x(t - \tau) \, d\tau = \dfrac{3}{2} - 1 = \dfrac{1}{2}$$

# ## Case IV: Trailing edge overlap, at $1 < t < 2$ 

# In[209]:


t = np.arange(-2.0, 2.0, 0.01)
x = step(t,0.5) - step(t,1.5)
h = (-t + 1)*(step(t,0) - step(t,1))

fig = plt.figure(figsize=(12,3))
ax1 = fig.add_axes([1, 0, 1, 1])   # [left, bottom, width, height]

plt.plot(t,x,'g-',linewidth=5, label="x at $t=1.5$");
plt.title('Time-reversed input signal, $x(t-T)$ with the Impulse response, $h(t)$')
plt.plot(t,h,'r-',linewidth=3, label="h");
plt.xlabel('T');

ax1.annotate('$t-1$', xy=(0.5, 0), xytext=(0.3, 0.15),
            arrowprops=dict(facecolor='yellow', shrink=0.05),
            );

ax1.fill_between(t,0,h,where=x>=h,color='black')
legend = plt.legend(loc='upper right');


# $$ y(t) = (h \ast x)(t) = \int_{t-1}^{1}   h(\tau)x(t - \tau) \, d\tau $$
# 
# $$ y(t) = \int_{t-1}^{1}  (-\tau + 1) (1) \, d\tau $$
# 
# $$ y(t) = \left. \dfrac{-\tau^2}{2} + \tau \right |_{t-1}^{1} $$
# 

# $$ y(t) = \left( \dfrac{-1^2}{2} +1 \right) -  \left( \dfrac{-(t - 1)^2}{2} + (t - 1) \right) $$
# 
# $$ y(t) = \dfrac{1}{2} - (t - 1)(\dfrac{-(t -1)}{2} + 1)$$
# 
# $$ y(t) = \dfrac{1}{2} - (t - 1)(\dfrac{-t}{2} + \dfrac{1}{2} + 1)$$
# 
# $$ y(t) = \dfrac{1}{2} - ( \dfrac{-t^2}{2} + \dfrac{4t}{2} - \dfrac{3}{2} ) $$
# 
# $$ y(t) = \dfrac{t^2}{2} - 2t + 2 $$

# ## Case V: No overlap, at $ t > 2$ 

# In[210]:


t = np.arange(-2.0, 2.0, 0.01)
x = step(t,1) - step(t,2)
h = (-t + 1)*(step(t,0) - step(t,1))

fig = plt.figure(figsize=(12,3))
ax1 = fig.add_axes([1, 0, 1, 1])   # [left, bottom, width, height]

plt.plot(t,x,'g-',linewidth=3, label="x at $t=2$");
plt.title('Time-reversed input signal, $x(t-T)$ with the Impulse response, $h(t)$')
plt.plot(t,h,'r-',linewidth=3, label="h");
plt.xlabel('T');
legend = plt.legend(loc='upper right');


# $$ y(t) = (h \ast x)(t) = \int_{2}^{\infty}   h(\tau)x(t - \tau) \, d\tau  = 0 $$

# ## 2. Final Answer

# Therefore, the convolution result is:
# 
# 
# 
# $$ y(t) = \begin{cases} 
# 0                  & \mbox{if } -\infty < t < 0 \\ 
# t ( 1 - \frac{t}{2}) & \mbox{if } 0 < t < 1 \\  
# \frac{1}{2}        & \mbox{if }  \, t = 1 \\ 
# \frac{t^2}{2} - 2t + 2  & \mbox{if }  \, 1 < t < 2 \\
#  0                 & \mbox{if }  \, 2 < t < \infty \\ 
# \end{cases} $$

# In[211]:


t = np.arange(-4.0, 4.0, 0.01)

# input
x = step(t,0) - step(t,1)

# impulse response
h = (-t + 1)*(step(t,0) - step(t,1))

# result
result = np.zeros(len(t))
result = t * (1 - 0.5*t) * (step(t,0) - step(t,1)) + (0.5*t*t - 2*t + 2)*(step(t,1) - step(t,2))

fig = plt.figure(figsize=(16,4))

plt.plot(t,x,'g-',linewidth=5, label='Input signal, $x(t)$');
plt.plot(t,h,'r-',linewidth=3, label='Impulse response, $h(t)$');
plt.plot(t,result,'b-',linewidth=3, label='Output signal, $y(t)$');
plt.xlabel('t')
plt.grid()
legend = plt.legend(loc='upper left');


# By: Melvin Cabatuan melvincabatuan@gmail.com
# 
# This ipython notebook is licensed under the CC-BY-NC-SA license: http://creativecommons.org/licenses/by-nc-sa/4.0/
# 
# ![http://i.creativecommons.org/l/by-nc-sa/3.0/88x31.png](http://i.creativecommons.org/l/by-nc-sa/3.0/88x31.png)

# References:
#     
#     [1] Weisstein, Eric W. "Convolution." From MathWorld--A Wolfram Web Resource. http://mathworld.wolfram.com/Convolution.html 
#     [2] Notes from  Prof. Alan Oppenheim. http://ocw.mit.edu/resources/res-6-007-signals-and-systems-spring-2011/