|
libpsynth 0.2.1
|
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_PLANAR_REF_H 00040 #define PSYNTH_SOUND_PLANAR_REF_H 00041 00042 #include <boost/mpl/range_c.hpp> 00043 00044 #include <psynth/base/compat.hpp> 00045 #include <psynth/sound/concept.hpp> 00046 #include <psynth/sound/channel_base.hpp> 00047 #include <psynth/sound/sample.hpp> 00048 #include <psynth/sound/frame.hpp> 00049 #include <psynth/sound/planar_frame_iterator.hpp> 00050 00051 namespace psynth 00052 { 00053 namespace sound 00054 { 00055 00082 template <typename SampleReference, typename ChannelSpace> 00083 // SampleReference is a sample reference (const or mutable) 00084 struct planar_frame_reference : public detail::homogeneous_channel_base< 00085 SampleReference, layout<ChannelSpace>, boost::mpl::size<ChannelSpace>::value> 00086 { 00087 typedef detail::homogeneous_channel_base< 00088 SampleReference, layout<ChannelSpace>, 00089 boost::mpl::size<ChannelSpace>::value> 00090 parent_type; 00091 00092 private: 00093 // These three are only defined for homogeneous frames 00094 typedef typename sample_traits<SampleReference>::value_type 00095 sample_type; 00096 typedef typename sample_traits<SampleReference>::const_reference 00097 sample_const_reference; 00098 00099 public: 00100 BOOST_STATIC_CONSTANT( 00101 bool, is_mutable = sample_traits<SampleReference>::is_mutable); 00102 00103 typedef frame <sample_type, layout<ChannelSpace> > value_type; 00104 typedef planar_frame_reference reference; 00105 typedef planar_frame_reference<sample_const_reference, ChannelSpace> 00106 const_reference; 00107 00108 planar_frame_reference (SampleReference v0, SampleReference v1) 00109 : parent_type (v0,v1) {} 00110 00111 planar_frame_reference (SampleReference v0, SampleReference v1, 00112 SampleReference v2) 00113 : parent_type (v0,v1,v2) {} 00114 00115 planar_frame_reference (SampleReference v0, SampleReference v1, 00116 SampleReference v2, SampleReference v3) 00117 : parent_type (v0,v1,v2,v3) {} 00118 00119 planar_frame_reference (SampleReference v0, SampleReference v1, 00120 SampleReference v2, SampleReference v3, 00121 SampleReference v4) 00122 : parent_type (v0,v1,v2,v3,v4) {} 00123 00124 planar_frame_reference (SampleReference v0, SampleReference v1, 00125 SampleReference v2, SampleReference v3, 00126 SampleReference v4, SampleReference v5) 00127 : parent_type (v0,v1,v2,v3,v4,v5) {} 00128 00129 template <typename P> 00130 planar_frame_reference (const P& p) 00131 : parent_type(p) 00132 { check_compatible<P>(); } 00133 00134 // PERFORMANCE_CHECK: Is this constructor necessary? 00135 template <typename SampleV, typename Mapping> 00136 planar_frame_reference (frame<SampleV,layout<ChannelSpace,Mapping> >& p) 00137 : parent_type (p) 00138 { check_compatible<frame<SampleV,layout<ChannelSpace,Mapping> > >();} 00139 00140 // Construct at offset from a given location 00141 template <typename SamplePtr> 00142 planar_frame_reference ( 00143 const planar_frame_iterator<SamplePtr,ChannelSpace>& p, 00144 std::ptrdiff_t diff) 00145 : parent_type (p, diff) {} 00146 00147 const planar_frame_reference& 00148 operator= (const planar_frame_reference& p) const 00149 { 00150 static_copy (p, *this); 00151 return *this; 00152 } 00153 00154 template <typename P> 00155 const planar_frame_reference& operator= (const P& p) const 00156 { 00157 check_compatible<P>(); 00158 static_copy (p,*this); 00159 return *this; 00160 } 00161 00162 /* 00163 This overload is necessary for a compiler implementing Core 00164 Issue 574 to prevent generation of an implicit copy assignment 00165 operator (the reason for generating implicit copy assignment 00166 operator is that according to Core Issue 574, a cv-qualified 00167 assignment operator is not considered "copy assignment 00168 operator"). EDG implemented Core Issue 574 starting with EDG 00169 Version 3.8. I'm not sure why they did it for a template member 00170 function as well. 00171 */ 00172 00173 #if BOOST_WORKAROUND(__HP_aCC, >= 61700) || \ 00174 BOOST_WORKAROUND(__INTEL_COMPILER, >= 1000) 00175 00176 const planar_frame_reference& operator= (const planar_frame_reference& p) 00177 { 00178 static_copy (p, *this); 00179 return *this; 00180 } 00181 00182 template <typename P> 00183 const planar_frame_reference& operator= (const P& p) 00184 { 00185 check_compatible<P>(); 00186 static_copy (p, *this); 00187 return *this; 00188 } 00189 00190 #endif /* BOOST_WORKAROUND */ 00191 00192 template <typename P> 00193 bool operator== (const P& p) const 00194 { 00195 check_compatible<P>(); 00196 return static_equal (*this, p); 00197 } 00198 00199 template <typename P> 00200 bool operator!= (const P& p) const 00201 { 00202 return !(*this == p); 00203 } 00204 00205 SampleReference operator[] (std::size_t i) const 00206 { 00207 return this->at_c_dynamic (i); 00208 } 00209 00210 const planar_frame_reference* operator->() const 00211 { 00212 return this; 00213 } 00214 00215 private: 00216 template <typename Frame> 00217 static void check_compatible() 00218 { 00219 base::psynth_function_requires<FramesCompatibleConcept< 00220 Frame, planar_frame_reference> >(); 00221 } 00222 }; 00223 00224 00225 /* 00226 * 00227 * ChannelBasedConcept 00228 * 00229 */ 00230 00231 template <typename SampleReference, typename ChannelSpace, int K> 00232 struct kth_element_type<planar_frame_reference<SampleReference,ChannelSpace>, K> 00233 { 00234 typedef SampleReference type; 00235 }; 00236 00237 template <typename SampleReference, typename ChannelSpace, int K> 00238 struct kth_element_reference_type< 00239 planar_frame_reference<SampleReference,ChannelSpace>, K> 00240 { 00241 typedef SampleReference type; 00242 }; 00243 00244 template <typename SampleReference, typename ChannelSpace, int K> 00245 struct kth_element_const_reference_type<planar_frame_reference< 00246 SampleReference,ChannelSpace>, K> 00247 : public boost::add_reference< 00248 typename boost::add_const<SampleReference>::type> 00249 { 00250 // typedef typename sample_traits<SampleReference>::const_reference type; 00251 }; 00252 00253 00254 /* 00255 * 00256 * FrameConcept 00257 * 00258 */ 00259 00265 template <typename SampleReference, typename ChannelSpace> 00266 struct is_frame< planar_frame_reference<SampleReference,ChannelSpace> > 00267 : public boost::mpl::true_{}; 00268 00269 00270 /* 00271 * 00272 * HomogeneousFrameBasedConcept 00273 * 00274 */ 00275 00281 template <typename SampleReference, typename ChannelSpace> 00282 struct channel_space_type<planar_frame_reference<SampleReference,ChannelSpace> > 00283 { 00284 typedef ChannelSpace type; 00285 }; 00286 00293 template <typename SampleReference, typename ChannelSpace> 00294 struct sample_mapping_type<planar_frame_reference<SampleReference, ChannelSpace> > 00295 { 00296 typedef typename layout<ChannelSpace>::sample_mapping_t type; 00297 }; 00298 00299 00306 template <typename SampleReference, typename ChannelSpace> 00307 struct is_planar<planar_frame_reference<SampleReference,ChannelSpace> > : 00308 boost::mpl::true_ {}; 00309 00316 template <typename SampleReference, typename ChannelSpace> 00317 struct sample_type<planar_frame_reference<SampleReference,ChannelSpace> > 00318 { 00319 typedef typename sample_traits<SampleReference>::value_type type; 00320 }; 00321 00322 } /* namespace sound */ 00323 } /* namespace psynth */ 00324 00325 namespace std 00326 { 00327 00328 /* 00329 We are forced to define swap inside std namespace because on some 00330 platforms (Visual Studio 8) STL calls swap qualified. 00331 00332 swap with 'left bias': 00333 - swap between proxy and anything 00334 - swap between value type and proxy 00335 - swap between proxy and proxy 00336 00337 Having three overloads allows us to swap between different (but 00338 compatible) models of FrameConcept 00339 00340 */ 00341 00346 template <typename CR, typename CS, typename R> inline 00347 void swap (const psynth::sound::planar_frame_reference<CR,CS> x, R& y) 00348 { 00349 psynth::sound::swap_proxy< 00350 typename psynth::sound::planar_frame_reference<CR,CS>::value_type> (x, y); 00351 } 00352 00357 template <typename CR, typename CS> inline 00358 void swap (typename psynth::sound::planar_frame_reference<CR,CS>::value_type& x, 00359 const psynth::sound::planar_frame_reference<CR,CS> y) 00360 { 00361 psynth::sound::swap_proxy< 00362 typename psynth::sound::planar_frame_reference<CR,CS>::value_type> (x, y); 00363 } 00364 00365 00370 template <typename CR, typename CS> inline 00371 void swap (const psynth::sound::planar_frame_reference<CR,CS> x, 00372 const psynth::sound::planar_frame_reference<CR,CS> y) 00373 { 00374 psynth::sound::swap_proxy< 00375 typename psynth::sound::planar_frame_reference<CR,CS>::value_type>(x, y); 00376 } 00377 00378 } /* namespace std */ 00379 00380 #endif /* PSYNTH_SOUND_PLANAR_FRAME_REF */
1.7.4