傲劍游戲工作室

   莫等闲、白了少年头,空悲切! - 劒蚩
posts - 29, comments - 185, trackbacks - 0, articles - 0
  IT博客网 :: 首页 :: 新随笔 :: 联系 :: 聚合  :: 管理

Opengl - 使用唯一的颜色ID精确选择物体(转)

Posted on 2007-09-04 15:25 劒蚩 阅读(454) 评论(0)  编辑 收藏 引用 所属分类: Opengl

这是我在国外的一个网站上看到的一篇文章,觉得很不错,以前我所知道的在Opengl中选择物体的方式有2种,一种是用Opengl自带的Select模式,一种是用包围盒来选择物体.这篇文章的方式是用一个唯一的Color ID来代表一个物体,然后根据这个Color来选择物体.DX也同样可以使用这样的方式.

实现的步骤:

  • 关闭Opengl中的纹理,灯光和雾
  • 使用物体定义的唯一Color来渲染这个物体
  • 从后备缓冲数据中读出当前鼠标所在位置的颜色值
  • 找出与读出的颜色值相匹配的物体

这种方法有个问题,在32Bit模式下是完全正确的,在16Bit下会因为颜色丢失的问题而选不中物体,解决方案在这篇文章里:http://www.3dkingdoms.com/selection.html

o_ObjectsTextures.jpg  o_ObjectsColorIDs.jpg

				
						源代码:
class
BaseObject {
private: unsignedchar m_colorID[3]; staticunsignedchar gColorID[3]; public: BaseObject()
{ m_colorID[0] = gColorID[0]; m_colorID[1] = gColorID[1]; m_colorID[2] = gColorID[2]; gColorID[0]++; if(gColorID[0] > 255)
{ gColorID[0] = 0; gColorID[1]++; if(gColorID[1] > 255)
{ gColorID[1] = 0; gColorID[2]++; }
}
} ~BaseObject(){};
};

unsignedchar BaseObject::gColorID[3] = {0, 0, 0};


class SceneObject : public BaseObject {
private: float m_position[3]; string m_name; public: SceneObject(); ~SceneObject(); void Render(); void Picking()
{ // set mesh position glPushMatrix(); glTranslatef(m_position[0], m_position[1], m_position[2]); glColor3f(m_colorID[0]/255.0f, m_colorID[1]/255.0f, m_colorID[2]/255.0f); // render object's vertices here glPopMatrix(); }
};


void MouseDownEvent(int x, int y)
{
// turn off texturing, lighting and fog glDisable(GL_TEXTURE_2D); glDisable(GL_FOG); glDisable(GL_LIGHTING); // render every object in our scene// suppose every object is stored in a list container called SceneObjects list<SceneObject *>::iterator itr = SceneObjects.begin(); while(itr != SceneObjects.end())
{
(*itr)->Picking(); itr++; }


// get color information from framebuffer




unsignedchar pixel[3]; GLint viewport[4]; glGetIntegerv(GL_VIEWPORT, viewport); glReadPixels(x, viewport[3] - y, 1, 1, GL_RGB, GL_UNSIGNED_BYTE, pixel); // now our picked screen pixel color is stored in pixel[3]// so we search through our object list looking for the object that was selected itr = SceneObjects.begin(); while(itr != SceneObjects.end())
{
if((*itr)->m_colorID[0] == pixel[0] && (*itr)->m_colorID[1] == pixel[1] && (*itr)->m_colorID[2] == pixel[2])
{
// flag object as selected SetSelected((*itr); break; } itr++; }
}









原文地址:http://gpwiki.org/index.php/OpenGL_Selection_Using_Unique_Color_IDs



标题  
姓名  
主页
验证码 *
内容(提交失败后,可以通过“恢复上次提交”恢复刚刚提交的内容)
 
  登录  使用高级评论  新用户注册  返回页首  恢复上次提交      
[使用Ctrl+Enter键可以直接提交]
 
相关链接: