理论教育 VegaPrime虚拟现实开发技术:单通道模板效果设计

VegaPrime虚拟现实开发技术:单通道模板效果设计

时间:2023-11-25 理论教育 版权反馈
【摘要】:比如:pChannel_myChannel->setDrawArea;可以设置绘制区域为窗口的中间[0.01,0.99]的区域,四周留下黑色边框,如图9.11.2所示。模板显示效果的核心设计在于通道订阅类的设计。首先,在PublicMember 类里面设计两个静态浮点数,默认值为0.5,表示圆形模板的中心位于绘制区域的中心,用于控制圆形模板的中心位置://圆形模板中心坐标floatPublicMember::drawX=0.5;floatPublicMember::drawY=0.5;图9.11.2设置通道绘制区域效果其次,进行窗口订阅类的设计,其详细代码如图9.11.3所示。

VegaPrime虚拟现实开发技术:单通道模板效果设计

按照模板效果的3个基本要素,前2个要素非常简单,只要记住进行设置即可。

窗口模板效果开关采用如下代码设置即可:

pWindow_myWindow->setNumStencilBits(1);

通道绘制区域设置采用如下代码即可:

pChannel_myChannel->setDrawArea(0.00,1.00,0.00,1.00);

参数值采用了默认设置,也就是表示绘制区域是整个窗口。开发者也可以自己尝试[0,1]的合理值,试试效果。比如:

pChannel_myChannel->setDrawArea(0.01,0.99,0.01,0.99);

可以设置绘制区域为窗口的中间[0.01,0.99]的区域,四周留下黑色边框,如图9.11.2所示。

模板显示效果的核心设计在于通道订阅类的设计。

首先,在PublicMember 类里面设计两个静态浮点数,默认值为0.5,表示圆形模板的中心位于绘制区域的中心,用于控制圆形模板的中心位置:

//圆形模板中心坐标

float PublicMember::drawX=0.5;

float PublicMember::drawY=0.5;

图9.11.2 设置通道绘制区域效果

其次,进行窗口订阅类的设计,其详细代码如图9.11.3所示。

单通道模板效果通道订阅类myChannelStencil 继承于通道订阅类vsChannel::Subscriber,实现原有的两个虚函数。

虚函数 virtual void notify(vsChannel::Event event,const vsChannel *channel,vrDrawContext *context)是主要的功能设计区。这里首先定义了一个模板元素 stencilTestElement,然后在vsChannel::EVENT_PRE_DRAW 事件中处理全部事情,其他事件则不再进行特殊处理。

由于OpenGL 没有直接绘制圆形的函数,就利用静态变量只进行一次赋值的特性,准备了一个包含37个元素的数组,每个元素包含x 和y 两个值,也就是平面上的37个点,这37个点是圆形模板上的37个点,从而通过绘制扇形得到圆形。

然后,设置通道的基本颜色,设置为蓝色:

channel->getVrChannel()->setClearColor(0.0f,0.0f,1.0f,1.0f);

启用通道的绘制上下文

channel->getVrChannel()->apply(context);

接下来,允许重新设置图形状态,并启用其默认值:

context->pushElements(true);

模板效果只对平面起作用,需要设置相关项目:

glDisable(GL_DEPTH_TEST);

glMatrixMode(GL_PROJECTION);

glPushMatrix();

glLoadIdentity();

gluOrtho2D(0.0,1.0,0.0,1.0);

glMatrixMode(GL_MODELVIEW);

glPushMatrix();

glLoadIdentity();

清理模板缓冲区的值,并设置为0:

glClearStencil(0);

glClear(GL_STENCIL_BUFFER_BIT);

设置并启用模板元素值,其他值均被模板值代替:

stencilTestElement.m_enable=true;

stencilTestElement.m_mode=vrStencilTest::MODE_ALWAYS;

stencilTestElement.m_ref=1;

stencilTestElement.m_mask=1;

stencilTestElement.m_fail=vrStencilTest::OPERATION_REPLACE;

stencilTestElement.m_dfail=vrStencilTest::OPERATION_REPLACE;

stencilTestElement.m_dpass=vrStencilTest::OPERATION_REPLACE;

context->setElement(vrStencilTest::Element::Id,&stencilTestElement);//启用模板值

绘制模板显示的形状,这里绘制为圆形:

glBegin(GL_TRIANGLE_FAN);

for (i=0;i<numVertices;i++)(www.daowen.com)

glVertex2f(PublicMember::drawX + vertex[i][0],PublicMember::drawY + vertex[i][1]);

glEnd();

其中的PublicMember::drawX 和PublicMember::drawY 代表圆心位置,默认值为绘制区域中心,后面可以在键盘事件中修改它们的值,以便于控制模板特效的显示位置。

设置并启用模板元素值,在绘制的圆形区域内,场景值得以保持:

context->popElements(false);

stencilTestElement.m_enable=true;

stencilTestElement.m_mode=vrStencilTest::MODE_EQUAL;

stencilTestElement.m_ref=1;

stencilTestElement.m_mask=1;

stencilTestElement.m_fail=vrStencilTest::OPERATION_KEEP;

stencilTestElement.m_dfail=vrStencilTest::OPERATION_KEEP;

stencilTestElement.m_dpass=vrStencilTest::OPERATION_KEEP;

context->setElement(vrStencilTest::Element::Id,&stencilTestElement);

至此,单通道模板效果的设计全部完成,所有设计均在vsChannel::EVENT_PRE_DRAW事件中完成,详细代码如图9.11.3所示。

图9.11.3 单通道模板效果通道订阅类的设计

单通道模板效果设计完成后,还需要在主线程中进行启用,才会有实际效果。为了使用方便,需要预先定义一个通道静态变量PublicMember::MainChannel。整个启用过程是在VP的主线程中配置完成的,主要是为通道事件EVENT_PRE_DRAW 和EVENT_POST_DRAW 添加处理程序。

首先,获取通道,并保存于通道指针中:

PublicMember::MainChannel=vpChannel::find("myChannel");

PublicMember::MainChannel->ref();

其次,实例化一个模板特效通道订阅类:

myChannelStencil *myChStencil=new myChannelStencil();

最后,为通道添加订阅者事件及其处理程序:

当然,在主线程退出时,可以移除订阅者:

详细代码如图9.11.4所示。

图9.11.2 模板通道订阅类在主线程中的使用

运行结果如图9.11.5(a)所示。

在键盘的左移键功能中减小PublicMember::drawX的值,使模板圆形左移,其效果如图9.11.3(b)所示当然,右移与此类似。

在键盘的下移键功能中减小PublicMember::drawY的值,使模板圆形下移,其效果如图9.11.3(d)所示当然,上移与此类似。

图9.11.5 单通道模板效果

为了更好地体现模板效果,需要重新设计键盘函数的功能。这里增加了一个静态float 类型的变量PublicMember::m_magnification,用于控制放大倍数。

放大与缩小效果则放在了字母m 功能之下,PublicMember::m_magnification 默认为1,当其值被修改时,通过修改通道的FOV 角度值实现场景的放大与缩小:

PublicMember::MainChannel->setFOVSymmetric(45.0/PublicMember::m_magnification,-1.0f);

PublicMember::MainChannel ->setLODVisibilityRangeScale(1.0f/ PublicMember::m_ magnification);

键盘函数的详细代码如图9.11.6所示。

图9.11.6 单模板效果的键盘函数

效果如图9.11.5(c)所示,通道的FOV 角度默认为45°,修改PublicMember::m_magnification的值也就能修改通道的FOV 角度,从而实现场景的放大与缩小。

免责声明:以上内容源自网络,版权归原作者所有,如有侵犯您的原创版权请告知,我们将尽快删除相关内容。

我要反馈