Sophie

Sophie

distrib > Mandriva > 2010.0 > i586 > media > contrib-release > by-pkgid > c00aac9511e40e4946e24ea6485133f4 > files > 112

ocaml-glmlite-devel-0.03.35-1mdv2010.0.i586.rpm

open GL
open Glu
open Glut

let b_down = ref false
let anglex = ref (-46)
let angley = ref (-32)
let xold = ref 0
let yold = ref 0
let list_id = ref 0

(* {{{ load datas from file *)

open SExprLite

let map_colors = function
  | (Atom "colors")::lst ->
      let f = float_of_string in
      List.map (function 
          Expr [Atom r; Atom g; Atom b] -> (f r, f g, f b)
        | _ -> failwith "wrong data format"
      ) lst
  | _ -> failwith "wrong data format"
;;

let map_points = function
  | (Atom "points")::lst ->
      let f = float_of_string in
      List.map (function
          Expr [Atom x; Atom y; Atom z] -> (f x, f y, f z)
        | _ -> failwith "wrong data format"
      ) lst
  | _ -> failwith "wrong data format"
;;

let map_faces = function
  | (Atom "faces")::lst ->
      let i = int_of_string in
      List.map (function
          Expr [Atom a; Atom b; Atom c; Atom d] -> (i a, i b, i c, i d)
        | _ -> failwith "wrong data format"
      ) lst
  | _ -> failwith "wrong data format"
;;

let map_contents = function
  [Expr
    [Atom "obj";
     Expr colors;
     Expr points;
     Expr faces]] ->
       let c = map_colors colors
       and p = map_points points
       and f = map_faces faces in
       (Array.of_list c,
        Array.of_list p,
        Array.of_list f)
  | _ ->
      failwith "wrong data format"
;;

let compile_list ~filename =
  let ic = open_in filename in
  let colors, points, faces = map_contents(parse_ic ic) in
  close_in ic;

  glNewList !list_id GL_COMPILE;
    glBegin GL_QUADS;
      Array.iter (fun (a,b,c,d) ->
        let put_point i =
          glColor3v  colors.(i);
          glVertex3v  points.(i);
        in
        put_point a;
        put_point b;
        put_point c;
        put_point d;
      ) faces;
    glEnd();
  glEndList();
;;

(* }}} *)
(* {{{ callback display *)

let display () =
  glClear ~mask:[GL_COLOR_BUFFER_BIT; GL_DEPTH_BUFFER_BIT];

  glLoadIdentity();
  glTranslate ~x:(0.5) ~y:(-0.5) ~z:(-12.0);

  glRotate ~angle:(float(- !angley)) ~x:1.0 ~y:0.0 ~z:0.0;
  glRotate ~angle:(float(- !anglex)) ~x:0.0 ~y:1.0 ~z:0.0;

  glScale ~x:(0.1) ~y:(0.1) ~z:(0.1);

  glCallList !list_id;

  glFlush();
  glutSwapBuffers();
;;
(* }}} *)
(* {{{ callback reshape *)

let reshape ~width ~height =
  glMatrixMode GL_PROJECTION;
  glLoadIdentity();
  gluPerspective 30. (float width /. float height) 2. 30.;
  glViewport 0 0 width height;
  glMatrixMode GL_MODELVIEW;
  glutPostRedisplay();
;;
(* }}} *)
(* {{{ callback keyboard *)

let keyboard ~key ~x ~y =
  match key with
  | 'e' -> Printf.printf " %d %d\n%!" !anglex !angley;
  | 'p' -> glPolygonMode GL_FRONT_AND_BACK  GL_FILL;  glutPostRedisplay();
  | 'f' -> glPolygonMode GL_FRONT_AND_BACK  GL_LINE;  glutPostRedisplay();
  | 's' -> glPolygonMode GL_FRONT_AND_BACK  GL_POINT; glutPostRedisplay();
  | 'd' -> glEnable GL_DEPTH_TEST; glutPostRedisplay();
  | 'D' -> glDisable GL_DEPTH_TEST; glutPostRedisplay();
  | 'm' -> 
        (*
        let m = glGetMatrix Get.GL_PROJECTION_MATRIX in
        glLoadIdentity();
        *)
        let m = glGetMatrix Get.GL_MODELVIEW_MATRIX in
        Printf.printf
          " %f  %f  %f  %f\n \
            %f  %f  %f  %f\n \
            %f  %f  %f  %f\n \
            %f  %f  %f  %f\n%!" 
            m.(0).(0)  m.(0).(1)  m.(0).(2)  m.(0).(3)
            m.(1).(0)  m.(1).(1)  m.(1).(2)  m.(1).(3)
            m.(2).(0)  m.(2).(1)  m.(2).(2)  m.(2).(3)
            m.(3).(0)  m.(3).(1)  m.(3).(2)  m.(3).(3);
      (*
      let mats = [
        Get.GL_COLOR_MATRIX;
        Get.GL_MODELVIEW_MATRIX;
        Get.GL_PROJECTION_MATRIX;
        Get.GL_TEXTURE_MATRIX ] in
      List.iter (fun _m ->
        let m = glGetMatrix _m in
        Printf.printf
          " %f  %f  %f  %f\n \
            %f  %f  %f  %f\n \
            %f  %f  %f  %f\n \
            %f  %f  %f  %f\n%!" 
            m.(0).(0)  m.(0).(1)  m.(0).(2)  m.(0).(3)
            m.(1).(0)  m.(1).(1)  m.(1).(2)  m.(1).(3)
            m.(2).(0)  m.(2).(1)  m.(2).(2)  m.(2).(3)
            m.(3).(0)  m.(3).(1)  m.(3).(2)  m.(3).(3);
        ) mats;
      *)
  | '\027'
  | 'q' -> exit(0)
  | _ -> ()
;;
(* }}} *)
(* {{{ callback mouse *)

let mouse ~button ~state ~x ~y =
  match button, state with
  (* if we press the left button *)
  | GLUT_LEFT_BUTTON, GLUT_DOWN ->
      b_down := true;
      xold := x;  (* save mouse position *)
      yold := y;
  (* if we release the left button *)
  | GLUT_LEFT_BUTTON, GLUT_UP ->
      b_down := false;
  | _ -> ()
;;
(* }}} *)
(* {{{ callback motion *)

let motion ~x ~y =
  if !b_down then  (* if the left button is down *)
  begin
 (* change the rotation angles according to the last position
    of the mouse and the new one *)
    anglex := !anglex + (!xold - x);
    angley := !angley + (!yold - y);
    glutPostRedisplay();
  end;
  
  xold := x;
  yold := y;
;;
(* }}} *)
(* {{{ main init of GL & Glut *)

let () =
  ignore(glutInit Sys.argv);

  glutInitDisplayMode[GLUT_RGBA; GLUT_DOUBLE; GLUT_DEPTH];
  glutInitWindowPosition ~x:200 ~y:200;
  glutInitWindowSize ~width:640 ~height:480;

  ignore(glutCreateWindow ~title:"demo");

  glPointSize ~size:2.0;
  glClearColor ~r:0.2 ~g:0.3 ~b:0.5 ~a:0.0;

  (* init openGL *)
  glEnable GL_DEPTH_TEST;

  list_id := glGenLists 1;
  compile_list ~filename:"sixa.se";

  (* callback functions *)
  glutDisplayFunc ~display;
  glutReshapeFunc ~reshape;
  glutKeyboardFunc ~keyboard;
  glutMouseFunc ~mouse;
  glutMotionFunc ~motion;

  (* enter the main loop *)
  glutMainLoop();
;;
(* }}} *)

(* vim: sw=2 sts=2 ts=2 et fdm=marker
 *)