X-Git-Url: https://git.mxchange.org/?a=blobdiff_plain;f=src%2FModel%2Fmodel.cxx;h=3f1078cff0da8dd72d7bc533582bac359e3bd03c;hb=9569c43126cd07699a92ce6040c9f1bf52fe2d16;hp=a713ab8346a2f12eeb55efec4382c01d593cba34;hpb=cd041af9d8d601739b334e1f97df7fb00899f984;p=flightgear.git diff --git a/src/Model/model.cxx b/src/Model/model.cxx index a713ab834..3f1078cff 100644 --- a/src/Model/model.cxx +++ b/src/Model/model.cxx @@ -125,6 +125,21 @@ set_translation (sgMat4 &matrix, double position_m, sgVec3 &axis) } +/** + * Make an offset matrix from rotations and position offset. + */ +static void +make_offsets_matrix (sgMat4 * result, double h_rot, double p_rot, double r_rot, + double x_off, double y_off, double z_off) +{ + sgMat4 rot_matrix; + sgMat4 pos_matrix; + sgMakeRotMat4(rot_matrix, h_rot, p_rot, r_rot); + sgMakeTransMat4(pos_matrix, x_off, y_off, z_off); + sgMultMat4(*result, pos_matrix, rot_matrix); +} + + /** * Read an interpolation table from properties. */ @@ -134,7 +149,7 @@ read_interpolation_table (const SGPropertyNode * props) const SGPropertyNode * table_node = props->getNode("interpolation"); if (table_node != 0) { SGInterpTable * table = new SGInterpTable(); - vector entries = table_node->getChildren("entry"); + vector entries = table_node->getChildren("entry"); for (int i = 0; i < entries.size(); i++) table->addEntry(entries[i]->getDoubleValue("ind", 0.0), entries[i]->getDoubleValue("dep", 0.0)); @@ -151,9 +166,7 @@ read_interpolation_table (const SGPropertyNode * props) //////////////////////////////////////////////////////////////////////// FG3DModel::FG3DModel () - : _model(0), - _selector(new ssgSelector), - _position(new ssgTransform) + : _model(0) { } @@ -198,38 +211,26 @@ FG3DModel::init (const string &path) // Set up the alignment node ssgTransform * align = new ssgTransform; align->addKid(_model); - sgMat4 rot_matrix; - sgMat4 off_matrix; sgMat4 res_matrix; - float h_rot = props.getFloatValue("/offsets/heading-deg", 0.0); - float p_rot = props.getFloatValue("/offsets/roll-deg", 0.0); - float r_rot = props.getFloatValue("/offsets/pitch-deg", 0.0); - float x_off = props.getFloatValue("/offsets/x-m", 0.0); - float y_off = props.getFloatValue("/offsets/y-m", 0.0); - float z_off = props.getFloatValue("/offsets/z-m", 0.0); - sgMakeRotMat4(rot_matrix, h_rot, p_rot, r_rot); - sgMakeTransMat4(off_matrix, x_off, y_off, z_off); - sgMultMat4(res_matrix, off_matrix, rot_matrix); + make_offsets_matrix(&res_matrix, + props.getFloatValue("/offsets/heading-deg", 0.0), + props.getFloatValue("/offsets/roll-deg", 0.0), + props.getFloatValue("/offsets/pitch-deg", 0.0), + props.getFloatValue("/offsets/x-m", 0.0), + props.getFloatValue("/offsets/y-m", 0.0), + props.getFloatValue("/offsets/z-m", 0.0)); align->setTransform(res_matrix); - // Set up the position node - _position->addKid(align); - - // Set up the selector node - _selector->addKid(_position); - _selector->clrTraversalMaskBits(SSGTRAV_HOT); - - // Set up a location class - _location = (FGLocation *) new FGLocation; - // Load animations - vector animation_nodes = props.getChildren("animation"); + vector animation_nodes = props.getChildren("animation"); unsigned int i; for (i = 0; i < animation_nodes.size(); i++) { - vector name_nodes = + vector name_nodes = animation_nodes[i]->getChildren("object-name"); if (name_nodes.size() < 1) { Animation * animation = make_animation(0, animation_nodes[i]); + if (animation != 0) + _animations.push_back(animation); } else { for (unsigned int j = 0; j < name_nodes.size(); j++) { Animation * animation = @@ -238,98 +239,39 @@ FG3DModel::init (const string &path) _animations.push_back(animation); } } + } + + // Load sub-models + vector model_nodes = props.getChildren("model"); + for (i = 0; i < model_nodes.size(); i++) { + SGPropertyNode_ptr node = model_nodes[i]; + ssgTransform * align = new ssgTransform; + sgMat4 res_matrix; + make_offsets_matrix(&res_matrix, + node->getFloatValue("offsets/heading-deg", 0.0), + node->getFloatValue("offsets/roll-deg", 0.0), + node->getFloatValue("offsets/pitch-deg", 0.0), + node->getFloatValue("offsets/x-m", 0.0), + node->getFloatValue("offsets/y-m", 0.0), + node->getFloatValue("offsets/z-m", 0.0)); + align->setTransform(res_matrix); + FG3DModel * kid = new FG3DModel; + kid->init(node->getStringValue("path")); + align->addKid(kid->getSceneGraph()); + _model->addKid(align); + _children.push_back(kid); } } void -FG3DModel::update (int dt) +FG3DModel::update (double dt) { unsigned int i; + for (i = 0; i < _children.size(); i++) + _children[i]->update(dt); for (i = 0; i < _animations.size(); i++) _animations[i]->update(dt); - - _location->setPosition( _lon_deg, _lat_deg, _elev_ft ); - _location->setOrientation( _roll_deg, _pitch_deg, _heading_deg ); - - sgMat4 POS; - sgCopyMat4(POS, _location->getTransformMatrix()); - - sgVec3 trans; - sgCopyVec3(trans, _location->get_view_pos()); - - for(i = 0; i < 4; i++) { - float tmp = POS[i][3]; - for( int j=0; j<3; j++ ) { - POS[i][j] += (tmp * trans[j]); - } - } - _position->setTransform(POS); -} - -bool -FG3DModel::getVisible () const -{ - return _selector->getSelect(); -} - -void -FG3DModel::setVisible (bool visible) -{ - _selector->select(visible); -} - -void -FG3DModel::setLongitudeDeg (double lon_deg) -{ - _lon_deg = lon_deg; -} - -void -FG3DModel::setLatitudeDeg (double lat_deg) -{ - _lat_deg = lat_deg; -} - -void -FG3DModel::setElevationFt (double elev_ft) -{ - _elev_ft = elev_ft; -} - -void -FG3DModel::setPosition (double lon_deg, double lat_deg, double elev_ft) -{ - _lon_deg = lon_deg; - _lat_deg = lat_deg; - _elev_ft = elev_ft; -} - -void -FG3DModel::setRollDeg (double roll_deg) -{ - _roll_deg = roll_deg; -} - -void -FG3DModel::setPitchDeg (double pitch_deg) -{ - _pitch_deg = pitch_deg; -} - -void -FG3DModel::setHeadingDeg (double heading_deg) -{ - _heading_deg = heading_deg; -} - -void -FG3DModel::setOrientation (double roll_deg, double pitch_deg, - double heading_deg) -{ - _roll_deg = roll_deg; - _pitch_deg = pitch_deg; - _heading_deg = heading_deg; } FG3DModel::Animation * @@ -369,7 +311,8 @@ FG3DModel::make_animation (const char * object_name, object = _model; } - animation->init(object, node); + if (animation != 0) + animation->init(object, node); return animation; } @@ -412,7 +355,7 @@ FG3DModel::NullAnimation::init (ssgEntity * object, } void -FG3DModel::NullAnimation::update (int dt) +FG3DModel::NullAnimation::update (double dt) { } @@ -445,7 +388,7 @@ FG3DModel::RangeAnimation::init (ssgEntity * object, } void -FG3DModel::RangeAnimation::update (int dt) +FG3DModel::RangeAnimation::update (double dt) { } @@ -477,7 +420,7 @@ FG3DModel::BillboardAnimation::init (ssgEntity * object, } void -FG3DModel::BillboardAnimation::update (int dt) +FG3DModel::BillboardAnimation::update (double dt) { } @@ -512,7 +455,7 @@ FG3DModel::SelectAnimation::init (ssgEntity * object, } void -FG3DModel::SelectAnimation::update (int dt) +FG3DModel::SelectAnimation::update (double dt) { if (_condition != 0 && _condition->test()) _selector->select(0xffff); @@ -559,9 +502,9 @@ FG3DModel::SpinAnimation::init (ssgEntity * object, } void -FG3DModel::SpinAnimation::update (int dt) +FG3DModel::SpinAnimation::update (double dt) { - float velocity_rpms = (_prop->getDoubleValue() * _factor / 60000.0); + float velocity_rpms = (_prop->getDoubleValue() * _factor / 60.0); _position_deg += (dt * velocity_rpms * 360); while (_position_deg < 0) _position_deg += 360.0; @@ -627,7 +570,7 @@ FG3DModel::RotateAnimation::init (ssgEntity * object, } void -FG3DModel::RotateAnimation::update (int dt) +FG3DModel::RotateAnimation::update (double dt) { if (_table == 0) { _position_deg = (_prop->getDoubleValue() + _offset_deg) * _factor; @@ -695,7 +638,7 @@ FG3DModel::TranslateAnimation::init (ssgEntity * object, } void -FG3DModel::TranslateAnimation::update (int dt) +FG3DModel::TranslateAnimation::update (double dt) { if (_table == 0) { _position_m = (_prop->getDoubleValue() + _offset_m) * _factor; @@ -711,4 +654,126 @@ FG3DModel::TranslateAnimation::update (int dt) } + +//////////////////////////////////////////////////////////////////////// +// Implementation of FGModelPlacement. +//////////////////////////////////////////////////////////////////////// + +FGModelPlacement::FGModelPlacement () + : _model(new FG3DModel), + _lon_deg(0), + _lat_deg(0), + _elev_ft(0), + _roll_deg(0), + _pitch_deg(0), + _heading_deg(0), + _selector(new ssgSelector), + _position(new ssgTransform), + _location(new FGLocation) +{ +} + +FGModelPlacement::~FGModelPlacement () +{ + delete _model; + delete _selector; +} + +void +FGModelPlacement::init (const string &path) +{ + _model->init(path); + _position->addKid(_model->getSceneGraph()); + _selector->addKid(_position); + _selector->clrTraversalMaskBits(SSGTRAV_HOT); +} + +void +FGModelPlacement::update (double dt) +{ + _model->update(dt); + + _location->setPosition( _lon_deg, _lat_deg, _elev_ft ); + _location->setOrientation( _roll_deg, _pitch_deg, _heading_deg ); + + sgMat4 POS; + sgCopyMat4(POS, _location->getTransformMatrix()); + + sgVec3 trans; + sgCopyVec3(trans, _location->get_view_pos()); + + for(int i = 0; i < 4; i++) { + float tmp = POS[i][3]; + for( int j=0; j<3; j++ ) { + POS[i][j] += (tmp * trans[j]); + } + } + _position->setTransform(POS); +} + +bool +FGModelPlacement::getVisible () const +{ + return (_selector->getSelect() != 0); +} + +void +FGModelPlacement::setVisible (bool visible) +{ + _selector->select(visible); +} + +void +FGModelPlacement::setLongitudeDeg (double lon_deg) +{ + _lon_deg = lon_deg; +} + +void +FGModelPlacement::setLatitudeDeg (double lat_deg) +{ + _lat_deg = lat_deg; +} + +void +FGModelPlacement::setElevationFt (double elev_ft) +{ + _elev_ft = elev_ft; +} + +void +FGModelPlacement::setPosition (double lon_deg, double lat_deg, double elev_ft) +{ + _lon_deg = lon_deg; + _lat_deg = lat_deg; + _elev_ft = elev_ft; +} + +void +FGModelPlacement::setRollDeg (double roll_deg) +{ + _roll_deg = roll_deg; +} + +void +FGModelPlacement::setPitchDeg (double pitch_deg) +{ + _pitch_deg = pitch_deg; +} + +void +FGModelPlacement::setHeadingDeg (double heading_deg) +{ + _heading_deg = heading_deg; +} + +void +FGModelPlacement::setOrientation (double roll_deg, double pitch_deg, + double heading_deg) +{ + _roll_deg = roll_deg; + _pitch_deg = pitch_deg; + _heading_deg = heading_deg; +} + // end of model.cxx