comparison libinterp/corefcn/gl-render.cc @ 22192:20b225a3ebf8

Update to light (patch #8943) * gl-render.h, gl-render.cc (get_maxlights): New static function. (opengl_renderer::max_lights): New data member. (opengl_renderer::opengl_renderer): Use get_maxlights to initialize max_lights data member. (opengl_renderer::draw_all_lights): New function. Support local light sources. (opengl_renderer::draw_axes_children): Call draw_all_lights instead of doing the work here. (opengl_renderer::draw_surface): Remove warning for "phong". * scripts/plot/draw/light.m: Update docstring. Add and update demos. * doc/interpreter/genpropdoc.m: Update docstring.
author Markus Mützel <markus.muetzel@gmx.de>
date Sat, 23 Jul 2016 17:45:32 +0200
parents 3f5f1234c619
children 553490ffc203
comparison
equal deleted inserted replaced
22191:8971508e21c8 22192:20b225a3ebf8
585 // Dummy class. 585 // Dummy class.
586 }; 586 };
587 587
588 #endif 588 #endif
589 589
590 static int
591 get_maxlights (void)
592 {
593 #if defined (HAVE_OPENGL)
594
595 static int max_lights = 0;
596
597 // Check actual maximum number of lights possible
598 if (max_lights == 0)
599 {
600 for (max_lights = 0; max_lights < GL_MAX_LIGHTS; max_lights++)
601 {
602 glDisable (GL_LIGHT0 + max_lights);
603 if (glGetError ())
604 break;
605 }
606 }
607
608 return max_lights;
609 #else
610
611 err_disabled_feature ("opengl_renderer", "OpenGL");
612
613 #endif
614
615 }
616
590 opengl_renderer::opengl_renderer (void) 617 opengl_renderer::opengl_renderer (void)
591 : toolkit (), xform (), xmin (), xmax (), ymin (), ymax (), 618 : toolkit (), xform (), xmin (), xmax (), ymin (), ymax (),
592 zmin (), zmax (), xZ1 (), xZ2 (), marker_id (), filled_marker_id (), 619 zmin (), zmax (), xZ1 (), xZ2 (), marker_id (), filled_marker_id (),
593 camera_pos (), camera_dir (), interpreter ("none"), txt_renderer () 620 camera_pos (), camera_dir (), interpreter ("none"), txt_renderer ()
594 { 621 {
603 630
604 static bool ok = (sizeof (int) <= sizeof (GLsizei)); 631 static bool ok = (sizeof (int) <= sizeof (GLsizei));
605 632
606 if (! ok) 633 if (! ok)
607 error ("the size of GLsizei is smaller than the size of int"); 634 error ("the size of GLsizei is smaller than the size of int");
635
636 // Check actual maximum number of lights possible
637 max_lights = get_maxlights ();
608 638
609 #else 639 #else
610 640
611 err_disabled_feature ("opengl_renderer", "OpenGL"); 641 err_disabled_feature ("opengl_renderer", "OpenGL");
612 642
1616 else 1646 else
1617 gh_manager::get_object (props.get_zlabel ()).set ("visible", "off"); 1647 gh_manager::get_object (props.get_zlabel ()).set ("visible", "off");
1618 } 1648 }
1619 1649
1620 void 1650 void
1621 opengl_renderer::draw_axes_children (const axes::properties& props) 1651 opengl_renderer::draw_all_lights (const base_properties& props, std::list<graphics_object>& obj_list)
1622 { 1652 {
1623 #if defined (HAVE_OPENGL)
1624
1625 // Children
1626
1627 Matrix children = props.get_all_children (); 1653 Matrix children = props.get_all_children ();
1628 std::list<graphics_object> obj_list;
1629 std::list<graphics_object>::iterator it;
1630
1631 // 1st pass: draw light objects
1632
1633 // Start with the last element of the array of child objects to
1634 // display them in the order they were added to the array.
1635
1636 num_lights = 0;
1637 1654
1638 for (octave_idx_type i = children.numel () - 1; i >= 0; i--) 1655 for (octave_idx_type i = children.numel () - 1; i >= 0; i--)
1639 { 1656 {
1640 graphics_object go = gh_manager::get_object (children(i)); 1657 graphics_object go = gh_manager::get_object (children(i));
1641 1658
1642 if (go.get_properties ().is_visible ()) 1659 if (go.get_properties ().is_visible ())
1643 { 1660 {
1644 if (go.isa ("light")) 1661 if (go.isa ("light"))
1645 { 1662 {
1646 if (num_lights < GL_MAX_LIGHTS) 1663 if (num_lights < max_lights)
1647 { 1664 {
1648 current_light = GL_LIGHT0 + num_lights; 1665 current_light = GL_LIGHT0 + num_lights;
1649 set_clipping (go.get_properties ().is_clipping ()); 1666 set_clipping (go.get_properties ().is_clipping ());
1650 draw (go); 1667 draw (go);
1651 num_lights++; 1668 num_lights++;
1652 } 1669 }
1670 else
1671 warning_with_id ("Octave:max-lights-exceeded",
1672 "light: Maximum number of lights (%d) in these axes is "
1673 "exceeded.", max_lights);
1653 } 1674 }
1675 else if (go.isa ("hggroup"))
1676 draw_all_lights (go.get_properties (), obj_list);
1654 else 1677 else
1655 obj_list.push_back (go); 1678 obj_list.push_back (go);
1656 } 1679 }
1657 } 1680 }
1681 }
1682
1683 void
1684 opengl_renderer::draw_axes_children (const axes::properties& props)
1685 {
1686 #if defined (HAVE_OPENGL)
1687 // list for non-light child objects
1688 std::list<graphics_object> obj_list;
1689 std::list<graphics_object>::iterator it;
1690
1691 // 1st pass: draw light objects
1692
1693 // Start with the last element of the array of child objects to
1694 // display them in the order they were added to the array.
1695
1696 num_lights = 0;
1697 draw_all_lights (props, obj_list);
1658 1698
1659 // disable other OpenGL lights 1699 // disable other OpenGL lights
1660 for (int i = num_lights; i < GL_MAX_LIGHTS; i++) 1700 for (int i = num_lights; i < max_lights; i++)
1661 glDisable (GL_LIGHT0 + i); 1701 glDisable (GL_LIGHT0 + i);
1662 1702
1663 // save camera position and set ambient light color before drawing 1703 // save camera position and set ambient light color before drawing
1664 // other objects 1704 // other objects
1665 view_vector = props.get_cameraposition ().matrix_value (); 1705 view_vector = props.get_cameraposition ().matrix_value ();
1941 const NDArray n = props.get_vertexnormals ().array_value (); 1981 const NDArray n = props.get_vertexnormals ().array_value ();
1942 1982
1943 // FIXME: handle transparency 1983 // FIXME: handle transparency
1944 Matrix a; 1984 Matrix a;
1945 1985
1946 if (props.facelighting_is ("phong") || props.edgelighting_is ("phong"))
1947 warning ("opengl_renderer: phong light model not supported");
1948
1949 int fc_mode = (props.facecolor_is_rgb () ? 0 : 1986 int fc_mode = (props.facecolor_is_rgb () ? 0 :
1950 (props.facecolor_is ("flat") ? 1 : 1987 (props.facecolor_is ("flat") ? 1 :
1951 (props.facecolor_is ("interp") ? 2 : 1988 (props.facecolor_is ("interp") ? 2 :
1952 (props.facecolor_is ("texturemap") ? 3 : -1)))); 1989 (props.facecolor_is ("texturemap") ? 3 : -1))));
1953 int fl_mode = (props.facelighting_is ("none") ? 0 : 1990 int fl_mode = (props.facelighting_is ("none") ? 0 :
2294 { 2331 {
2295 for (int k = 0; k < 3; k++) 2332 for (int k = 0; k < 3; k++)
2296 cb[k] = c(j-1, i, k); 2333 cb[k] = c(j-1, i, k);
2297 glColor3fv (cb); 2334 glColor3fv (cb);
2298 2335
2299 if (fl_mode > 0) 2336 if (el_mode > 0)
2300 { 2337 {
2301 for (int k = 0; k < 3; k++) 2338 for (int k = 0; k < 3; k++)
2302 cb[k] *= as; 2339 cb[k] *= as;
2303 glMaterialfv (LIGHT_MODE, GL_AMBIENT, cb); 2340 glMaterialfv (LIGHT_MODE, GL_AMBIENT, cb);
2304 2341
2321 { 2358 {
2322 for (int k = 0; k < 3; k++) 2359 for (int k = 0; k < 3; k++)
2323 cb[k] = c(j, i, k); 2360 cb[k] = c(j, i, k);
2324 glColor3fv (cb); 2361 glColor3fv (cb);
2325 2362
2326 if (fl_mode > 0) 2363 if (el_mode > 0)
2327 { 2364 {
2328 for (int k = 0; k < 3; k++) 2365 for (int k = 0; k < 3; k++)
2329 cb[k] *= as; 2366 cb[k] *= as;
2330 glMaterialfv (LIGHT_MODE, GL_AMBIENT, cb); 2367 glMaterialfv (LIGHT_MODE, GL_AMBIENT, cb);
2331 2368
2391 { 2428 {
2392 for (int k = 0; k < 3; k++) 2429 for (int k = 0; k < 3; k++)
2393 cb[k] = c(j, i-1, k); 2430 cb[k] = c(j, i-1, k);
2394 glColor3fv (cb); 2431 glColor3fv (cb);
2395 2432
2396 if (fl_mode > 0) 2433 if (el_mode > 0)
2397 { 2434 {
2398 for (int k = 0; k < 3; k++) 2435 for (int k = 0; k < 3; k++)
2399 cb[k] *= as; 2436 cb[k] *= as;
2400 glMaterialfv (LIGHT_MODE, GL_AMBIENT, cb); 2437 glMaterialfv (LIGHT_MODE, GL_AMBIENT, cb);
2401 2438
2418 { 2455 {
2419 for (int k = 0; k < 3; k++) 2456 for (int k = 0; k < 3; k++)
2420 cb[k] = c(j, i, k); 2457 cb[k] = c(j, i, k);
2421 glColor3fv (cb); 2458 glColor3fv (cb);
2422 2459
2423 if (fl_mode > 0) 2460 if (el_mode > 0)
2424 { 2461 {
2425 for (int k = 0; k < 3; k++) 2462 for (int k = 0; k < 3; k++)
2426 cb[k] *= as; 2463 cb[k] *= as;
2427 glMaterialfv (LIGHT_MODE, GL_AMBIENT, cb); 2464 glMaterialfv (LIGHT_MODE, GL_AMBIENT, cb);
2428 2465
3013 3050
3014 // enable light source 3051 // enable light source
3015 glEnable (current_light); 3052 glEnable (current_light);
3016 3053
3017 // light position 3054 // light position
3018 float pos[4] = { 0, 0, 0, 0 }; // X,Y,Z,attenuation 3055 float pos[4] = { 0, 0, 0, 0 }; // X,Y,Z,infinite/local
3019 Matrix lpos = props.get_position ().matrix_value (); 3056 Matrix lpos = props.get_position ().matrix_value ();
3020 for (int i = 0; i < 3; i++) 3057 for (int i = 0; i < 3; i++)
3021 pos[i] = lpos(i); 3058 pos[i] = lpos(i);
3059 if (props.style_is ("local"))
3060 pos[3] = 1;
3022 glLightfv (current_light, GL_POSITION, pos); 3061 glLightfv (current_light, GL_POSITION, pos);
3023 3062
3024 // light color 3063 // light color
3025 float col[4] = { 1, 1, 1, 1 }; // R,G,B,ALPHA (the latter has no meaning) 3064 float col[4] = { 1, 1, 1, 1 }; // R,G,B,ALPHA (the latter has no meaning)
3026 Matrix lcolor = props.get_color ().matrix_value (); 3065 Matrix lcolor = props.get_color ().matrix_value ();