sliceview.h

Back to Concrete views

pastel/sys/view/

// Description: SliceView class
// Detail: An adapter view for an (n-1)-dimensional subset
// Documentation: concrete_views.txt

#ifndef PASTELSYS_SLICEVIEW_H
#define PASTELSYS_SLICEVIEW_H

#include "pastel/sys/view/view.h"
#include "pastel/sys/view/sliceviewcursor.h"

namespace Pastel
{

    template <integer N, typename Contained_ConstView>
    class ConstSliceView
    {
    public:
        static constexpr int Dimension = N - 1;

        using Element = typename Contained_ConstView::Element;
        using ConstReference = typename Contained_ConstView::ConstReference;
        typedef SliceView_::ConstSliceViewCursor<N, typename Contained_ConstView::ConstCursor>
            ConstCursor;

        ConstSliceView(
            const Contained_ConstView& view,
            integer fixedIndex,
            integer pivot)
            : view_(view)
            , pivot_(pivot)
            , extent_(shrink(view.extent(), fixedIndex))
            , fixedIndex_(fixedIndex)
        {
            ENSURE2(fixedIndex >= 0 && fixedIndex < N, fixedIndex, N);
            ENSURE2(pivot >= 0 && pivot < view.extent()[fixedIndex], pivot, view.extent()[fixedIndex]);
        }

        const Vector<integer, ModifyN<N, N - 1>::Result>& extent() const
        {
            return extent_;
        }

        ConstCursor constCursor(
            const Vector<integer, ModifyN<N, N - 1>::Result>& position) const
        {
            Vector<integer, N> actualPosition(
                extend(position, pivot_, fixedIndex_));

            return ConstCursor(view_.constCursor(
                actualPosition), fixedIndex_);
        }

    protected:
        Contained_ConstView view_;
        integer pivot_;
        Vector<integer, ModifyN<N, N - 1>::Result> extent_;
        integer fixedIndex_;
    };

    template <integer N, typename Input_Element, typename Input_ConstView>
    ConstView<N - 1, Input_Element, ConstSliceView<N, Input_ConstView> >
        constSliceView(
        const ConstView<N, Input_Element, Input_ConstView>& view,
        integer fixedIndex,
        integer pivot)
    {
        return wrapConstView(
            ConstSliceView<N, Input_ConstView>(view.contained(),
            fixedIndex,
            pivot));
    }

    template <integer N, typename Contained_View>
    class SliceView
        : public ConstSliceView<N, Contained_View>
    {
    private:
        using Base = ConstSliceView<N, Contained_View>;

        using Base::view_;
        using Base::pivot_;
        using Base::fixedIndex_;

    public:
        //using Base::Dimension;
        using ConstCursor = typename Base::ConstCursor;
        using Element = typename Base::Element;
        using Base::extent;
        using Base::constCursor;

        using Reference = typename Contained_View::Reference;
        typedef SliceView_::SliceViewCursor<N, typename Contained_View::Cursor>
            Cursor;

        SliceView(
            const Contained_View& view,
            integer fixedIndex,
            integer pivot)
            : Base(view, fixedIndex, pivot)
        {
            ENSURE2(fixedIndex >= 0 && fixedIndex < N, fixedIndex, N);
            ENSURE2(pivot >= 0 && pivot < view.extent()[fixedIndex], pivot, view.extent()[fixedIndex]);
        }

        Cursor cursor(const Vector<integer, ModifyN<N, N - 1>::Result>& position) const
        {
            Vector<integer, N> actualPosition(
                extend(position, pivot_, fixedIndex_));

            return Cursor(view_.cursor(actualPosition), fixedIndex_);
        }
    };

    template <integer N, typename Input_Element, typename Input_View>
    View<N - 1, Input_Element, SliceView<N, Input_View> > sliceView(
        const View<N, Input_Element, Input_View>& view,
        integer fixedIndex,
        integer pivot)
    {
        return wrapView(SliceView<N, Input_View>(
            view.contained(), fixedIndex, pivot));
    }

}

#endif