00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013 #include <uwsim/VirtualCamera.h>
00014 #include <uwsim/UWSimUtils.h>
00015 #include <uwsim/SceneBuilder.h>
00016 #include <iostream>
00017
00018 #include <osg/PositionAttitudeTransform>
00019
00020 class UpdateUnderWater : public osg::Uniform::Callback
00021 {
00022 public:
00023 UpdateUnderWater(osg::Camera* camera) :
00024 mCamera(camera)
00025 {
00026 }
00027 virtual void operator ()(osg::Uniform* u, osg::NodeVisitor*)
00028 {
00029 u->set(true);
00030 }
00031
00032 protected:
00033 osg::Camera* mCamera;
00034 };
00035
00036 class UpdateNoiseSeed : public osg::Uniform::Callback
00037 {
00038 public:
00039 UpdateNoiseSeed()
00040 {
00041 }
00042 virtual void operator ()(osg::Uniform* u, osg::NodeVisitor*)
00043 {
00044 u->set(osg::Vec4f(rand()/(float)RAND_MAX,rand()/(float)RAND_MAX,rand()/(float)RAND_MAX,rand()/(float)RAND_MAX));
00045 }
00046
00047 protected:
00048 };
00049
00050 class UpdateEye : public osg::Uniform::Callback
00051 {
00052 public:
00053 UpdateEye(osg::Camera* camera) :
00054 mCamera(camera)
00055 {
00056 }
00057 virtual void operator ()(osg::Uniform* u, osg::NodeVisitor*)
00058 {
00059 osg::Vec3d eye, center, up;
00060 mCamera->getViewMatrixAsLookAt(eye, center, up);
00061 u->set(eye);
00062 }
00063
00064 protected:
00065 osg::Camera* mCamera;
00066 };
00067
00068 class UpdateVMI : public osg::Uniform::Callback
00069 {
00070 public:
00071 UpdateVMI(osg::Camera* camera) :
00072 mCamera(camera)
00073 {
00074 }
00075 virtual void operator ()(osg::Uniform* u, osg::NodeVisitor*)
00076 {
00077 u->set(mCamera->getInverseViewMatrix());
00078 }
00079
00080 protected:
00081 osg::Camera* mCamera;
00082 };
00083
00084 VirtualCamera::VirtualCamera()
00085 {
00086 }
00087
00088 void VirtualCamera::init(osg::Group *uwsim_root, std::string name, std::string parentName, osg::Node *trackNode, int width,
00089 int height, double baseline, std::string frameId, Parameters *params, int range, double fov,
00090 double aspectRatio, double near, double far, int bw, int widget, SceneBuilder *oscene, float std)
00091 {
00092 this->uwsim_root = uwsim_root;
00093 this->name = name;
00094 this->parentLinkName=parentName;
00095 this->std=std;
00096
00097 this->trackNode = trackNode;
00098
00099 osg::ref_ptr < osg::Node > axis = UWSimGeometry::createSwitchableFrame();
00100
00101 axis->asGroup()->addChild(UWSimGeometry::createLabel(name));
00102 this->trackNode->asGroup()->addChild(axis);
00103
00104 this->width = width;
00105 this->height = height;
00106 this->baseline = baseline;
00107 this->frameId = frameId;
00108 this->fov = fov;
00109 this->aspectRatio = aspectRatio;
00110 this->near = near;
00111 this->far = far;
00112 if (params != NULL)
00113 {
00114 this->fx = params->fx;
00115 this->fy = params->fy;
00116 this->far = params->f;
00117 this->near = params->n;
00118 this->cx = params->x0;
00119 this->cy = params->y0;
00120 this->k = params->k;
00121 this->paramsOn = 1;
00122 }
00123 else
00124 this->paramsOn = 0;
00125 this->range = range;
00126 this->bw = bw;
00127 this->widget = widget;
00128
00129 if (!range)
00130 {
00131 renderTexture = new osg::Image();
00132 renderTexture->allocateImage(width, height, 1, GL_RGB, GL_UNSIGNED_BYTE);
00133 }
00134 else
00135 {
00136 depthTexture = new osg::Image();
00137 depthTexture->allocateImage(width, height, 1, GL_DEPTH_COMPONENT, GL_FLOAT);
00138 }
00139
00140 createCamera();
00141
00142 if(oscene)
00143 textureCamera->setCullMask(~oscene->scene->getOceanScene()->getARMask());
00144 loadShaders(oscene);
00145 }
00146
00147 VirtualCamera::VirtualCamera(osg::Group *uwsim_root, std::string name,std::string parentName, osg::Node *trackNode, int width,
00148 double fov, double range)
00149 {
00150
00151 init(uwsim_root, name, parentName, trackNode, 1, width, 0.0, "", NULL, 1, fov, 1.0 / width, 0.8, range * 1.2, 0, 0,NULL,0);
00152
00153 }
00154
00155 VirtualCamera::VirtualCamera(osg::Group *uwsim_root, std::string name,std::string parentName, osg::Node *trackNode, int width,
00156 int height, double fov, double aspectRatio)
00157 {
00158 init(uwsim_root, name, parentName, trackNode, width, height, 0.0, "", NULL, 1, fov, aspectRatio, 0.1, 20, 0, 0,NULL,0);
00159 }
00160
00161 VirtualCamera::VirtualCamera(osg::Group *uwsim_root, std::string name,std::string parentName, osg::Node *trackNode, int width,
00162 int height,double baseline, std::string frameId,double fov,SceneBuilder *oscene,float std, Parameters *params=NULL, int range=0, int bw=0)
00163 {
00164 init(uwsim_root, name, parentName, trackNode, width, height, baseline, frameId, params, range, fov, width/(float)height, 0.18, 20, bw, 1,oscene,std);
00165 }
00166
00167 void VirtualCamera::createCamera()
00168 {
00169 textureCamera = new osg::Camera;
00170 textureCamera->setReferenceFrame(osg::Transform::ABSOLUTE_RF);
00171 textureCamera->setClearMask(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
00172 textureCamera->setViewport(0, 0, width, height);
00173
00174
00175 textureCamera->setRenderTargetImplementation(osg::Camera::FRAME_BUFFER_OBJECT);
00176
00177
00178 textureCamera->setRenderOrder(osg::Camera::PRE_RENDER);
00179
00180
00181 if (!range)
00182 textureCamera->attach(osg::Camera::COLOR_BUFFER, renderTexture.get());
00183 else
00184 textureCamera->attach(osg::Camera::DEPTH_BUFFER, depthTexture.get());
00185
00186 textureCamera->setName("CamViewCamera");
00187 textureCamera->setComputeNearFarMode(osg::CullSettings::DO_NOT_COMPUTE_NEAR_FAR);
00188
00189 if (!paramsOn)
00190 {
00191
00192 textureCamera->setProjectionMatrixAsPerspective(fov, aspectRatio, near, far);
00193 osg::Matrixd m;
00194 m = textureCamera->getProjectionMatrix();
00195 fx = m(0, 0) * width / 2.0;
00196 fy = m(1, 1) * height / 2.0;
00197 cx = -(m(0, 2) - 1) * width / 2.0;
00198 cy = -(m(1, 2) - 1) * height / 2.0;
00199 }
00200 else
00201 {
00202
00203
00204
00205
00206
00207
00208
00209 osg::Matrixd m(2.0 * fx / width, 0, 0, 0, 2.0 * k / width, 2.0 * fy / height, 0, 0, 1 - (2 * cx / width),
00210 1 - (2.0 * cy / height), (far + near) / (near - far), -1, 0, 0, 2 * far * near / (near - far), 0);
00211 textureCamera->setProjectionMatrix(m);
00212
00213 }
00214
00215 Tx = (-fx * baseline);
00216 Ty = 0.0;
00217
00218 node_tracker = new MyNodeTrackerCallback(uwsim_root, depthTexture, textureCamera);
00219 trackNode->setEventCallback(node_tracker);
00220
00221
00222 osg::Uniform* u = new osg::Uniform("osgOcean_EyeUnderwater", true);
00223 u->setUpdateCallback(new UpdateUnderWater(textureCamera));
00224
00225 textureCamera->getOrCreateStateSet()->addUniform(u);
00226 osg::Vec3d eye, center, up;
00227 textureCamera->getViewMatrixAsLookAt(eye, center, up);
00228 osg::Uniform* u2 = new osg::Uniform("osgOcean_Eye", eye);
00229 u2->setUpdateCallback(new UpdateEye(textureCamera));
00230 textureCamera->getOrCreateStateSet()->addUniform(u2);
00231
00232 osg::Uniform* u3 = new osg::Uniform("osg_ViewMatrixInverse", textureCamera->getInverseViewMatrix());
00233 u3->setUpdateCallback(new UpdateVMI(textureCamera));
00234 textureCamera->getOrCreateStateSet()->addUniform(u3);
00235 }
00236
00237 void VirtualCamera::loadShaders(SceneBuilder *oscene)
00238 {
00239
00240 if(oscene)
00241 {
00242 static const char model_vertex[] = "default_scene.vert";
00243 static const char model_fragment[] = "default_scene.frag";
00244 osg::Program* program = osgOcean::ShaderManager::instance().createProgram("object_shader", model_vertex,model_fragment, "", "");
00245
00246 textureCamera->getOrCreateStateSet()->setAttributeAndModes(program, osg::StateAttribute::ON);
00247
00248 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_EnableGlare", oscene->scene->getOceanScene()->isGlareEnabled()) );
00249 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_EnableUnderwaterScattering", oscene->scene->getOceanScene()->isUnderwaterScatteringEnabled()) );
00250 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_EnableDOF", oscene->scene->getOceanScene()->isUnderwaterDOFEnabled()) );
00251
00252 float UWFogDensity= oscene->scene->getOceanScene()->getUnderwaterFogDensity();
00253 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_UnderwaterFogDensity", -UWFogDensity*UWFogDensity*1.442695f) );
00254 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_UnderwaterFogColor", oscene->scene->getOceanScene()->getUnderwaterFogColor() ) );
00255
00256 float AWFogDensity= oscene->scene->getOceanScene()->getAboveWaterFogDensity();
00257 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_AboveWaterFogDensity", -AWFogDensity*AWFogDensity*1.442695f ) );
00258 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_AboveWaterFogColor", oscene->scene->getOceanScene()->getAboveWaterFogColor() ) );
00259
00260 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_DOF_Near", oscene->scene->getOceanScene()->getDOFNear() ) );
00261 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_DOF_Far", oscene->scene->getOceanScene()->getDOFFar() ) );
00262 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_DOF_Focus", oscene->scene->getOceanScene()->getDOFFocalDistance() ) );
00263 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_DOF_Clamp", oscene->scene->getOceanScene()->getDOFFarClamp() ) );
00264
00265 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_WaterHeight", float(oscene->scene->getOceanScene()->getOceanSurfaceHeight()) ) );
00266
00267 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_UnderwaterAttenuation", oscene->scene->getOceanScene()->getUnderwaterAttenuation() ) );
00268 textureCamera->getStateSet()->addUniform( new osg::Uniform("osgOcean_UnderwaterDiffuse", oscene->scene->getOceanScene()->getUnderwaterDiffuse() ) );
00269
00270
00271
00272
00273
00274
00275 osg::Uniform* u = new osg::Uniform("offsets", osg::Vec4f(1,2,3,4));
00276 u->setUpdateCallback(new UpdateNoiseSeed());
00277 textureCamera->getStateSet()->addUniform(u);
00278
00279 textureCamera->getStateSet()->addUniform( new osg::Uniform("stddev", std ) );
00280 textureCamera->getStateSet()->addUniform( new osg::Uniform("mean", 0.0f ) );
00281
00282 }
00283 else
00284 {
00285 textureCamera->getOrCreateStateSet()->setAttributeAndModes(new osg::Program(), osg::StateAttribute::ON);
00286 }
00287 }
00288
00289 osg::ref_ptr<osgWidget::Window> VirtualCamera::getWidgetWindow()
00290 {
00291 osg::ref_ptr < osgWidget::Box > box = new osgWidget::Box("VirtualCameraBox", osgWidget::Box::HORIZONTAL, true);
00292 osg::ref_ptr < osgWidget::Widget > widget = new osgWidget::Widget("VirtualCameraWidget", width, height);
00293 if (!range)
00294 widget->setImage(renderTexture.get(), true, false);
00295 else
00296 widget->setImage(depthTexture.get(), true, false);
00297 box->addWidget(widget.get());
00298 box->getBackground()->setColor(1.0f, 0.0f, 0.0f, 0.8f);
00299 box->attachMoveCallback();
00300 box->attachScaleCallback();
00301 return box;
00302 }
00303
00304 int VirtualCamera::getTFTransform(tf::Pose & pose, std::string & parent){
00305 parent=parentLinkName;
00306 pose.setOrigin(tf::Vector3(trackNode->asTransform()->asPositionAttitudeTransform()->getPosition().x(),
00307 trackNode->asTransform()->asPositionAttitudeTransform()->getPosition().y(),
00308 trackNode->asTransform()->asPositionAttitudeTransform()->getPosition().z()));
00309 pose.setRotation( tf::Quaternion(trackNode->asTransform()->asPositionAttitudeTransform()->getAttitude().x(),
00310 trackNode->asTransform()->asPositionAttitudeTransform()->getAttitude().y(),
00311 trackNode->asTransform()->asPositionAttitudeTransform()->getAttitude().z(),
00312 trackNode->asTransform()->asPositionAttitudeTransform()->getAttitude().w()));
00313 return 1;
00314
00315 }