| 284 | } |
| 285 | |
| 286 | void DrawingProgramCache::refresh_draw_cache(const std::shared_ptr<DrawingProgramCacheBVHNode>& bvhNode, const DrawData& drawData) { |
| 287 | if(bvhNode->children.empty() && bvhNode->components.empty()) |
| 288 | return; |
| 289 | |
| 290 | NodeCache nodeCache; |
| 291 | auto bvhNodeCacheIt = nodeCacheMap.find(bvhNode); |
| 292 | if(bvhNodeCacheIt != nodeCacheMap.end()) { |
| 293 | nodeCache = bvhNodeCacheIt->second; |
| 294 | if(!nodeCache.invalidBounds.has_value()) // Node is cached already, and doesn't have invalid areas, so there's nothing to do |
| 295 | return; |
| 296 | nodeCacheMap.erase(bvhNode); // Ensure nodeCache is erased, so that the draw_components_to_canvas function doesnt use it while drawing |
| 297 | } |
| 298 | else |
| 299 | nodeCache.surface = drawP.world.main.create_native_surface(bvhNode->resolution, true); |
| 300 | |
| 301 | SkCanvas* cacheCanvas = nodeCache.surface->getCanvas(); |
| 302 | |
| 303 | DrawData cacheDrawData = drawData; |
| 304 | cacheDrawData.cam.c = bvhNode->coords; |
| 305 | cacheDrawData.cam.set_viewing_area(bvhNode->resolution.cast<float>()); |
| 306 | cacheDrawData.refresh_draw_optimizing_values(); |
| 307 | |
| 308 | if(nodeCache.invalidBounds.has_value()) { |
| 309 | auto iBounds = nodeCache.invalidBounds.value(); |
| 310 | iBounds = bvhNode->bounds.get_intersection_between_aabbs(iBounds); |
| 311 | |
| 312 | WorldVec bDim = bvhNode->bounds.dim(); |
| 313 | |
| 314 | Vector2f clipBoundMin{static_cast<float>((iBounds.min.x() - bvhNode->bounds.min.x()) / bDim.x()) * bvhNode->resolution.x(), |
| 315 | static_cast<float>((iBounds.min.y() - bvhNode->bounds.min.y()) / bDim.y()) * bvhNode->resolution.y()}; |
| 316 | Vector2f clipBoundMax{static_cast<float>((iBounds.max.x() - bvhNode->bounds.min.x()) / bDim.x()) * bvhNode->resolution.x(), |
| 317 | static_cast<float>((iBounds.max.y() - bvhNode->bounds.min.y()) / bDim.y()) * bvhNode->resolution.y()}; |
| 318 | |
| 319 | SCollision::AABB<float> clipRectBoundAABB{clipBoundMin - Vector2f{4, 4}, clipBoundMax + Vector2f{4, 4}}; |
| 320 | SkIRect clipRect = SkIRect::MakeLTRB(clipRectBoundAABB.min.x(), |
| 321 | clipRectBoundAABB.min.y(), |
| 322 | clipRectBoundAABB.max.x(), |
| 323 | clipRectBoundAABB.max.y()); |
| 324 | SCollision::AABB<WorldScalar> clipRectBoundAABBWorld{ |
| 325 | bvhNode->coords.from_space(clipRectBoundAABB.min), |
| 326 | bvhNode->coords.from_space(clipRectBoundAABB.max) |
| 327 | }; |
| 328 | |
| 329 | cacheCanvas->save(); |
| 330 | cacheCanvas->clipIRect(clipRect); |
| 331 | cacheCanvas->clear(SkColor4f{0, 0, 0, 0}); |
| 332 | draw_components_to_canvas(cacheCanvas, cacheDrawData, clipRectBoundAABBWorld); |
| 333 | cacheCanvas->restore(); |
| 334 | nodeCache.invalidBounds = std::nullopt; |
| 335 | } |
| 336 | else { |
| 337 | cacheCanvas->clear(SkColor4f{0, 0, 0, 0}); |
| 338 | draw_components_to_canvas(cacheCanvas, cacheDrawData, std::nullopt); |
| 339 | } |
| 340 | |
| 341 | nodeCache.lastRenderTime = std::chrono::steady_clock::now(); |
| 342 | nodeCache.attachedDrawingProgramCache = this; |
| 343 |
nothing calls this directly
no test coverage detected