404 lines
9.4 KiB
Plaintext
404 lines
9.4 KiB
Plaintext
|
|
%{
|
|
|
|
#include <stdio.h>
|
|
#include <iostream>
|
|
#include "main/Scene.h"
|
|
#include "main/Material.h"
|
|
#include "util/Vector.h"
|
|
#include "util/refptr.h"
|
|
#include "shapes/Shape.h" /* includes all shape types */
|
|
#include "nodes.h"
|
|
#include "parser.h"
|
|
using namespace std;
|
|
|
|
int yylex(void);
|
|
|
|
extern FILE * yyin;
|
|
|
|
void yyerror(const char * str)
|
|
{
|
|
fprintf(stderr, "error: %s\n", str);
|
|
}
|
|
|
|
int yywrap()
|
|
{
|
|
return 1;
|
|
}
|
|
|
|
static Scene * g_scene;
|
|
|
|
%}
|
|
|
|
%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 AMBIENT;
|
|
%token BOX;
|
|
%token CAMERA;
|
|
%token DIFFUSE;
|
|
%token HEIGHT;
|
|
%token INTERSECT;
|
|
%token LIGHT;
|
|
%token LOOKAT;
|
|
%token MATERIAL;
|
|
%token MULTISAMPLE;
|
|
%token OPTIONS;
|
|
%token PLANE;
|
|
%token POSITION;
|
|
%token RADIUS;
|
|
%token REFLECTANCE;
|
|
%token ROTATE;
|
|
%token SCALE;
|
|
%token SCENE;
|
|
%token SHININESS;
|
|
%token SIZE;
|
|
%token SPECULAR;
|
|
%token SPHERE;
|
|
%token SUBTRACT;
|
|
%token TRANSLATE;
|
|
%token UNION;
|
|
%token UP;
|
|
%token VFOV;
|
|
%token WIDTH;
|
|
|
|
%%
|
|
|
|
scene: SCENE LCURLY scene_items RCURLY {
|
|
$$ = new SceneNode();
|
|
$$->addChildren($3);
|
|
}
|
|
;
|
|
|
|
box: BOX LCURLY box_items RCURLY {
|
|
$$ = new BoxNode();
|
|
$$->addChildren($3);
|
|
}
|
|
;
|
|
|
|
box_items: /* empty */
|
|
| box_item box_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
box_item: SIZE vector {
|
|
$$ = new SizeNode($2->getVector());
|
|
}
|
|
| shape_item { $$ = $1; }
|
|
;
|
|
|
|
camera: CAMERA LCURLY camera_items RCURLY {
|
|
Vector default_position(0, -1, 0);
|
|
Vector default_look_at(0, 0, 0);
|
|
Vector default_up(0, 0, 1);
|
|
}
|
|
;
|
|
|
|
camera_items: /* empty */
|
|
| camera_item camera_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
camera_item: POSITION vector {
|
|
$$ = new PositionNode();
|
|
$$->addChild($2);
|
|
}
|
|
| LOOKAT vector {
|
|
$$ = new LookAtNode();
|
|
$$->addChild($2);
|
|
}
|
|
| UP vector {
|
|
$$ = new UpNode();
|
|
$$->addChild($2);
|
|
}
|
|
| VFOV vector {
|
|
$$ = new VFOVNode();
|
|
$$->addChild($2);
|
|
}
|
|
;
|
|
|
|
intersect: INTERSECT LCURLY shape shape shape_items RCURLY {
|
|
$$ = new IntersectNode();
|
|
$$->addChild($3);
|
|
$$->addChild($4);
|
|
$$->addChildren($5);
|
|
}
|
|
;
|
|
|
|
light: LIGHT LCURLY light_items RCURLY {
|
|
$$ = new LightNode();
|
|
$$->addChildren($3);
|
|
}
|
|
;
|
|
|
|
light_items: /* empty */
|
|
| light_item light_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
light_item: POSITION vector {
|
|
$$ = new PositionNode();
|
|
$$->addChild($2);
|
|
}
|
|
| DIFFUSE vector {
|
|
$$ = new DiffuseNode();
|
|
$$->addChild($2);
|
|
}
|
|
| SPECULAR vector {
|
|
$$ = new SpecularNode();
|
|
$$->addChild($2);
|
|
}
|
|
;
|
|
|
|
material: MATERIAL LCURLY material_items RCURLY {
|
|
$$ = new MaterialNode();
|
|
$$->addChildren($3);
|
|
}
|
|
;
|
|
|
|
material_items: /* empty */
|
|
| material_item material_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
material_item: AMBIENT vector {
|
|
$$ = new AmbientNode();
|
|
$$->addChild($2);
|
|
}
|
|
| DIFFUSE vector {
|
|
$$ = new DiffuseNode();
|
|
$$->addChild($2);
|
|
}
|
|
| SPECULAR vector {
|
|
$$ = new SpecularNode();
|
|
$$->addChild($2);
|
|
}
|
|
| REFLECTANCE number {
|
|
$$ = new ReflectanceNode($2->getNumber());
|
|
}
|
|
| SHININESS number {
|
|
$$ = new ShininessNode($2->getNumber());
|
|
}
|
|
;
|
|
|
|
number: DEC_NUMBER { $$ = $1; }
|
|
| REAL_NUMBER { $$ = $1; }
|
|
;
|
|
|
|
options: OPTIONS LCURLY options_items RCURLY {
|
|
$$ = new OptionsNode();
|
|
$$->addChildren($3);
|
|
}
|
|
;
|
|
|
|
options_items: /* empty */
|
|
| options_item options_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
options_item: WIDTH DEC_NUMBER {
|
|
$$ = new WidthNode($2->getInteger());
|
|
}
|
|
| HEIGHT DEC_NUMBER {
|
|
$$ = new HeightNode($2->getInteger());
|
|
}
|
|
| MULTISAMPLE DEC_NUMBER {
|
|
$$ = new MultisampleNode($2->getInteger());
|
|
}
|
|
;
|
|
|
|
plane: PLANE LCURLY plane_items RCURLY {
|
|
$$ = new PlaneNode();
|
|
$$->addChildren($3);
|
|
}
|
|
;
|
|
|
|
plane_items: /* empty */
|
|
| plane_item plane_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
plane_item: POSITION vector COMMA number {
|
|
$$ = new PlanePositionNode($2->getVector(), $4->getNumber());
|
|
}
|
|
| shape_item { $$ = $1; }
|
|
;
|
|
|
|
radius: RADIUS number {
|
|
$$ = new RadiusNode($2->getNumber());
|
|
}
|
|
;
|
|
|
|
scene_items: /* empty */
|
|
| scene_item scene_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
scene_item: camera { $$ = $1; }
|
|
| shape { $$ = $1; }
|
|
| options { $$ = $1; }
|
|
| light { $$ = $1; }
|
|
| transform_block { $$ = $1; }
|
|
;
|
|
|
|
shape: plane { $$ = $1; }
|
|
| sphere { $$ = $1; }
|
|
| box { $$ = $1; }
|
|
| union { $$ = $1; }
|
|
| intersect { $$ = $1; }
|
|
| subtract { $$ = $1; }
|
|
;
|
|
|
|
shape_items: /* empty */
|
|
| shape_item shape_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
shape_item: material { $$ = $1; }
|
|
| transform { $$ = $1; }
|
|
;
|
|
|
|
sphere: SPHERE LCURLY sphere_items RCURLY {
|
|
$$ = new SphereNode();
|
|
$$->addChild($3);
|
|
}
|
|
;
|
|
|
|
sphere_items: /* empty */
|
|
| sphere_item sphere_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
sphere_item: radius { $$ = $1; }
|
|
| shape_item { $$ = $1; }
|
|
;
|
|
|
|
subtract: SUBTRACT LCURLY shape shape shape_items RCURLY {
|
|
$$ = new SubtractNode();
|
|
$$->addChild($3);
|
|
$$->addChild($4);
|
|
$$->addChildren($5);
|
|
}
|
|
;
|
|
|
|
transform: TRANSLATE vector {
|
|
$$ = new TranslateNode($2->getVector());
|
|
}
|
|
| ROTATE number COMMA vector {
|
|
$$ = new RotateNode($2->getNumber(), $4->getVector());
|
|
}
|
|
| SCALE vector {
|
|
$$ = new ScaleNode($2->getVector());
|
|
}
|
|
;
|
|
|
|
transform_block: TRANSLATE vector LCURLY transform_block_items RCURLY {
|
|
$$ = new TranslateBlockNode($2->getVector());
|
|
$$->addChildren($4);
|
|
}
|
|
| ROTATE number COMMA vector LCURLY transform_block_items RCURLY {
|
|
$$ = new RotateBlockNode($2->getNumber(), $4->getVector());
|
|
$$->addChildren($6);
|
|
}
|
|
| SCALE vector LCURLY transform_block_items RCURLY {
|
|
$$ = new ScaleBlockNode($2->getVector());
|
|
$$->addChildren($4);
|
|
}
|
|
;
|
|
|
|
transform_block_items: /* empty */
|
|
| transform_block_item transform_block_items {
|
|
$$ = new ItemsNode();
|
|
$$->addChild($1);
|
|
$$->addChildren($2);
|
|
}
|
|
;
|
|
|
|
transform_block_item: transform_block { $$ = $1; }
|
|
| light { $$ = $1; }
|
|
| shape { $$ = $1; }
|
|
;
|
|
|
|
union: UNION LCURLY shape shape shape_items RCURLY {
|
|
$$ = new UnionNode();
|
|
$$->addChild($3);
|
|
$$->addChild($4);
|
|
$$->addChildren($5);
|
|
}
|
|
;
|
|
|
|
vector: LESS number COMMA number COMMA number GREATER {
|
|
refptr<Vector> vec = new Vector();
|
|
(*vec)[0] = $2->getNumber();
|
|
(*vec)[1] = $4->getNumber();
|
|
(*vec)[2] = $6->getNumber();
|
|
$$ = new VectorNode(vec);
|
|
}
|
|
;
|
|
|
|
%%
|
|
|
|
int Scene::parse(const char * fileName)
|
|
{
|
|
g_scene = this;
|
|
yyin = fopen(fileName, "r");
|
|
if (yyin == NULL)
|
|
{
|
|
cerr << "Failed to open file '" << fileName << "'" << endl;
|
|
return -1;
|
|
}
|
|
yyparse();
|
|
return 0;
|
|
}
|