/* -*-c++-*- */
/* osgEarth - Dynamic map generation toolkit for OpenSceneGraph
 * Copyright 2008-2010 Pelican Mapping
 * http://osgearth.org
 *
 * osgEarth is free software; you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>
 */

#ifndef OSGEARTHSYMBOLOGY_SYMBOL_H
#define OSGEARTHSYMBOLOGY_SYMBOL_H 1

#include <osgEarthSymbology/Common>
#include <osgEarth/Config>
#include <osg/Referenced>
#include <vector>

namespace osgEarth { namespace Symbology
{
    /**
     * Abstract base class for all Symbol types.
     */
    class OSGEARTHSYMBOLOGY_EXPORT Symbol : public osg::Referenced
    {
    public:
        Symbol( const Config& conf =Config() );

        const URIContext& uriContext() const { return _uriContext; }

        virtual Config getConfig() const { return Config(); }

    protected:
        URIContext _uriContext;
    };
    typedef std::vector<osg::ref_ptr<Symbol> > SymbolList;

    //--------------------------------------------------------------------
    
    /**
     * Simple drawing parameters for a line.
     */
    class OSGEARTHSYMBOLOGY_EXPORT Stroke
    {
    public:
        enum LineCapStyle {
            LINECAP_DEFAULT,
            LINECAP_BUTT,
            LINECAP_SQUARE,
            LINECAP_ROUND
        };

        enum LineJoinStyle {
            LINEJOIN_DEFAULT
        };

    public:
        Stroke();
        Stroke( float r, float g, float b, float a );
        Stroke( const Config& conf ) { mergeConfig(conf); }

        /** Line color. */
        osg::Vec4f& color() { return _color; }
        const osg::Vec4f& color() const { return _color; }

        /** Capping of line ends. */
        optional<LineCapStyle>& lineCap() { return _lineCap; }
        const optional<LineCapStyle>& lineCap() const { return _lineCap; }

        /** How to render line joints in a LineString. */
        optional<LineJoinStyle>& lineJoin() { return _lineJoin; }
        const optional<LineJoinStyle>& lineJoin() const { return _lineJoin; }

        /** Line rendering width. */
        optional<float>& width() { return _width; }        
        const optional<float>& width() const { return _width; }

        /** Stippling pattern. */
        optional<unsigned short>& stipple() { return _stipple;}
        const optional<unsigned short>& stipple() const { return _stipple; }

    public:
        virtual Config getConfig() const;            
        virtual void mergeConfig( const Config& conf );

    protected:
        osg::Vec4f               _color;
        optional<LineCapStyle>   _lineCap;
        optional<LineJoinStyle>  _lineJoin;
        optional<float>          _width;
        optional<unsigned short> _stipple;
    };

    //--------------------------------------------------------------------

    /**
     * Simple drawing parameters for a filled area.
     */
    class OSGEARTHSYMBOLOGY_EXPORT Fill
    {
    public:
        Fill();
        Fill( float r, float g, float b, float a );
        Fill( const Config& conf ) { mergeConfig(conf); }

        osg::Vec4f& color() { return _color; }
        const osg::Vec4f& color() const { return _color; }

    public:
        virtual Config getConfig() const;
        virtual void mergeConfig( const Config& conf );

    protected:
        osg::Vec4f _color;
    };

} } // namespace osgEarth::Symbology

#endif // OSGEARTH_SYMBOLOGY_SYMBOL_H
