diff --git a/src/app/TileBasemap.cpp b/src/app/TileBasemap.cpp index d4788f7..2bbf928 100644 --- a/src/app/TileBasemap.cpp +++ b/src/app/TileBasemap.cpp @@ -43,6 +43,7 @@ const char* kTk = "aca91d8c9f59a4f779f39061b8a07737"; constexpr int kRootZoom = 9; // 四叉树根层级(单块~78km,±1 覆盖~234km 到天边) constexpr double kTargetPx = 384.0; // 瓦片屏幕像素阈值:超过则细分(越小越清晰但块更多) constexpr int kMaxLeaves = 200; // 一次覆盖的叶瓦片上限(安全兜底,防细分爆炸) +constexpr double kMaxTileDist = 10000.0; // 底图离数据中心最大距离(米):远裁剪面有界,且免无限拉远 constexpr int kMaxConcurrent = 8; // 瓦片请求最大并发(防暴发饱和单域名连接) constexpr int kMinZoom = 3; constexpr int kMaxZoom = 18; @@ -216,6 +217,10 @@ void TileBasemap::refineTile(int z, int x, int y, std::set& out, int& const double cx = (sw.x + ne.x) * 0.5, cy = (sw.y + ne.y) * 0.5; // 瓦片中心(局部米) const double g = std::max(std::abs(ne.x - sw.x), std::abs(ne.y - sw.y)); // 瓦片地面尺寸(米) + // 距离上限:数据中心在局部原点(0,0);瓦片离它太远则不加载——远裁剪面有界(剖面不被近裁剪面切), + // 也避免拉远时无限铺。叶块本身可大于此距离(其近端仍在范围内即保留)。 + if (std::sqrt(cx * cx + cy * cy) - g * 0.5 > kMaxTileDist) return; + // 该瓦片投影到屏幕的近似像素尺寸 > 阈值且未到最大层级 → 细分为 4 子块(近处更细)。 double screenPx; if (projParallel_) { diff --git a/src/app/VtkSceneView.cpp b/src/app/VtkSceneView.cpp index f5b9334..f14bbeb 100644 --- a/src/app/VtkSceneView.cpp +++ b/src/app/VtkSceneView.cpp @@ -64,7 +64,11 @@ VtkSceneView::VtkSceneView(geopro::render::Scene& scene, vtkRenderWindow* render : scene_(scene), renderWindow_(renderWindow), frame_(std::move(frame)), - zRefElev_(zRefElev) {} + zRefElev_(zRefElev) { + // 近裁剪容差调小:场景含近处剖面 + 远处底图(几十km),默认容差会把近裁剪面随远面推出去、 + // 切掉离相机近的剖面。调小后近面可贴近,剖面不被切(代价:远处深度精度略降,不可见层无所谓)。 + scene_.renderer()->SetNearClippingPlaneTolerance(1e-5); +} void VtkSceneView::removeProps(std::vector>& props) { for (auto& p : props) @@ -187,13 +191,7 @@ void VtkSceneView::setAxes(geopro::controller::AxesMode mode, geopro::controller void VtkSceneView::applyCameraView(geopro::controller::ViewDir dir) { geopro::render::applyView(scene_.renderer(), toRenderViewDir(dir)); // 设朝向(内部 ResetCamera 含底图) double bounds[6]; - const bool ok = computeDataBounds(bounds); - qInfo() << "[view] 预设取景 computeDataBounds=" << ok << " ds数=" << int(dsProps_.size()) - << (ok ? QString(" bounds[%1,%2 %3,%4 %5,%6]") - .arg(bounds[0]).arg(bounds[1]).arg(bounds[2]) - .arg(bounds[3]).arg(bounds[4]).arg(bounds[5]) - : QString()); - if (ok) + if (computeDataBounds(bounds)) scene_.renderer()->ResetCamera(bounds); // 重新取景到数据(否则被~公里级底图推到超远) scene_.renderer()->ResetCameraClippingRange(); // 裁剪面含底图 if (renderWindow_) renderWindow_->Render();