576 {},
577#if defined(SK_RESOLVE_FILTERS_BEFORE_RESTORE)
578 bool mustCoverDst = true,
579#endif
583 !localToDst.
invert(&dstToLocal)) {
584 return {};
585 }
586
589#if defined(SK_RESOLVE_FILTERS_BEFORE_RESTORE)
590
591
592 if (mustCoverDst) {
593 contentBounds.reset();
594 }
595#endif
596
597
598
602 if (filter) {
603 capability = std::min(capability,
as_IFB(filter)->getCTMCapability());
604 }
605 }
607 return {};
608 }
609
610
611 if (scaleFactor != 1.0f &&
613 return {};
614 }
615
616
617
618
619
620
621 static const int kMinDimThreshold = 2048;
623 SkIRect(targetOutput).height64())),
624 kMinDimThreshold);
625
627 if (contentBounds) {
628
629
631 if (!baseLayerBounds.intersect(knownBounds)) {
633 }
634 }
635
637 if (!filters.
empty()) {
639 return filters[i] ? as_IFB(filters[i])
640 ->getInputBounds(mapping, targetOutput, contentBounds)
641 : baseLayerBounds;
642 });
643
644
645 if (layerBounds.width() > maxLayerDim || layerBounds.height() > maxLayerDim) {
648 if (filter) {
650 idealMapping, targetOutput, contentBounds);
651 maxLayerDim = std::max(std::max(idealLayerBounds.width(),
652 idealLayerBounds.height()),
653 maxLayerDim);
654 }
655 }
656 }
657 } else {
658 if (baseLayerBounds.isEmpty()) {
659 return {};
660 }
661 layerBounds = baseLayerBounds;
662 }
663
664 if (layerBounds.width() > maxLayerDim || layerBounds.height() > maxLayerDim) {
667 std::min(layerBounds.height(), maxLayerDim)));
672 return {};
673 } else {
674 layerBounds = newLayerBounds;
675 }
676 }
677
678 return std::make_pair(mapping, layerBounds);
679}
static skif::ParameterSpace< SkPoint > compute_decomposition_center(const SkMatrix &dstToLocal, std::optional< skif::ParameterSpace< SkRect > > contentBounds, const skif::DeviceSpace< SkIRect > &targetOutput)
static SkImageFilter_Base * as_IFB(SkImageFilter *filter)
static constexpr int32_t Sk64_pin_to_s32(int64_t x)
skif::LayerSpace< SkIRect > getInputBounds(const skif::Mapping &mapping, const skif::DeviceSpace< SkIRect > &desiredOutput, std::optional< skif::ParameterSpace< SkRect > > knownContentBounds) const
static SkMatrix Scale(SkScalar sx, SkScalar sy)
@ kFill_ScaleToFit
scales in x and y to fill destination SkRect
bool invert(SkMatrix *inverse) const
static SkMatrix MakeRectToRect(const SkRect &src, const SkRect &dst, ScaleToFit stf)
constexpr bool empty() const
constexpr size_t size() const
const SkMatrix & deviceToLayer() const
bool decomposeCTM(const SkMatrix &ctm, const SkImageFilter *filter, const skif::ParameterSpace< SkPoint > &representativePt)
const SkMatrix & layerMatrix() const
LayerSpace< T > paramToLayer(const ParameterSpace< T > ¶mGeometry) const
bool adjustLayerSpace(const SkMatrix &layer)
static constexpr SkIRect MakeWH(int32_t w, int32_t h)
static SkRect Make(const SkISize &size)