libpsynth 0.2.1
/home/raskolnikov/dev/psynth/trunk/src/psynth/sound/dynamic_buffer.hpp
Go to the documentation of this file.
00001 
00011 /*
00012  *  Copyright (C) 2010 Juan Pedro Bolivar Puente
00013  *
00014  *  This file is part of Psychosynth.
00015  *   
00016  *  Psychosynth is free software: you can redistribute it and/or modify
00017  *  it under the terms of the GNU General Public License as published by
00018  *  the Free Software Foundation, either version 3 of the License, or
00019  *  (at your option) any later version.
00020  *
00021  *  Psychosynth is distributed in the hope that it will be useful,
00022  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00023  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00024  *  GNU General Public License for more details.
00025  *
00026  *  You should have received a copy of the GNU General Public License
00027  *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
00028  *
00029  */
00030 
00031 /*
00032  *  Copyright 2005-2007 Adobe Systems Incorporated
00033  * 
00034  *  Use, modification and distribution are subject to the Boost
00035  *  Software License, Version 1.0. (See accompanying file
00036  *  LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt).
00037  */
00038 
00039 #ifndef PSYNTH_SOUND_DYNAMIC_BUFFER_HPP
00040 #define PSYNTH_SOUND_DYNAMIC_BUFFER_HPP
00041 
00042 #include <psynth/sound/buffer.hpp>
00043 #include <psynth/sound/dynamic_buffer_range.hpp>
00044 #include <psynth/sound/apply_operation.hpp>
00045 
00046 //#ifdef _MSC_VER
00047 //#pragma warning(push)
00048 //#pragma warning(disable : 4244)
00049 // conversion from 'std::ptrdiff_t' to 'int', possible loss of
00050 // data. even if we static-assert the two types are the same (on
00051 // visual studio 8)
00052 //#endif
00053 
00054 namespace psynth
00055 {
00056 
00057 namespace mpl = boost::mpl;
00058 
00059 namespace sound
00060 {
00061 
00062 namespace detail
00063 {
00064 
00065 template <typename T> struct get_range_type
00066 {
00067     typedef typename T::range type;
00068 };
00069 
00070 template <typename Buffers>
00071 struct buffers_get_ranges_type :
00072         public mpl::transform<Buffers,
00073                               mpl::quote1<get_range_type> > {};
00074 
00075 template <typename T>
00076 struct get_const_range_type
00077 {
00078     typedef typename T::const_range type;
00079 };
00080 
00081 template <typename Buffers>
00082 struct buffers_get_const_ranges_type :
00083         public mpl::transform<Buffers,
00084                               mpl::quote1<get_const_range_type> > {};
00085 
00086 struct recreate_buffer_fnobj
00087 {
00088     typedef void result_type;
00089     std::size_t _size;
00090     unsigned    _alignment;
00091 
00092     recreate_buffer_fnobj (std::size_t size, unsigned alignment)
00093         : _size (size)
00094         , _alignment (alignment)
00095     {}
00096 
00097     template <typename Buffer>
00098     result_type operator () (Buffer& img) const
00099     {
00100         img.recreate (_size, _alignment);
00101     }
00102 };
00103 
00104 template <typename AnyRange>  // Models AnyRangeConcept
00105 struct dynamic_buffer_get_range
00106 {
00107     typedef AnyRange result_type;
00108 
00109     template <typename Buffer>
00110     result_type operator() (Buffer& img) const
00111     {
00112         return result_type (range (img));
00113     }
00114 };
00115 
00116 template <typename AnyConstRange>  // Models AnyConstRangeConcept
00117 struct dynamic_buffer_get_const_range
00118 {
00119     typedef AnyConstRange result_type;
00120         
00121     template <typename Buffer>
00122     result_type operator () (const Buffer& img) const
00123     {
00124         return result_type (const_range (img));
00125     }
00126 };
00127 
00128 } /* namespace detail */
00129 
00148 template <typename BufferTypes>
00149 class dynamic_buffer : public variant<BufferTypes>
00150 {
00151     typedef variant<BufferTypes> parent_type;
00152 
00153 public:
00154     typedef dynamic_buffer_range<
00155     typename detail::buffers_get_const_ranges_type<BufferTypes>::type>
00156     const_range;
00157 
00158     typedef dynamic_buffer_range<
00159         typename detail::buffers_get_ranges_type<BufferTypes>::type>
00160     range;
00161 
00162     typedef typename range::size_type       size_type;
00163     typedef typename range::difference_type difference_type;
00164 
00165     dynamic_buffer ()
00166         : parent_type () {}
00167     
00168     template <typename T>
00169     explicit dynamic_buffer (const T& obj)
00170         : parent_type (obj) {}
00171     
00172     template <typename T>
00173     explicit dynamic_buffer (T& obj, bool do_swap)
00174         : parent_type (obj, do_swap) {}
00175 
00176     dynamic_buffer (const dynamic_buffer& v)
00177         : parent_type ((const parent_type&) v)    {}
00178 
00179     template <typename T>
00180     dynamic_buffer& operator= (const T& obj)
00181     {
00182         parent_type::operator= (obj);
00183         return *this;
00184     }
00185     
00186     dynamic_buffer& operator= (const dynamic_buffer& v)
00187     {
00188         parent_type::operator= ((const parent_type&) v);
00189         return *this;
00190     }
00191 
00192     void recreate (size_type size, unsigned align = 1)
00193     {
00194         apply_operation (*this, detail::recreate_buffer_fnobj (size, align));
00195     }
00196 
00197     std::size_t num_samples () const
00198     {
00199         return apply_operation (*this, detail::dynamic_type_get_num_samples ());
00200     }
00201 
00202     size_type size () const
00203     {
00204         return apply_operation (*this, detail::dynamic_type_get_size ());
00205     }
00206 };
00207 
00218 template <typename Types>  PSYNTH_FORCEINLINE // Models BufferVectorConcept
00219 typename dynamic_buffer<Types>::range
00220 range (dynamic_buffer<Types>& buf)
00221 { 
00222     return apply_operation (
00223         buf, detail::dynamic_buffer_get_range<
00224             typename dynamic_buffer<Types>::range> ());
00225 }
00226 
00231 template <typename Types> PSYNTH_FORCEINLINE // Models BufferVectorConcept
00232 typename dynamic_buffer<Types>::const_range
00233 const_range (const dynamic_buffer<Types>& buf)
00234 { 
00235     return apply_operation (
00236         buf, detail::dynamic_buffer_get_const_range <
00237             typename dynamic_buffer<Types>::const_range> ());
00238 }
00241 } /* namespace sound */
00242 } /* namespace psynth */
00243 
00244 //#ifdef _MSC_VER
00245 //#pragma warning(pop)
00246 //#endif
00247 
00248 #endif /* PSYNTH_SOUND_DYNAMIC_BUFFER */