old_contents: # Copyright (c) James Percent and Unlock contributors.
  # All rights reserved.
  # Redistribution and use in source and binary forms, with or without modification,
  # are permitted provided that the following conditions are met:
  #
  #    1. Redistributions of source code must retain the above copyright notice,
  #       this list of conditions and the following disclaimer.
  #    
  #    2. Redistributions in binary form must reproduce the above copyright
  #       notice, this list of conditions and the following disclaimer in the
  #       documentation and/or other materials provided with the distribution.
  #
  #    3. Neither the name of Unlock nor the names of its contributors may be used
  #       to endorse or promote products derived from this software without
  #       specific prior written permission.
  #
  # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
  # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
  # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  # DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
  # ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
  # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
  # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
  # ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  # SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  from __future__ import division
  import matplotlib.pyplot as plt
  from unlock.analysis.accessor import NumpyDataTable
  import numpy as np
  import os
  from scipy.signal import butter, lfilter
  
  class Filter(object):
      def __init__(self, fs=256):
          super(Filter, self).__init__()
          self.fs = fs
  
      def filter(self, data):
          '''Subclass hook'''
          return data
  
  
  class BandpassFilter(Filter):
      def __init__(self, fs, lowcut, highcut):
          self.nyq = 0.5 * self.fs
          self.low = lowcut / self.nyq
          self.high = highcut / self.nyq
  
  
  class Butterworth(BandpassFilter):
      def __init__(self, schema, data, fs=256, lowcut=4, highcut=65, order=5):
          super(Butterworth, self).__init__(fs, lowcut, highcut)
          self.order = order
  
      def apply(self, data):
          b, a = butter(self.order, [self.low, self.high], btype='band')
          filtered_data = lfilter(b, a, data)
          return filtered_data
  
new_contents: # Copyright (c) James Percent and Unlock contributors.
  # All rights reserved.
  # Redistribution and use in source and binary forms, with or without modification,
  # are permitted provided that the following conditions are met:
  #
  #    1. Redistributions of source code must retain the above copyright notice,
  #       this list of conditions and the following disclaimer.
  #    
  #    2. Redistributions in binary form must reproduce the above copyright
  #       notice, this list of conditions and the following disclaimer in the
  #       documentation and/or other materials provided with the distribution.
  #
  #    3. Neither the name of Unlock nor the names of its contributors may be used
  #       to endorse or promote products derived from this software without
  #       specific prior written permission.
  #
  # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
  # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
  # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  # DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
  # ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
  # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
  # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
  # ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  # SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  from __future__ import division
  from scipy import signal
  
  class Filter(object):
      def __init__(self, fs=256):
          super(Filter, self).__init__()
          self.fs = fs
  
      def filter(self, data):
          '''Subclass hook'''
          return data
  
  
  class BandpassFilter(Filter):
      def __init__(self, fs, lowcut, highcut):
          self.nyq = 0.5 * self.fs
          self.low = lowcut / self.nyq
          self.high = highcut / self.nyq
  
  
  class Butterworth(BandpassFilter):
      def __init__(self, schema, data, fs=256, lowcut=4, highcut=65, order=5):
          super(Butterworth, self).__init__(fs, lowcut, highcut)
          self.order = order
  
      def apply(self, data):
          b, a = signal.butter(self.order, [self.low, self.high], btype='band')
          filtered_data = signal.filtfilt(b, a, data)
          return filtered_data
  
subject: Use filtfilt rather than lfilter