Commit 5b0e60e6 authored by Dick Hollenbeck's avatar Dick Hollenbeck
Browse files

more free software, sweet parser nearing completion

parent 137d1329
Loading
Loading
Loading
Loading
+57 B (20.6 KiB)

File changed.

No diff preview for this file type.

+59 −12
Original line number Original line Diff line number Diff line
@@ -8,17 +8,58 @@ PARTS="eyes ears feet"


REVS="rev1 rev5 rev10"
REVS="rev1 rev5 rev10"


LINE="(line (pts (xy 12 13)(xy 12 20))(line_width 1.5))"
RECT="(rectangle (start 4 5)(end 6 8)(line_width 2.3)(fill transparent))"
CIRCLE="(circle (center 1 0)(radius 5)(line_width 2.1)(fill none))"
ARC="(arc (pos 22 33)(radius 12)(start 2 4)(end 13 33)(line_width 2.3)(fill filled))"
BEZIER="(bezier (fill none)(line_width 2.0)(pts (xy 0 1)(xy 2 4)))"
TEXT="(text \"This is some text\" (at 23 23 90.0)(justify left bottom)(visible yes)(fill filled))"


PIN="(pin input line (at 7 8 90.0)(length 2)(visible YES))"
REFERENCE="
# add to pin
    (reference U
#            (name NAME (font [FONT] (size HEIGHT WIDTH) [ITALIC] [BOLD])(visible YES))
        (effects (at 12 13 180)(font (size .7 1))(visible yes))
#            (number NUMBER (font [FONT] (size HEIGHT WIDTH) [ITALIC] [BOLD] (visible YES))
    )"

LINE="
    (line
        (pts (xy 12 13)(xy 12 20))(line_width 1.5)
    )"

RECT="
    (rectangle
        (start 4 5)(end 6 8)(line_width 2.3)(fill transparent)
    )"

CIRCLE="
    (circle
        (center 1 0)(radius 5)(line_width 2.1)(fill none)
    )"

ARC="
    (arc
        (pos 22 33)(radius 12)(start 2 4)(end 13 33)(line_width 2.3)(fill filled)
    )"

BEZIER="
    (bezier
        (fill none)(line_width 2.0)(pts (xy 0 1)(xy 2 4))
    )"

TEXT="
    (text \"This is some text\" (at 23 23 90.0)(justify left bottom)(visible yes)(fill filled)
        (font arial (size .8 1.2))
    )"

PIN1="
    (pin output line (at 7 8 90)(length 2)(visible yes)
        (signal #WE  (font  (size 0.9 1.1) bold)(visible yes))
        (padname A23 (font (size 0.9 1.1) italic bold) (visible yes))
    )"

PIN2="
    (pin input line (at 8 8)(length 2)(visible yes)
        (signal #WAIT  (font  (size 0.9 1.1) bold)(visible yes))
        (padname A24 (font (size 0.9 1.1) italic bold) (visible yes))
    )"

PROP1="
    (property mWatts 12
        (effects (at 1 34 270)(font (size .5 1) italic bold)(visible no))
    )"




for C in ${CATEGORIES}; do
for C in ${CATEGORIES}; do
@@ -28,24 +69,30 @@ for C in ${CATEGORIES}; do
    for P in ${PARTS};  do
    for P in ${PARTS};  do
        for R in ${REVS}; do
        for R in ${REVS}; do
            echo "(part $C/$P (value 22)(footprint SM0805)(model Airplane)
            echo "(part $C/$P (value 22)(footprint SM0805)(model Airplane)
                $REFERENCE
                $LINE
                $LINE
                $RECT
                $RECT
                $CIRCLE
                $CIRCLE
                $ARC
                $ARC
                $BEZIER
                $BEZIER
                $TEXT
                $TEXT
                $PIN
                $PIN1
                $PIN2
                $PROP1
                )" > $BASEDIR/$C/$P.part.$R
                )" > $BASEDIR/$C/$P.part.$R
        done
        done
        # also make the part without a rev:
        # also make the part without a rev:
        echo "(part $C/$P (value 22)(footprint SM0805)(model Airplane)
        echo "(part $C/$P (value 22)(footprint SM0805)(model Airplane)
            $REFERENCE
            $LINE
            $LINE
            $RECT
            $RECT
            $CIRCLE
            $CIRCLE
            $ARC
            $ARC
            $BEZIER
            $BEZIER
            $TEXT
            $TEXT
            $PIN
            $PIN1
            $PIN2
            $PROP1
            )" > $BASEDIR/$C/$P.part
            )" > $BASEDIR/$C/$P.part
    done
    done
done
done
+11 −2
Original line number Original line Diff line number Diff line
@@ -38,7 +38,12 @@ PART::PART( LIB* aOwner, const STRING& aPartNameAndRev ) :
    contains( 0 ),
    contains( 0 ),
    partNameAndRev( aPartNameAndRev ),
    partNameAndRev( aPartNameAndRev ),
    extends( 0 ),
    extends( 0 ),
    base( 0 )
    base( 0 ),
    reference(  this, wxT( "reference " ) ),
    value(      this, wxT( "value" ) ),
    footprint(  this, wxT( "footprint" ) ),
    model(      this, wxT( "model" ) ),
    datasheet(  this, wxT( "datasheet" ) )
{
{
    // Our goal is to have class LIB only instantiate what is needed, so print here
    // Our goal is to have class LIB only instantiate what is needed, so print here
    // what it is doing. It is the only class where PART can be instantiated.
    // what it is doing. It is the only class where PART can be instantiated.
@@ -64,7 +69,11 @@ void PART::clear()
        delete *it;
        delete *it;
    pins.clear();
    pins.clear();


    // @todo delete all properties
    // delete non-mandatory properties I own, since their container will not destroy them:
    for( PROPERTIES::iterator it = properties.begin();  it != properties.end();  ++it )
        delete *it;
    properties.clear();

}
}




+94 −29
Original line number Original line Diff line number Diff line
@@ -41,6 +41,7 @@ namespace SCH {


class PART;
class PART;
class SWEET_PARSER;
class SWEET_PARSER;
class PROPERTY;


};
};


@@ -57,10 +58,12 @@ public:
    {}
    {}
};
};


typedef float   ANGLE;



namespace SCH {
namespace SCH {


class GR_FONT
class FONT
{
{
    friend class PART;
    friend class PART;
    friend class SWEET_PARSER;
    friend class SWEET_PARSER;
@@ -72,12 +75,31 @@ protected:
    bool            bold;
    bool            bold;


public:
public:
    GR_FONT() :
    FONT() :
        italic( false ),
        italic( false ),
        bold( false )
        bold( false )
    {}
    {}
};
};



struct TEXT_EFFECTS
{
    POINT       pos;
    ANGLE       angle;
    FONT        font;
    bool        isVisible;

    PROPERTY*   property;       ///< only used from a COMPONENT, specifies PROPERTY in PART
    wxString    propName;       ///< only used from a COMPONENT, specifies PROPERTY in PART

    TEXT_EFFECTS() :
        angle( 0 ),
        isVisible( false ),
        property( 0 )
    {}
};


class BASE_GRAPHIC
class BASE_GRAPHIC
{
{
    friend class PART;
    friend class PART;
@@ -186,13 +208,15 @@ class GR_TEXT : public BASE_GRAPHIC


protected:
protected:
    POINT       pos;
    POINT       pos;
    float       angle;
    ANGLE       angle;

    int         fillType;       ///< T_none, T_filled, or T_transparent
    int         fillType;       ///< T_none, T_filled, or T_transparent
    int         hjustify;       ///< T_center, T_right, or T_left
    int         hjustify;       ///< T_center, T_right, or T_left
    int         vjustify;       ///< T_center, T_top, or T_bottom
    int         vjustify;       ///< T_center, T_top, or T_bottom

    bool        isVisible;
    bool        isVisible;
    wxString    text;
    wxString    text;
//    FONT        font;
    FONT        font;


public:
public:
    GR_TEXT( PART* aOwner ) :
    GR_TEXT( PART* aOwner ) :
@@ -206,36 +230,71 @@ public:
};
};




class PIN : public BASE_GRAPHIC
class PROPERTY : public BASE_GRAPHIC
{
{
    friend class PART;
    friend class PART;
    friend class SWEET_PARSER;
    friend class SWEET_PARSER;


protected:
protected:
    POINT       pos;
    PART*           birthplace;     ///< at which PART in inheritance chain was this PROPERTY added
    float       angle;
    int         connectionType;     ///< T_input, T_output, T_bidirectional, T_tristate, T_passive, T_unspecified,
                                    ///< T_power_in, T_power_out, T_open_collector, T_open_emitter, or T_unconnected.
    int         shape;              ///< T_none, T_line, T_inverted, T_clock, T_inverted_clk, T_input_low, T_clock_low,
                                    ///< T_falling_edge, T_non_logic.
    int         length;             ///< length of pin in internal units
    wxString        name;
    wxString        name;
    wxString    number;
    wxString        text;
    bool        nameIsVisible;      ///< name is visible
    TEXT_EFFECTS    effects;
    bool        numIsVisible;       ///< number is visible

    bool        isVisible;          ///< pin is visible
public:
    PROPERTY( PART* aOwner, const wxChar* aName = wxT( "" ) ) :
        BASE_GRAPHIC( aOwner ),
        birthplace( aOwner ),
        name( aName )
    {}
};


struct PINTEXT
{
    wxString    text;
    FONT        font;
    bool        isVisible;

    PINTEXT() :
        isVisible( true )
    {}
};


class PIN : public BASE_GRAPHIC
{
    friend class PART;
    friend class SWEET_PARSER;


public:
public:
    PIN( PART* aOwner ) :
    PIN( PART* aOwner ) :
        BASE_GRAPHIC( aOwner ),
        BASE_GRAPHIC( aOwner ),
        birthplace( aOwner ),
        angle( 0 ),
        angle( 0 ),
        connectionType( PR::T_input ),
        connectionType( PR::T_input ),
        shape( PR::T_line ),
        shape( PR::T_line ),
        length( 0 ),
        length( 0 ),
        nameIsVisible( true ),
        numIsVisible( true ),
        isVisible( true )
        isVisible( true )
    {}
    {}

protected:
    PART*       birthplace;         ///< at which PART in inheritance chain was this PIN added
    POINT       pos;
    ANGLE       angle;

    PINTEXT     padname;
    PINTEXT     signal;

    int         connectionType;     ///< T_input, T_output, T_bidirectional, T_tristate, T_passive, T_unspecified,
                                    ///< T_power_in, T_power_out, T_open_collector, T_open_emitter, or T_unconnected.

    int         shape;              ///< T_none, T_line, T_inverted, T_clock, T_inverted_clk, T_input_low, T_clock_low,
                                    ///< T_falling_edge, T_non_logic.

    int         length;             ///< length of pin in internal units
    bool        isVisible;          ///< pin is visible

};
};




@@ -249,6 +308,7 @@ namespace SCH {


typedef std::vector< BASE_GRAPHIC* >    GRAPHICS;
typedef std::vector< BASE_GRAPHIC* >    GRAPHICS;
typedef std::vector< PIN* >             PINS;
typedef std::vector< PIN* >             PINS;
typedef std::vector< PROPERTY* >        PROPERTIES;


class LPID;
class LPID;
class SWEET_PARSER;
class SWEET_PARSER;
@@ -306,12 +366,20 @@ protected: // not likely to have C++ descendants, but protected none-the-le
    /// actually becomes cached in RAM.
    /// actually becomes cached in RAM.
    STRING          body;
    STRING          body;


//    bool        cachedRevisions;    ///< allows lazy loading of revision of this same part name
    // mandatory properties
    PROPERTY        reference;      ///< prefix only, only components have full references
    PROPERTY        value;
    PROPERTY        footprint;
    PROPERTY        model;
    PROPERTY        datasheet;


    // 3 separate lists for speed:
    // separate lists for speed:


    /// A property list.
    /**
    //PROPERTIES    properties;
     * Member properties
     * holds the non-mandatory properties.
     */
    PROPERTIES      properties;


    /**
    /**
     * Member graphics
     * Member graphics
@@ -325,14 +393,9 @@ protected: // not likely to have C++ descendants, but protected none-the-le
     */
     */
    PINS            pins;
    PINS            pins;



    /// Alternate body forms.
    /// Alternate body forms.
    //ALTERNATES  alternates;
    //ALTERNATES  alternates;


    // mandatory properties
    wxString        value;
    wxString        footprint;
    wxString        model;
    wxString        keywords;
    wxString        keywords;




@@ -361,6 +424,7 @@ public:
     */
     */
    void Parse( SWEET_PARSER* aParser, LIB_TABLE* aLibTable ) throw( IO_ERROR, PARSE_ERROR );
    void Parse( SWEET_PARSER* aParser, LIB_TABLE* aLibTable ) throw( IO_ERROR, PARSE_ERROR );


/*
    void SetValue( const wxString& aValue )
    void SetValue( const wxString& aValue )
    {
    {
        value = aValue;
        value = aValue;
@@ -387,6 +451,7 @@ public:
    {
    {
        return model;
        return model;
    }
    }
*/


/*
/*
    void SetBody( const STR_UTF& aSExpression )
    void SetBody( const STR_UTF& aSExpression )
+281 −58
Original line number Original line Diff line number Diff line
@@ -250,14 +250,44 @@ void SWEET_PARSER::Parse( PART* me, LIB_TABLE* aTable ) throw( IO_ERROR, PARSE_E
            parseText( text );
            parseText( text );
            break;
            break;


        // reference in a PART is incomplete, it is just the prefix of an
        // unannotated reference. Only components have full reference designators.
        case T_reference:
            if( contains & PB(REFERENCE) )
                Duplicate( tok );
            contains |= PB(REFERENCE);
            NeedSYMBOLorNUMBER();
            me->reference.text = FromUTF8();
            tok = NextTok();
            if( tok == T_LEFT )
            {
                tok = NextTok();
                if( tok != T_effects )
                    Expecting( T_effects );
                parseTextEffects( &me->reference.effects );
                NeedRIGHT();
            }
            else if( tok != T_RIGHT )
                Expecting( ") | effects" );
            break;

        case T_value:
        case T_value:
            if( contains & PB(VALUE) )
            if( contains & PB(VALUE) )
                Duplicate( tok );
                Duplicate( tok );
            contains |= PB(VALUE);
            contains |= PB(VALUE);
            NeedSYMBOLorNUMBER();
            NeedSYMBOLorNUMBER();
            me->SetValue( FROM_UTF8( CurText() ) );
            me->value.text = FromUTF8();
            // @todo handle optional (effects..) here
            tok = NextTok();
            if( tok == T_LEFT )
            {
                tok = NextTok();
                if( tok != T_effects )
                    Expecting( T_effects );
                parseTextEffects( &me->value.effects );
                NeedRIGHT();
                NeedRIGHT();
            }
            else if( tok != T_RIGHT )
                Expecting( ") | effects" );
            break;
            break;


        case T_footprint:
        case T_footprint:
@@ -265,9 +295,37 @@ void SWEET_PARSER::Parse( PART* me, LIB_TABLE* aTable ) throw( IO_ERROR, PARSE_E
                Duplicate( tok );
                Duplicate( tok );
            contains |= PB(FOOTPRINT);
            contains |= PB(FOOTPRINT);
            NeedSYMBOLorNUMBER();
            NeedSYMBOLorNUMBER();
            me->SetFootprint( FROM_UTF8( CurText() ) );
            me->footprint.text = FromUTF8();
            // @todo handle optional (effects..) here
            tok = NextTok();
            if( tok == T_LEFT )
            {
                tok = NextTok();
                if( tok != T_effects )
                    Expecting( T_effects );
                parseTextEffects( &me->footprint.effects );
                NeedRIGHT();
                NeedRIGHT();
            }
            else if( tok != T_RIGHT )
                Expecting( ") | effects" );
            break;

        case T_datasheet:
            if( contains & PB(MODEL) )
                Duplicate( tok );
            contains |= PB(MODEL);
            NeedSYMBOLorNUMBER();
            me->datasheet.text = FromUTF8();
            tok = NextTok();
            if( tok == T_LEFT )
            {
                tok = NextTok();
                if( tok != T_effects )
                    Expecting( T_effects );
                parseTextEffects( &me->datasheet.effects );
                NeedRIGHT();
            }
            else if( tok != T_RIGHT )
                Expecting( ") | effects" );
            break;
            break;


        case T_model:
        case T_model:
@@ -275,9 +333,40 @@ void SWEET_PARSER::Parse( PART* me, LIB_TABLE* aTable ) throw( IO_ERROR, PARSE_E
                Duplicate( tok );
                Duplicate( tok );
            contains |= PB(MODEL);
            contains |= PB(MODEL);
            NeedSYMBOLorNUMBER();
            NeedSYMBOLorNUMBER();
            me->SetModel( FROM_UTF8( CurText() ) );
            me->model.text = FromUTF8();
            // @todo handle optional (effects..) here
            tok = NextTok();
            if( tok == T_LEFT )
            {
                tok = NextTok();
                if( tok != T_effects )
                    Expecting( T_effects );
                parseTextEffects( &me->model.effects );
                NeedRIGHT();
            }
            else if( tok != T_RIGHT )
                Expecting( ") | effects" );
            break;

        case T_property:
            PROPERTY* property;
            property = new PROPERTY( me );
            // @todo check for uniqueness
            me->properties.push_back( property );
            NeedSYMBOLorNUMBER();
            property->name = FromUTF8();
            NeedSYMBOLorNUMBER();
            property->text = FromUTF8();
            tok = NextTok();
            if( tok == T_LEFT )
            {
                tok = NextTok();
                if( tok != T_effects )
                    Expecting( T_effects );
                parseTextEffects( &property->effects );
                NeedRIGHT();
                NeedRIGHT();
            }
            else if( tok != T_RIGHT )
                Expecting( ") | effects" );
            break;
            break;


        case T_pin:
        case T_pin:
@@ -287,16 +376,15 @@ void SWEET_PARSER::Parse( PART* me, LIB_TABLE* aTable ) throw( IO_ERROR, PARSE_E
            parsePin( pin );
            parsePin( pin );
            break;
            break;



/*
/*
        @todo
        case T_keywords:
        case T_keywords:
            break;
            break;


        case T_alternates:
        case T_alternates:
            break;
            break;


        case T_property:
            break;

        case T_property_del:
        case T_property_del:
            break;
            break;


@@ -316,14 +404,6 @@ void SWEET_PARSER::Parse( PART* me, LIB_TABLE* aTable ) throw( IO_ERROR, PARSE_E
            break;
            break;


*/
*/

        // Not sure about reference in a PART, comes in at COMPONENT object.
        // It is maybe just a hint here or a prefix.
        case T_reference:
            if( contains & PB(REFERENCE) )
                Duplicate( tok );
            contains |= PB(REFERENCE);
            break;
        }
        }
    }
    }


@@ -333,7 +413,7 @@ void SWEET_PARSER::Parse( PART* me, LIB_TABLE* aTable ) throw( IO_ERROR, PARSE_E
}
}




void SWEET_PARSER::parseFont( GR_FONT* me )
void SWEET_PARSER::parseFont( FONT* me )
{
{
    /*
    /*
        # The FONT value needs to be defined.  Currently, EESchema does not support
        # The FONT value needs to be defined.  Currently, EESchema does not support
@@ -344,9 +424,7 @@ void SWEET_PARSER::parseFont( GR_FONT* me )
        (font [FONT] (size HEIGHT WIDTH) [italic] [bold])
        (font [FONT] (size HEIGHT WIDTH) [italic] [bold])
    */
    */



    // handle the [FONT] 'position dependently', i.e. first

    // handle the [FONT] position dependently, i.e. first
    T       tok = NextTok();
    T       tok = NextTok();
    bool    sawBold   = false;
    bool    sawBold   = false;
    bool    sawItalic = false;
    bool    sawItalic = false;
@@ -363,9 +441,10 @@ void SWEET_PARSER::parseFont( GR_FONT* me )
        if( tok == T_LEFT )
        if( tok == T_LEFT )
        {
        {
            tok = NextTok();
            tok = NextTok();
            if( tok != T_size )
                Expecting( T_size );


            switch( tok )
            {
            case T_size:
                if( sawSize )
                if( sawSize )
                    Duplicate( T_size );
                    Duplicate( T_size );
                sawSize = true;
                sawSize = true;
@@ -376,27 +455,33 @@ void SWEET_PARSER::parseFont( GR_FONT* me )
                NeedNUMBER( "size width" );
                NeedNUMBER( "size width" );
                me->size.SetWidth( internal( CurText() ) );
                me->size.SetWidth( internal( CurText() ) );
                NeedRIGHT();
                NeedRIGHT();
                break;

            default:
                Expecting( "size" );
            }
        }
        }
        else
        else
        {
        {
            if( tok == T_bold )
            switch( tok )
            {
            {
            case T_bold:
                if( sawBold )
                if( sawBold )
                    Duplicate( T_bold );
                    Duplicate( T_bold );
                sawBold = true;
                sawBold = true;

                me->bold = true;
                me->bold = true;
            }
                break;
            else if( tok == T_italic )

            {
            case T_italic:
                if( sawItalic )
                if( sawItalic )
                    Duplicate( T_italic );
                    Duplicate( T_italic );
                sawItalic = true;
                sawItalic = true;

                me->italic = true;
                me->italic = true;
                break;

            default:
                Unexpected( "bold|italic" );
            }
            }
            else
                Unexpected( tok );
        }
        }


        tok = NextTok();
        tok = NextTok();
@@ -420,14 +505,69 @@ void SWEET_PARSER::parseBool( bool* aBool )
}
}




void SWEET_PARSER::parsePinText( PINTEXT* me )
{
    /*  either:
        (signal SIGNAL   (font [FONT] (size HEIGHT WIDTH) [italic] [bold])(visible YES))
        or
        (padname PADNAME (font [FONT] (size HEIGHT WIDTH) [italic] [bold])(visible YES))
    */
    T       tok;
    bool    sawFont = false;
    bool    sawVis  = false;

    // padname or signal text
    NeedSYMBOLorNUMBER();
    me->text = FromUTF8();

    while( ( tok = NextTok() ) != T_RIGHT )
    {
        if( tok == T_LEFT )
        {
            tok = NextTok();

            switch( tok )
            {
            case T_font:
                if( sawFont )
                    Duplicate( tok );
                sawFont = true;
                parseFont( &me->font );
                break;

            case T_visible:
                if( sawVis )
                    Duplicate( tok );
                sawVis = true;
                parseBool( &me->isVisible );
                NeedRIGHT();
                break;

            default:
                Expecting( "font" );
            }
        }

        else
        {
            switch( tok )
            {
            default:
                Expecting( T_LEFT );
            }
        }
    }
}


void SWEET_PARSER::parsePin( PIN* me )
void SWEET_PARSER::parsePin( PIN* me )
{
{
    /*
    /*
        (pin TYPE SHAPE
        (pin TYPE SHAPE
            (at X Y [ANGLE])
            (at X Y [ANGLE])
            (length LENGTH)
            (length LENGTH)
            (name NAME (font [FONT] (size HEIGHT WIDTH) [italic] [bold])(visible YES))
            (signal NAME (font [FONT] (size HEIGHT WIDTH) [italic] [bold])(visible YES))
            (number NUMBER (font [FONT] (size HEIGHT WIDTH) [italic] [bold] (visible YES))
            (padname NUMBER (font [FONT] (size HEIGHT WIDTH) [italic] [bold] (visible YES))
            (visible YES)
            (visible YES)
        )
        )
    */
    */
@@ -437,8 +577,8 @@ void SWEET_PARSER::parsePin( PIN* me )
    bool    sawType    = false;
    bool    sawType    = false;
    bool    sawAt      = false;
    bool    sawAt      = false;
    bool    sawLen     = false;
    bool    sawLen     = false;
    bool    sawName  = false;
    bool    sawSignal  = false;
    bool    sawNum   = false;
    bool    sawPadName = false;
    bool    sawVis     = false;
    bool    sawVis     = false;


    while( ( tok = NextTok() ) != T_RIGHT )
    while( ( tok = NextTok() ) != T_RIGHT )
@@ -465,11 +605,19 @@ void SWEET_PARSER::parsePin( PIN* me )
                NeedRIGHT();
                NeedRIGHT();
                break;
                break;


/*          @todo and associated fonts
            case T_signal:
            case T_name:
                if( sawSignal )
            case T_number:
                    Duplicate( tok );
                sawSignal = true;
                parsePinText( &me->signal );
                break;

            case T_padname:
                if( sawPadName )
                    Duplicate( tok );
                sawPadName = true;
                parsePinText( &me->padname );
                break;
                break;
*/


            case T_visible:
            case T_visible:
                if( sawVis )
                if( sawVis )
@@ -528,6 +676,79 @@ void SWEET_PARSER::parsePin( PIN* me )
}
}




void SWEET_PARSER::parseTextEffects( TEXT_EFFECTS* me )
{
    /*
        (effects [PROPERTY]

            # Position requires an X and Y coordinates.  Position coordinates can be
            # non-intergr.  Angle is in degrees and defaults to 0 if not defined.
            (at X Y [ANGLE])

            # The FONT value needs to be defined.  Currently, EESchema does not support
            # different fonts.  In the future this feature may be implemented and at
            # that time FONT will have to be defined.  Initially, only the font size and
            # style are required.  Italic and bold styles are optional.  The font size
            # height and width are in units yet to be determined.
            (font [FONT] (size HEIGHT WIDTH) [italic] [bold])

            # Valid visibility values are yes and no.
            (visible YES)
        )
    */

    bool    sawFont = false;
    bool    sawAt   = false;
    bool    sawVis  = false;

    T       tok = NextTok();

    if( IsSymbol( tok ) )
    {
        me->propName = FromUTF8();
        tok = NextTok();
    }

    while( tok != T_RIGHT )
    {
        if( tok != T_LEFT )
            Expecting( T_LEFT );

        tok = NextTok();

        switch( tok )
        {
        case T_at:
            if( sawAt )
                Duplicate( tok );
            sawAt = true;
            parseAt( &me->pos, &me->angle );
            break;

        case T_font:
            if( sawFont )
                Duplicate( tok );
            sawFont = true;
            parseFont( &me->font );
            break;

        case T_visible:
            if( sawVis )
                Duplicate( sawVis );
            sawVis = true;
            parseBool( &me->isVisible );
            NeedRIGHT();
            break;

        default:
            Expecting( "at|font|visible" );
        }

        tok = NextTok();
    }
}


void SWEET_PARSER::parsePolyLine( POLY_LINE* me )
void SWEET_PARSER::parsePolyLine( POLY_LINE* me )
{
{
    /*
    /*
@@ -1000,8 +1221,10 @@ void SWEET_PARSER::parseText( GR_TEXT* me )
            break;
            break;


        case T_font:
        case T_font:
            // @todo
            if( sawFont )
                Duplicate( tok );
            sawFont = true;
            sawFont = true;
            parseFont( &me->font );
            break;
            break;


        default:
        default:
Loading