%{ #include #include #include "main/Scene.h" #include "main/Material.h" #include "util/Vector.h" #include "util/refptr.h" #include "shapes/Shape.h" /* includes all shape types */ using namespace std; extern "C" { int yylex(void); } extern FILE * yyin; extern char * yytext; void yyerror(const char * str) { fprintf(stderr, "error: %s\n", str); } int yywrap() { return 1; } class Node { public: Node(); ~Node(); int type; double * the_double; Material * the_Material; Shape * the_Shape; Vector * the_Vector; }; static Scene * g_scene; #define YYSTYPE refptr %} %token PLUS; %token MINUS; %token STAR; %token DIVIDE; %token MOD; %token SEMICOLON; %token COLON; %token QUESTION; %token DOLLAR; %token DOT; %token DQUOTE; %token SQUOTE; %token COMMA; %token LCURLY; %token RCURLY; %token LBRACKET; %token RBRACKET; %token LPAREN; %token RPAREN; %token LESS; %token GREATER; %token DEC_NUMBER; %token REAL_NUMBER; %token BOX; %token CAMERA; %token COLOR; %token HEIGHT; %token INTERSECT; %token LOOKAT; %token MATERIAL; %token MULTISAMPLE; %token OPTIONS; %token PLANE; %token POSITION; %token REFLECTANCE; %token SCENE; %token SHININESS; %token SIZE; %token SPHERE; %token SUBTRACT; %token UNION; %token UP; %token VFOV; %token WIDTH; %% scene: /* empty */ | scene_spec { printf("Saw a scene\n"); } ; boolean_items: shape shape boolean_items_more ; boolean_items_more: /* empty */ | material boolean_items_more ; box: BOX LPAREN vector RPAREN LCURLY box_items RCURLY ; box_items: shape_items ; camera: CAMERA LCURLY camera_items RCURLY ; camera_items: /* empty */ | camera_item camera_items ; camera_item: POSITION vector { $$ = new Node(); $$->type = POSITION; $$->the_Vector = $2->the_Vector; } | LOOKAT vector { $$ = new Node(); $$->type = LOOKAT; $$->the_Vector = $2->the_Vector; } | UP vector { $$ = new Node(); $$->type = UP; $$->the_Vector = $2->the_Vector; } | VFOV vector { $$ = new Node(); $$->type = VFOV; $$->the_Vector = $2->the_Vector; } ; intersect: INTERSECT LCURLY boolean_items RCURLY ; material: MATERIAL LCURLY material_items RCURLY ; material_items: /* empty */ | material_item material_items ; material_item: COLOR vector { $$ = new Node(); $$->type = COLOR; $$->the_Vector = $2->the_Vector; } | REFLECTANCE number { $$ = new Node(); $$->type = REFLECTANCE; $$->the_double = $2->the_double; } | SHININESS number { $$ = new Node(); $$->type = SHININESS; $$->the_double = $2->the_double; } ; number: DEC_NUMBER { double * ptr = new double; *ptr = atoi(yytext); $$ = new Node(); $$->the_double = ptr; } | REAL_NUMBER { double * ptr = new double; *ptr = atof(yytext); $$ = new Node(); $$->the_double = ptr; } ; plane: PLANE LPAREN vector COMMA number RPAREN LCURLY plane_items RCURLY { Plane * plane = new Plane((*($3->the_Vector))[0], (*($3->the_Vector))[1], (*($3->the_Vector))[2], *($5->the_double)); $$ = new Node(); $$->the_Shape = plane; } ; plane_items: shape_items ; scene_spec: SCENE LCURLY scene_items RCURLY ; scene_items: /* empty */ | scene_item scene_items ; scene_item: camera { $$ = $1; } | shape { $$ = $1; } ; shape: plane { $$ = $1; } | sphere { $$ = $1; } | box { $$ = $1; } | union { $$ = $1; } | intersect { $$ = $1; } | subtract { $$ = $1; } ; shape_items: /* empty */ | material { $$ = $1; } ; sphere: SPHERE LPAREN number RPAREN LCURLY sphere_items RCURLY { Sphere * sphere = new Sphere(*($3->the_double)); $$ = new Node(); $$->the_Shape = sphere; } ; sphere_items: shape_items ; subtract: SUBTRACT LCURLY boolean_items RCURLY ; union: UNION LCURLY boolean_items RCURLY ; vector: LESS number COMMA number COMMA number GREATER { Vector * ptr = new Vector(); (*ptr)[0] = * (double *) $2->the_double; (*ptr)[1] = * (double *) $4->the_double; (*ptr)[2] = * (double *) $6->the_double; $$ = new Node(); $$->the_Vector = ptr; } ; %% int parse(Scene * scene, const char * fileName) { g_scene = scene; yyin = fopen(fileName, "r"); if (yyin == NULL) { cerr << "Failed to open file '" << fileName << "'" << endl; return -1; } yyparse(); } Node::Node() { type = -1; the_double = NULL; the_Material = NULL; the_Shape = NULL; the_Vector = NULL; } Node::~Node() { if (the_double != NULL) delete the_double; if (the_Material != NULL) delete the_Material; if (the_Shape != NULL) delete the_Shape; if (the_Vector != NULL) delete the_Vector; }