diff options
-rw-r--r-- | dimension/common.nonterminals | 2 | ||||
-rw-r--r-- | dimension/common.rules | 13 | ||||
-rw-r--r-- | dimension/common.terminals | 2 | ||||
-rw-r--r-- | dimension/grammar.epilogue | 1 | ||||
-rw-r--r-- | dimension/lexer.l | 1 | ||||
-rw-r--r-- | dimension/parse.h | 1 | ||||
-rw-r--r-- | dimension/realize.c | 25 | ||||
-rw-r--r-- | tests/dimension/demo.pov | 7 | ||||
-rwxr-xr-x | tests/dimension/demo.sh | 9 |
9 files changed, 59 insertions, 2 deletions
diff --git a/dimension/common.nonterminals b/dimension/common.nonterminals index 768e075..9feb03b 100644 --- a/dimension/common.nonterminals +++ b/dimension/common.nonterminals @@ -39,6 +39,8 @@ %type <astnode> FINITE_SOLID_OBJECT %type <astnode> BOX %type <astnode> SPHERE +%type <astnode> INFINITE_SOLID_OBJECT +%type <astnode> PLANE %type <astnode> CSG_OBJECT %type <astnode> UNION %type <astnode> INTERSECTION diff --git a/dimension/common.rules b/dimension/common.rules index c5f9eea..7a6dba1 100644 --- a/dimension/common.rules +++ b/dimension/common.rules @@ -111,6 +111,7 @@ CAMERA_MODIFIER: "angle" FLOAT { /* Objects */ OBJECT: FINITE_SOLID_OBJECT + | INFINITE_SOLID_OBJECT | CSG_OBJECT | LIGHT_SOURCE | "object" "{" @@ -194,6 +195,18 @@ SPHERE: "sphere" "{" } ; +INFINITE_SOLID_OBJECT: PLANE +; + +PLANE: "plane" "{" + VECTOR "," FLOAT + OBJECT_MODIFIERS + "}" + { + $$ = dmnsn_new_astnode3(DMNSN_AST_PLANE, @$, $3, $5, $6); + } +; + CSG_OBJECT: UNION | INTERSECTION | DIFFERENCE diff --git a/dimension/common.terminals b/dimension/common.terminals index 4458af3..c125489 100644 --- a/dimension/common.terminals +++ b/dimension/common.terminals @@ -335,7 +335,7 @@ %token DMNSN_T_PIGMENT_MAP %token DMNSN_T_PIGMENT_PATTERN %token DMNSN_T_PLANAR -%token DMNSN_T_PLANE +%token DMNSN_T_PLANE "plane" %token DMNSN_T_PNG %token DMNSN_T_POINT_AT %token DMNSN_T_POLY diff --git a/dimension/grammar.epilogue b/dimension/grammar.epilogue index 275e03d..606e9dc 100644 --- a/dimension/grammar.epilogue +++ b/dimension/grammar.epilogue @@ -137,6 +137,7 @@ dmnsn_astnode_string(dmnsn_astnode_type astnode_type) dmnsn_astnode_map(DMNSN_AST_INTERSECTION, "intersection"); dmnsn_astnode_map(DMNSN_AST_LIGHT_SOURCE, "light_source"); dmnsn_astnode_map(DMNSN_AST_MERGE, "merge"); + dmnsn_astnode_map(DMNSN_AST_PLANE, "plane"); dmnsn_astnode_map(DMNSN_AST_SPHERE, "sphere"); dmnsn_astnode_map(DMNSN_AST_UNION, "union"); diff --git a/dimension/lexer.l b/dimension/lexer.l index cc5fef5..5039bef 100644 --- a/dimension/lexer.l +++ b/dimension/lexer.l @@ -222,6 +222,7 @@ unsigned long wchar; "phong_size" RETURN_TOKEN(DMNSN_T_PHONG_SIZE); "pi" RETURN_TOKEN(DMNSN_T_PI); "pigment" RETURN_TOKEN(DMNSN_T_PIGMENT); +"plane" RETURN_TOKEN(DMNSN_T_PLANE); "pow" RETURN_TOKEN(DMNSN_T_POW); "radians" RETURN_TOKEN(DMNSN_T_RADIANS); "red" RETURN_TOKEN(DMNSN_T_RED); diff --git a/dimension/parse.h b/dimension/parse.h index 64fbf25..7387fbd 100644 --- a/dimension/parse.h +++ b/dimension/parse.h @@ -51,6 +51,7 @@ typedef enum { DMNSN_AST_INTERSECTION, DMNSN_AST_LIGHT_SOURCE, DMNSN_AST_MERGE, + DMNSN_AST_PLANE, DMNSN_AST_SPHERE, DMNSN_AST_UNION, diff --git a/dimension/realize.c b/dimension/realize.c index b5c6066..8ca24cc 100644 --- a/dimension/realize.c +++ b/dimension/realize.c @@ -771,6 +771,28 @@ dmnsn_realize_sphere(dmnsn_astnode astnode) return sphere; } +static dmnsn_object * +dmnsn_realize_plane(dmnsn_astnode astnode) +{ + dmnsn_assert(astnode.type == DMNSN_AST_PLANE, "Expected a plane."); + + dmnsn_astnode normal, distance; + dmnsn_array_get(astnode.children, 0, &normal); + dmnsn_array_get(astnode.children, 1, &distance); + + dmnsn_vector n = dmnsn_vector_normalize(dmnsn_realize_vector(normal)); + double d = dmnsn_realize_float(distance); + + dmnsn_object *plane = dmnsn_new_plane(n); + plane->trans = dmnsn_translation_matrix(dmnsn_vector_mul(d, n)); + + dmnsn_astnode modifiers; + dmnsn_array_get(astnode.children, 2, &modifiers); + dmnsn_realize_object_modifiers(modifiers, plane); + + return plane; +} + typedef dmnsn_object *dmnsn_csg_object_fn(dmnsn_object *a, dmnsn_object *b); /* Generalized CSG realizer */ @@ -857,6 +879,8 @@ dmnsn_realize_object(dmnsn_astnode astnode, dmnsn_array *lights) return dmnsn_realize_intersection(astnode, lights); case DMNSN_AST_MERGE: return dmnsn_realize_merge(astnode, lights); + case DMNSN_AST_PLANE: + return dmnsn_realize_plane(astnode); case DMNSN_AST_SPHERE: return dmnsn_realize_sphere(astnode); case DMNSN_AST_UNION: @@ -925,6 +949,7 @@ dmnsn_realize_astree(const dmnsn_astree *astree) case DMNSN_AST_DIFFERENCE: case DMNSN_AST_INTERSECTION: case DMNSN_AST_MERGE: + case DMNSN_AST_PLANE: case DMNSN_AST_SPHERE: case DMNSN_AST_UNION: object = dmnsn_realize_object(astnode, scene->lights); diff --git a/tests/dimension/demo.pov b/tests/dimension/demo.pov index d14cebb..4f558c5 100644 --- a/tests/dimension/demo.pov +++ b/tests/dimension/demo.pov @@ -70,3 +70,10 @@ difference { } } } + +plane { + y, -2 + pigment { + color rgb 1 + } +} diff --git a/tests/dimension/demo.sh b/tests/dimension/demo.sh index 7e9306a..7691093 100755 --- a/tests/dimension/demo.sh +++ b/tests/dimension/demo.sh @@ -68,7 +68,14 @@ demo_exp=$(echo -n \ (finish (phong (float 0.2)) (phong_size (float 40))))))) - object-modifiers))' \ + object-modifiers) + (plane + (vector (integer 0) (integer 1) (integer 0) (integer 0) (integer 0)) + (integer -2) + (object-modifiers + (pigment + (vector (integer 1) (integer 1) (integer 1) + (integer 0) (integer 0))))))' \ | tr '\n' ' ' | sed -r 's/[[:space:]]+/ /g') if [ "$demo" != "$demo_exp" ]; then |