Package icyllis.arc3d.engine

# Class SurfaceProxy

java.lang.Object
icyllis.arc3d.core.RefCnt
icyllis.arc3d.engine.SurfaceProxy

All Implemented Interfaces:
  `RefCounted`

Direct Known Subclasses:
  `RenderTargetProxy`

public abstract class SurfaceProxy extends RefCnt
The `SurfaceProxy` implements the proxy pattern for `GpuSurface`, it targets a `GpuSurface` with three instantiation methods: deferred, lazy-callback and wrapped.

Target: The backing GPU texture or framebuffer that referenced by this proxy.

Instantiate: Create new GPU surfaces or find surfaces in `ResourceCache` when they are actually required on flush.

BackingFit: Indicates whether a backing store needs to be an exact match or can be larger than is strictly necessary. True: Exact; False: Approx. See `ISurface.FLAG_APPROX_FIT`, the default is exact.

UseAllocator:

- False: This surface will be instantiated outside the allocator (e.g. for surfaces that are instantiated in on-flush callbacks).
- True: `SurfaceAllocator` should instantiate this surface.

Threading: Proxies can be created on any thread, and change the reference count through `RefCnt.ref()` and `RefCnt.unref()`. If proxy is, or will be used by render thread, its final `RefCnt.unref()` must be called on render thread (the case where render thread will have ownership). This is because the backing GPU texture can only be operated on render thread.

Use `ImageProxyCache` to obtain `SurfaceProxy` objects.

See Also:
  - `ImageViewProxy`
  - `ImageProxyView`

- ## Nested Class Summary

  Nested Classes
  Modifier and Type
  Class
  Description
  `static class`
  `SurfaceProxy.LazyCallbackResult`
  `static interface`
  `SurfaceProxy.LazyInstantiateCallback`
  Lazy-callback function.

- ## Method Summary

  Modifier and Type
  Method
  Description
  `ImageViewProxy`
  `asImageProxy()`
  `RenderTargetProxy`
  `asRenderTargetProxy()`
  `abstract void`
  `clear()`
  De-instantiate.
  `abstract boolean`
  `doLazyInstantiation(ResourceProvider resourceProvider)`
  `boolean`
  `equals(Object o)`
  `final BackendFormat`
  `getBackendFormat()`
  `abstract int`
  `getBackingHeight()`
  Returns the physical height of the backing surface.
  `abstract UniqueID`
  `getBackingUniqueID()`
  `abstract int`
  `getBackingWidth()`
  Returns the physical width of the backing surface.
  `@RawPtr Image`
  `getGpuImage()`
  If this is a texturable surface and the surface is already instantiated, return its backing `Image`; if not, return null.
  `@RawPtr GpuRenderTarget`
  `getGpuRenderTarget()`
  If this is a renderable surface and the surface is already instantiated, return its backing `GpuRenderTarget`; if not, return null.
  `abstract @RawPtr GpuSurface`
  `getGpuSurface()`
  `final int`
  `getHeight()`
  Returns the logical height of this surface.
  `long`
  `getMemorySize()`
  Retrieves the amount of GPU memory that will be or currently is used by this resource in bytes.
  `abstract int`
  `getSampleCount()`
  Returns the number of samples per pixel in color buffers (one if non-MSAA).
  `final int`
  `getTaskTargetCount()`
  How many render tasks has this surface been the target of?
  `final UniqueID`
  `getUniqueID()`
  The contract for the unique ID is: For wrapped resources: the unique ID will match that of the wrapped resource For deferred resources: The unique ID will be different from the real resource, when it is allocated The surface's unique ID will not change across the instantiates call The unique IDs of the proxies and the resources draw from the same pool What this boils down to is that the unique ID of a surface can be used to consistently track/identify a surface but should never be used to distinguish between resources and proxies - beware!
  `IUniqueKey`
  `getUniqueKey()`
  `final int`
  `getWidth()`
  Returns the logical width of this surface.
  `int`
  `hashCode()`
  `abstract boolean`
  `instantiate(ResourceProvider resourceProvider)`
  Instantiates the backing store, if necessary.
  `abstract boolean`
  `isBackingWrapped()`
  Returns whether the backing store references the wrapped object.
  `final boolean`
  `isBudgeted()`
  Does the resource count against the resource budget?
  `final boolean`
  `isDeferredListTarget()`
  `final boolean`
  `isExact()`
  If set to exact or approx size is equal to exact size.
  `abstract boolean`
  `isInstantiated()`
  Returns true if the backing store is instantiated.
  `abstract boolean`
  `isLazy()`
  Returns true if the surface has a lazy callback and not instantiated.
  `final boolean`
  `isLazyMost()`
  Returns true if the surface has a lazy callback, not instantiated, loose fit and dimension is not known.
  `final boolean`
  `isManualMSAAResolve()`
  `final boolean`
  `isProtected()`
  `final boolean`
  `isReadOnly()`
  The pixel values of this surface's texture cannot be modified (e.g.
  `final void`
  `isUsedAsTaskTarget()`
  Called when this task becomes a target of a `RenderTask`.
  `final boolean`
  `isUserExact()`
  `void`
  `setIsDeferredListTarget()`
  `abstract boolean`
  `shouldSkipAllocator()`
  Proxies that are already instantiated and whose backing texture cannot be recycled to instantiate other proxies do not need to be considered by `SurfaceAllocator`.
  `final boolean`
  `wrapsGLDefaultFB()`
  `final boolean`
  `wrapsVkSecondaryCB()`

  ### Methods inherited from class icyllis.arc3d.core.RefCnt

  `create, create, deallocate, getRefCnt, getRefCntAcquire, getRefCntVolatile, move, move, ref, unique, unref`

  ### Methods inherited from class java.lang.Object

  `clone, finalize, getClass, notify, notifyAll, toString, wait, wait, wait`

- ## Method Details

  - ### isLazy

    public abstract boolean isLazy()
    Returns true if the surface has a lazy callback and not instantiated.

  - ### isLazyMost

    public final boolean isLazyMost()
    Returns true if the surface has a lazy callback, not instantiated, loose fit and dimension is not known.

  - ### getWidth

    public final int getWidth()
    Returns the logical width of this surface. The result is undefined if `isLazyMost()` returns true.
    Returns:
      the desired width of the surface

  - ### getHeight

    public final int getHeight()
    Returns the logical height of this surface. The result is undefined if `isLazyMost()` returns true.
    Returns:
      the desired height of the surface

  - ### getBackingWidth

    public abstract int getBackingWidth()
    Returns the physical width of the backing surface. The result is undefined if `isLazyMost()` returns true.
    Returns:
      the width of the backing store

  - ### getBackingHeight

    public abstract int getBackingHeight()
    Returns the physical height of the backing surface. The result is undefined if `isLazyMost()` returns true.
    Returns:
      the height of the backing store

  - ### isExact

    public final boolean isExact()
    If set to exact or approx size is equal to exact size. Must call when not lazy-most. Equivalent to getWidth() == getBackingWidth() invalid input: '&'invalid input: '&' getHeight() == getBackingHeight();
    Returns:
      true if backing fit is (as if) exact
    See Also:
      - `isUserExact()`

  - ### getSampleCount

    public abstract int getSampleCount()
    Returns the number of samples per pixel in color buffers (one if non-MSAA). If this surface it non-renderable, this method always returns one.
    Returns:
      the number of samples, greater than (multisample) or equal to one

  - ### getBackendFormat

    @Nonnull public final BackendFormat getBackendFormat()
    Returns:
      the backend format of the surface

  - ### getUniqueID

    public final UniqueID getUniqueID()
    The contract for the unique ID is:
    - For wrapped resources: the unique ID will match that of the wrapped resource
    - For deferred resources:
      - The unique ID will be different from the real resource, when it is allocated
      - The surface's unique ID will not change across the instantiates call
    - The unique IDs of the proxies and the resources draw from the same pool
    What this boils down to is that the unique ID of a surface can be used to consistently track/identify a surface but should never be used to distinguish between resources and proxies - beware!
    Returns:
      a reference for identity hash map

  - ### getBackingUniqueID

    public abstract UniqueID getBackingUniqueID()

  - ### isInstantiated

    public abstract boolean isInstantiated()
    Returns true if the backing store is instantiated.

  - ### instantiate

    public abstract boolean instantiate(ResourceProvider resourceProvider)
    Instantiates the backing store, if necessary.
    Parameters:
      `resourceProvider` - the resource provider to create textures
    Returns:
      success or not

  - ### clear

    public abstract void clear()
    De-instantiate. Called after instantiated.

  - ### shouldSkipAllocator

    public abstract boolean shouldSkipAllocator()
    Proxies that are already instantiated and whose backing texture cannot be recycled to instantiate other proxies do not need to be considered by `SurfaceAllocator`.

  - ### isBackingWrapped

    public abstract boolean isBackingWrapped()
    Returns whether the backing store references the wrapped object. Always false if not instantiated.

  - ### isUsedAsTaskTarget

    public final void isUsedAsTaskTarget()
    Called when this task becomes a target of a `RenderTask`.

  - ### getTaskTargetCount

    public final int getTaskTargetCount()
    How many render tasks has this surface been the target of?

  - ### getGpuSurface

    @Nullable @RawPtr public abstract @RawPtr GpuSurface getGpuSurface()

  - ### getGpuImage

    @Nullable @RawPtr public @RawPtr Image getGpuImage()
    If this is a texturable surface and the surface is already instantiated, return its backing `Image`; if not, return null.

  - ### getGpuRenderTarget

    @Nullable @RawPtr public @RawPtr GpuRenderTarget getGpuRenderTarget()
    If this is a renderable surface and the surface is already instantiated, return its backing `GpuRenderTarget`; if not, return null.

  - ### isBudgeted

    public final boolean isBudgeted()
    Does the resource count against the resource budget?

    Always true for lazy-callback resources; set from the backing resource for wrapped resources; only meaningful if 'mLazyInstantiateCallback' is non-null.

  - ### isReadOnly

    public final boolean isReadOnly()
    The pixel values of this surface's texture cannot be modified (e.g. doesn't support write pixels or MIP map level regen). Read-only proxies also bypass interval tracking and assignment in ResourceAllocator.

  - ### isProtected

    public final boolean isProtected()

  - ### isManualMSAAResolve

    public final boolean isManualMSAAResolve()

  - ### wrapsGLDefaultFB

    public final boolean wrapsGLDefaultFB()

  - ### wrapsVkSecondaryCB

    public final boolean wrapsVkSecondaryCB()

  - ### isDeferredListTarget

    public final boolean isDeferredListTarget()

  - ### setIsDeferredListTarget

    @Internal public void setIsDeferredListTarget()

  - ### isUserExact

    @Internal public final boolean isUserExact()

  - ### asImageProxy

    public ImageViewProxy asImageProxy()
    Returns:
      the texture proxy associated with the surface proxy, may be NULL.

  - ### asRenderTargetProxy

    public RenderTargetProxy asRenderTargetProxy()
    Returns:
      the render target proxy associated with the surface proxy, may be NULL.

  - ### getUniqueKey

    public IUniqueKey getUniqueKey()
    Returns:
      the unique key for this proxy, may be NULL

  - ### getMemorySize

    public long getMemorySize()
    Retrieves the amount of GPU memory that will be or currently is used by this resource in bytes. It is approximate since we aren't aware of additional padding or copies made by the driver.
    Returns:
      the amount of GPU memory used in bytes

  - ### hashCode

    public int hashCode()
    Overrides:
      `hashCode` in class `Object`

  - ### equals

    public boolean equals(Object o)
    Overrides:
      `equals` in class `Object`

  - ### doLazyInstantiation

    @Internal public abstract boolean doLazyInstantiation(ResourceProvider resourceProvider)