#ifndef SPROUT_COMPOST_EFFECTS_AUTO_PAN_HPP #define SPROUT_COMPOST_EFFECTS_AUTO_PAN_HPP #include #include #include #include #include #include #include #include #include #include namespace sprout { namespace compost { // // auto_pan_outdirected_value // template struct auto_pan_outdirected_value { public: typedef Value value_type; typedef IntType int_type; private: value_type depth_; value_type rate_; int_type samples_per_sec_; private: template SPROUT_CONSTEXPR typename std::enable_if< Left, typename std::iterator_traits::value_type >::type calc(Outdirected const& x) const { return (1 + depth_ * sprout::sin(2 * sprout::math::pi() * rate_ * x.index() / samples_per_sec_)) * *x; } template SPROUT_CONSTEXPR typename std::enable_if< !Left, typename std::iterator_traits::value_type >::type calc(Outdirected const& x) const { return (1 + depth_ * sprout::sin(2 * sprout::math::pi() * rate_ * x.index() / samples_per_sec_ + sprout::math::pi())) * *x; } public: SPROUT_CONSTEXPR auto_pan_outdirected_value( value_type const& depth, value_type const& rate, int_type samples_per_sec = 44100 ) : depth_(depth), rate_(rate), samples_per_sec_(samples_per_sec) {} template SPROUT_CONSTEXPR typename std::iterator_traits::value_type operator()(Outdirected const& x) const { return calc(x); } }; namespace effects { // // auto_pan_holder // template class auto_pan_holder { public: typedef T value_type; typedef IntType int_type; private: value_type depth_; value_type rate_; int_type samples_per_sec_; public: auto_pan_holder() = default; auto_pan_holder(auto_pan_holder const&) = default; SPROUT_CONSTEXPR auto_pan_holder( value_type const& depth, value_type const& rate, int_type samples_per_sec = 44100 ) : depth_(depth), rate_(rate), samples_per_sec_(samples_per_sec) {} SPROUT_CONSTEXPR value_type const& depth() const { return depth_; } SPROUT_CONSTEXPR value_type const& rate() const { return rate_; } SPROUT_CONSTEXPR int_type const& samples_per_sec() const { return samples_per_sec_; } }; // // auto_pan_forwarder // class auto_pan_forwarder { public: template SPROUT_CONSTEXPR sprout::compost::effects::auto_pan_holder operator()(T const& depth, T const& rate, IntType samples_per_sec) { return sprout::compost::effects::auto_pan_holder(depth, rate, samples_per_sec); } template SPROUT_CONSTEXPR sprout::compost::effects::auto_pan_holder operator()(T const& depth, T const& rate) { return sprout::compost::effects::auto_pan_holder(depth, rate); } }; // // auto_pan // namespace { SPROUT_STATIC_CONSTEXPR sprout::compost::effects::auto_pan_forwarder auto_pan = {}; } // anonymous-namespace // // operator| // template inline SPROUT_CONSTEXPR auto operator|(Range&& lhs, sprout::compost::effects::auto_pan_holder const& rhs) -> decltype( sprout::forward(lhs) | sprout::adaptors::indexed | sprout::adaptors::outdirected | sprout::adaptors::transformed( sprout::compost::auto_pan_outdirected_value(rhs.depth(), rhs.rate(), rhs.samples_per_sec()) ) | sprout::compost::formats::stereo( sprout::forward(lhs) | sprout::adaptors::indexed | sprout::adaptors::outdirected | sprout::adaptors::transformed( sprout::compost::auto_pan_outdirected_value(rhs.depth(), rhs.rate(), rhs.samples_per_sec()) ) ) ) { return sprout::forward(lhs) | sprout::adaptors::indexed | sprout::adaptors::outdirected | sprout::adaptors::transformed( sprout::compost::auto_pan_outdirected_value(rhs.depth(), rhs.rate(), rhs.samples_per_sec()) ) | sprout::compost::formats::stereo( sprout::forward(lhs) | sprout::adaptors::indexed | sprout::adaptors::outdirected | sprout::adaptors::transformed( sprout::compost::auto_pan_outdirected_value(rhs.depth(), rhs.rate(), rhs.samples_per_sec()) ) ) ; } } // namespace effects using sprout::compost::effects::auto_pan; } // namespace compost } // namespace sprout #endif // #ifndef SPROUT_COMPOST_EFFECTS_AUTO_PAN_HPP