diff --git a/src/Airports/GenAirports850/airport.cxx b/src/Airports/GenAirports850/airport.cxx index 4a0fdca2..a9c4ab6b 100644 --- a/src/Airports/GenAirports850/airport.cxx +++ b/src/Airports/GenAirports850/airport.cxx @@ -173,6 +173,97 @@ static TGPolygon rwy_section_tex_coords( const TGPolygon& in_poly, const TGTexPa return result; } +static TGPolygon linear_feature_tex_coords( const TGPolygon& in_poly, const TGTexParams& tp ) +{ + int i, j; + TGPolygon result; + result.erase(); + + Point3D ref = tp.get_ref(); + double width = tp.get_width(); + double length = tp.get_length(); + double heading = tp.get_heading(); + double minu = tp.get_minu(); + double maxu = tp.get_maxu(); + double minv = tp.get_minv(); + double maxv = tp.get_maxv(); + SG_LOG( SG_GENERAL, SG_DEBUG, "section ref = " << ref ); + SG_LOG( SG_GENERAL, SG_DEBUG, " width = " << width ); + SG_LOG( SG_GENERAL, SG_DEBUG, " length = " << length ); + SG_LOG( SG_GENERAL, SG_DEBUG, " heading = " << heading ); + Point3D p, t; + double x, y, tx, ty; + + for ( i = 0; i < in_poly.contours(); ++i ) + { + for ( j = 0; j < in_poly.contour_size( i ); ++j ) + { + p = in_poly.get_pt( i, j ); + SG_LOG(SG_GENERAL, SG_DEBUG, "point = " << p); + + // + // 1. Calculate distance and bearing from the center of + // the feature + // + + // given alt, lat1, lon1, lat2, lon2, calculate starting + // and ending az1, az2 and distance (s). Lat, lon, and + // azimuth are in degrees. distance in meters + double az1, az2, dist; + geo_inverse_wgs_84( 0, ref.y(), ref.x(), p.y(), p.x(), + &az1, &az2, &dist ); + SG_LOG(SG_GENERAL, SG_DEBUG, "basic course = " << az2); + + // + // 2. Rotate this back into a coordinate system where Y + // runs the length of the runway and X runs crossways. + // + + double course = az2 - heading; + while ( course < -360 ) { course += 360; } + while ( course > 360 ) { course -= 360; } + SG_LOG( SG_GENERAL, SG_DEBUG, + " course = " << course << " dist = " << dist ); + + // + // 3. Convert from polar to cartesian coordinates + // + + x = sin( course * SGD_DEGREES_TO_RADIANS ) * dist; + y = cos( course * SGD_DEGREES_TO_RADIANS ) * dist; + SG_LOG(SG_GENERAL, SG_DEBUG, " x = " << x << " y = " << y); + + // + // 4. Map x, y point into texture coordinates + // + double tmp; + + tmp = x / width; + tx = tmp * (maxu - minu) + minu; + SG_LOG(SG_GENERAL, SG_DEBUG, " (" << tx << ")"); + + //if ( tx < 0.0 ) { tx = 0.0; } + //if ( tx > 1.0 ) { tx = 1.0; } + + ty = y / length; + tmp = y / length; + ty = tmp * (maxv - minv) + minv; + + SG_LOG(SG_GENERAL, SG_DEBUG, " (" << ty << ")"); + + //if ( ty < 0.0 ) { ty = 0.0; } + //if ( ty > 1.0 ) { ty = 1.0; } + + t = Point3D( tx, ty, 0 ); + SG_LOG(SG_GENERAL, SG_DEBUG, " (" << tx << ", " << ty << ")"); + + result.add_node( i, t ); + } + } + + return result; +} + // TODO : Add somewhere // Determine node elevations of a point_list based on the provided // TGAptSurface. Offset is added to the final elevation @@ -518,7 +609,14 @@ void Airport::BuildBtg(const string& root, const string_list& elev_src ) SG_LOG(SG_GENERAL, SG_DEBUG, "total size after = " << tri.total_size()); TGPolygon tc; - tc = rwy_section_tex_coords( tri, pvmt_tps[i], false ); + if (pvmt_polys[i].get_flag() == "lf") + { + tc = linear_feature_tex_coords( tri, pvmt_tps[i] ); + } + else + { + tc = rwy_section_tex_coords( tri, pvmt_tps[i], false ); + } pvmt_polys[i].set_tris( tri ); pvmt_polys[i].set_texcoords( tc ); diff --git a/src/Airports/GenAirports850/closedpoly.cxx b/src/Airports/GenAirports850/closedpoly.cxx index ca16d3cd..b8a17d00 100644 --- a/src/Airports/GenAirports850/closedpoly.cxx +++ b/src/Airports/GenAirports850/closedpoly.cxx @@ -65,7 +65,7 @@ void ClosedPoly::AddNode( BezNode* node ) } SG_LOG(SG_GENERAL, SG_DEBUG, " Adding node (" << node->GetLoc().x() << "," << node->GetLoc().y() << ") to current linear feature " << cur_marking); - cur_marking = new LinearFeature(marking_desc /* TODO offset */ ); + cur_marking = new LinearFeature(marking_desc, 1.5f, 0.6f ); } cur_marking->AddNode( node ); } diff --git a/src/Airports/GenAirports850/linearfeature.cxx b/src/Airports/GenAirports850/linearfeature.cxx index b94d79d7..3ad4e4df 100644 --- a/src/Airports/GenAirports850/linearfeature.cxx +++ b/src/Airports/GenAirports850/linearfeature.cxx @@ -350,6 +350,7 @@ int LinearFeature::Finish() double heading; double dist; double az2; + double last_end_v; int i, j; string material; @@ -369,7 +370,12 @@ int LinearFeature::Finish() switch( marks[i]->type ) { case LF_NONE: + break; + case LF_SOLID_YELLOW: + material = "lf_sng_solid_yellow"; + break; + case LF_BROKEN_YELLOW: case LF_SOLID_DBL_YELLOW: case LF_RUNWAY_HOLD: @@ -401,7 +407,7 @@ int LinearFeature::Finish() case LF_OMNIDIR_RED: //material = "gloff_lf_b_solid_yellow"; // material = "pa_lftest"; - material = "pa_tiedown"; + material = "pa_tstlin"; break; default: @@ -409,9 +415,10 @@ int LinearFeature::Finish() exit(1); } + last_end_v = 0.0f; for (j = marks[i]->start_idx; j <= marks[i]->end_idx; j++) { - SG_LOG(SG_GENERAL, SG_ALERT, "LinearFeature::Finish: calculating offsets for mark " << i << " whose start idx is " << marks[i]->start_idx << " and end idx is " << marks[i]->end_idx << " cur idx is " << j ); + SG_LOG(SG_GENERAL, SG_DEBUG, "LinearFeature::Finish: calculating offsets for mark " << i << " whose start idx is " << marks[i]->start_idx << " and end idx is " << marks[i]->end_idx << " cur idx is " << j ); // for each point on the PointsList, generate a quad from // start to next, offset by 2 distnaces from the edge @@ -419,19 +426,19 @@ int LinearFeature::Finish() if (j == marks[i]->start_idx) { // first point on the mark - offset heading is 90deg - cur_outer = OffsetPointFirst( &points[j], &points[j+1], 1.0 ); - cur_inner = OffsetPointFirst( &points[j], &points[j+1], 2.0 ); + cur_outer = OffsetPointFirst( &points[j], &points[j+1], offset-width/2.0f ); + cur_inner = OffsetPointFirst( &points[j], &points[j+1], offset+width/2.0f ); } else if (j == marks[i]->end_idx) { // last point on the mark - offset heading is 90deg - cur_outer = OffsetPointLast( &points[j-1], &points[j], 1.0 ); - cur_inner = OffsetPointLast( &points[j-1], &points[j], 2.0 ); + cur_outer = OffsetPointLast( &points[j-1], &points[j], offset-width/2.0f ); + cur_inner = OffsetPointLast( &points[j-1], &points[j], offset+width/2.0f ); } else { - cur_outer = OffsetPointMiddle( &points[j-1], &points[j], &points[j+1], 1.0 ); - cur_inner = OffsetPointMiddle( &points[j-1], &points[j], &points[j+1], 2.0 ); + cur_outer = OffsetPointMiddle( &points[j-1], &points[j], &points[j+1], offset-width/2.0f ); + cur_inner = OffsetPointMiddle( &points[j-1], &points[j], &points[j+1], offset+width/2.0f ); } if ( (prev_inner.x() != 0.0f) && (prev_inner.y() != 0.0f) ) @@ -447,10 +454,22 @@ int LinearFeature::Finish() sp.erase(); sp.set_poly( poly ); sp.set_material( material ); + sp.set_flag("lf"); feature_polys.push_back(sp); - tp = TGTexParams( prev_inner, 0.1, 1.0, heading ); + tp = TGTexParams( prev_inner, width, 1.0f, heading ); + +// SG_LOG(SG_GENERAL, SG_ALERT, "LinearFeature::Finish: calculating minv for mark " << i << " poly " << j << " distance " << dist << " cur minv " << last_end_v << " next minv " << (fmod( (last_end_v + dist), 1.0f )) ); + +// tp.set_minv(last_end_v); +// tp.set_maxv(0.5); feature_tps.push_back(tp); + + // this almost works.... + last_end_v = 1.0f - (fmod( (last_end_v + dist), 1.0f )); + +// SG_LOG(SG_GENERAL, SG_ALERT, "LinearFeature::Finish: last_end_v is " << last_end_v ); + } prev_outer = cur_outer; diff --git a/src/Airports/GenAirports850/linearfeature.hxx b/src/Airports/GenAirports850/linearfeature.hxx index f046bf05..72c7f523 100644 --- a/src/Airports/GenAirports850/linearfeature.hxx +++ b/src/Airports/GenAirports850/linearfeature.hxx @@ -57,7 +57,7 @@ typedef std::vector MarkingList; class LinearFeature { public: - LinearFeature( char* desc ) + LinearFeature( char* desc, double o, double w ) { if ( desc ) { @@ -67,11 +67,15 @@ public: { description = "none"; } + offset = o; + width = w; } - LinearFeature( string desc ) + LinearFeature( string desc, double o, double w ) { description = desc; + offset = o; + width = w; } inline string GetDescription() { return description; } @@ -90,6 +94,8 @@ private: Point3D OffsetPointMiddle( Point3D *prev, Point3D *cur, Point3D *next, double offset_by ); Point3D OffsetPointLast( Point3D *prev, Point3D *cur, double offset_by ); + double offset; + double width; MarkingList marks; Marking* cur_mark; diff --git a/src/Airports/GenAirports850/parser.cxx b/src/Airports/GenAirports850/parser.cxx index 99898d7b..1a1b5065 100644 --- a/src/Airports/GenAirports850/parser.cxx +++ b/src/Airports/GenAirports850/parser.cxx @@ -162,11 +162,11 @@ LinearFeature* Parser::ParseFeature( char* line ) if (strlen( line )) { - feature = new LinearFeature(line); + feature = new LinearFeature(line, 0.0f, 1.0f); } else { - feature = new LinearFeature(NULL); + feature = new LinearFeature(NULL, 0.0f, 1.0f); } SG_LOG(SG_GENERAL, SG_ALERT, "Creating Linear Feature with desription \"" << line << "\"");