Eine aufbereitete Darstellung der Quelle

 
     
 
 
Anforderungen  |   Konzepte  |   Entwurf  |   Entwicklung  |   Qualitätssicherung  |   Lebenszyklus  |   Steuerung
 
 
 
 

Benutzer

Quelle  WaylandSurface.h   Sprache: C

 

/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */


#ifndef MOZ_WAYLAND_SURFACE_H_
#define MOZ_WAYLAND_SURFACE_H_

#include "nsWaylandDisplay.h"
#include "mozilla/Mutex.h"
#include "mozilla/Atomics.h"
#include "WaylandSurfaceLock.h"
#include "mozilla/GRefPtr.h"

/* Workaround for bug at wayland-util.h,
 * present in wayland-devel < 1.12
 */

struct wl_surface;
struct wl_subsurface;
struct wl_egl_window;

class MessageLoop;

namespace mozilla::widget {

class WaylandBuffer;
class BufferTransaction;

// WaylandSurface is a wrapper for Wayland rendering target
// which is wl_surface / wl_subsurface.
class WaylandSurface final {
  friend WaylandSurfaceLock;

  NS_INLINE_DECL_THREADSAFE_REFCOUNTING(WaylandSurface);

  WaylandSurface();

  // aRootLayer is a WaylandSurface root which is used by layered (HDR)
  // rendering.
  void Init(RefPtr<WaylandSurface> aRootLayer = nullptr);

#ifdef MOZ_LOGGING
  nsAutoCString GetDebugTag() const;
  void* GetLoggingWidget() const { return mLoggingWidget; };
  void SetLoggingWidget(void* aWidget) { mLoggingWidget = aWidget; }
#endif

  // Fire VSync handler registered to this surface.
  void VSyncCallbackHandler(struct wl_callback* aCallback, uint32_t aTime,
                            bool aEmulated, bool aRoutedFromChildSurface);

  // Set VSync handler which is fired when it's good time for painting
  // and WalandSurface is visible and VSync is enabled.
  //
  // If aEmulateVSyncCallback is set to true, we file VSync handler even
  // if WaylandSurface is not visible. It's used for painting to hidden
  // surface.
  //
  // Once set, the aVSyncCallbackHandler is preserved between unmap/map.
  //
  // It's VSync source responsibility to disable emulated VSync events
  // by SetVSyncCallbackStateLocked().
  void SetVSyncCallbackHandlerLocked(
      const WaylandSurfaceLock& aProofOfLock,
      const std::function<void(wl_callback*, uint32_t, bool)>&
          aVSyncCallbackHandler,
      bool aEmulateVSyncCallback = false);

  // Clears VSync callback handler. It's used if frame callback handler
  // contains strong reference to WaylandSurface class owner
  // which we want to clear.
  void ClearVSyncCallbackHandlerLocked(const WaylandSurfaceLock& aProofOfLock);

  // Enable/Disable any frame callback emission (includes emulated ones).
  void SetVSyncCallbackStateLocked(const WaylandSurfaceLock& aProofOfLock,
                                   bool aEnabled);
  // Register handler which is called on VSync state change set by
  // SetVSyncCallbackStateLocked().
  void SetVSyncCallbackStateHandlerLocked(
      const WaylandSurfaceLock& aProofOfLock,
      const std::function<void(bool)>& aVSyncCallbackStateHandler);

  // Set a routine which returns whether we should run emulated callback
  // or not. Don't overwrite existing one unless aForce is set.
  void SetVSyncEmulateCheckLocked(
      const WaylandSurfaceLock& aProofOfLock,
      const std::function<bool(void)>& aVSyncEmulateCheck, bool aForce = false);

  wl_egl_window* GetEGLWindow(DesktopIntSize aSize);
  bool HasEGLWindow() const { return !!mEGLWindow; }

  // Set WaylandSurface target size (viewport & ELG surface if it's present).
  void SetSize(DesktopIntSize aSize);

  // Apply changes to EGLWindow size set by SetSize().
  // ApplyEGLWindowSize() is called from compostor thread
  // right before GL rendering to set EGLWindow size / viewport size
  // for actual back buffer.
  //
  // aEGLWindowSize is scaled backbuffer size and it's used similary
  // as WaylandBuffer size at Attach().
  void ApplyEGLWindowSize(LayoutDeviceIntSize aEGLWindowSize);

  // Mapped means we have all internals created.
  bool IsMapped() const { return mIsMapped; }

  // We've got first frame callback so we're really visible now.
  bool IsVisible() const { return mIsVisible; }

  bool IsToplevelSurface() const { return !mParent; }

  // Called from frame callback and sets the visible flag
  void VisibleCallbackHandler();

  // Indicate that Wayland surface uses Gdk resources which
  // need to be released on main thread by GdkCleanUpLocked().
  // It may be called after Unmap() to make sure
  // Gtk resources are not allocated again.
  bool IsPendingGdkCleanup() const { return mIsPendingGdkCleanup; }

  bool IsOpaqueSurfaceHandlerSet() const { return mIsOpaqueSurfaceHandlerSet; }

  bool HasBufferAttached() const { return mBufferAttached; }

  // Mapped as direct surface of MozContainer
  bool MapLocked(const WaylandSurfaceLock& aProofOfLock,
                 wl_surface* aParentWLSurface,
                 DesktopIntPoint aSubsurfacePosition);
  // Mapped as child of WaylandSurface (used by layers)
  bool MapLocked(const WaylandSurfaceLock& aProofOfLock,
                 WaylandSurfaceLock* aParentWaylandSurfaceLock,
                 DesktopIntPoint aSubsurfacePosition);
  // Unmap surface which hides it
  void UnmapLocked(WaylandSurfaceLock& aSurfaceLock);

  // Clean up Gdk resources, on main thread only
  void GdkCleanUpLocked(const WaylandSurfaceLock& aProofOfLock);

  // Allow to register and run a callback when associated widget (nsWindow)
  // is mapped.
  //
  // Map callback is called *after* WaylandSurface::MapLocked() call
  // by widget code on main thread.
  void SetMapCallbackLocked(
      const WaylandSurfaceLock& aProofOfLock,
      const std::function<void(WaylandSurfaceLock& aProofOfLock)>& aMapCB);
  void ClearMapCallbackLocked(const WaylandSurfaceLock& aProofOfLock);
  void RunMapCallbackLocked(WaylandSurfaceLock& aProofOfLock);

  // Allow to register and run a callback when associated widget (nsWindow)
  // is unmapped.
  //
  // Unmap callback is called *before* WaylandSurface::UnmapLocked() call
  // by widget code on main thread.
  void SetUnmapCallbackLocked(const WaylandSurfaceLock& aProofOfLock,
                              const std::function<void(void)>& aUnmapCB);
  void ClearUnmapCallbackLocked(const WaylandSurfaceLock& aProofOfLock);
  void RunUnmapCallback();

  // Attach WaylandBuffer which shows WaylandBuffer content
  // on screen.
  bool AttachLocked(const WaylandSurfaceLock& aSurfaceLock,
                    RefPtr<WaylandBuffer> aBuffer);
  bool IsBufferAttached(WaylandBuffer* aBuffer);

  // If there's any WaylandBuffer recently attached, detach it.
  // It makes the WaylandSurface invisible and it doesn't have any
  // content.
  void RemoveAttachedBufferLocked(const WaylandSurfaceLock& aProofOfLock);

  // Remove deleted transaction from WaylandSurface, it may release
  // referenced WaylandBuffer.
  void RemoveTransactionLocked(const WaylandSurfaceLock& aSurfaceLock,
                               RefPtr<BufferTransaction> aTransaction);

  // CommitLocked() is needed to call after some of *Locked() method
  // to submit the action to Wayland compositor by wl_surface_commit().

  // It's possible to stack more *Locked() methods
  // together and do commit after the last one to do the changes in atomic way.

  // Need of commit is tracked by mSurfaceNeedsCommit flag and
  // if it's set, CommitLocked() is called when WaylandSurfaceLock is destroyed
  // and WaylandSurface is unlocked.
  void CommitLocked(const WaylandSurfaceLock& aProofOfLock,
                    bool aForceCommit = false, bool aForceDisplayFlush = false);

  void EnableDMABufFormatsLocked(
      const WaylandSurfaceLock& aProofOfLock,
      const std::function<void(DMABufFormats*)>& aFormatRefreshCB);
  void DisableDMABufFormatsLocked(const WaylandSurfaceLock& aProofOfLock);

  // Place this WaylandSurface above aLowerSurface
  void PlaceAboveLocked(const WaylandSurfaceLock& aProofOfLock,
                        WaylandSurfaceLock& aLowerSurfaceLock);
  void MoveLocked(const WaylandSurfaceLock& aProofOfLock,
                  DesktopIntPoint aPosition);
  void SetViewportFollowsSizeChangesLocked(
      const WaylandSurfaceLock& aProofOfLock);
  void SetViewPortSourceRectLocked(const WaylandSurfaceLock& aProofOfLock,
                                   const DesktopIntRect& aRect);
  void SetViewPortDestLocked(const WaylandSurfaceLock& aProofOfLock,
                             const DesktopIntSize& aDestSize);
  void SetTransformFlippedLocked(const WaylandSurfaceLock& aProofOfLock,
                                 bool aFlippedX, bool aFlippedY);

  void SetOpaqueRegion(const gfx::IntRegion& aRegion);
  void SetOpaqueRegionLocked(const WaylandSurfaceLock& aProofOfLock,
                             const gfx::IntRegion& aRegion);
  void SetOpaqueLocked(const WaylandSurfaceLock& aProofOfLock);
  void ClearOpaqueRegionLocked(const WaylandSurfaceLock& aProofOfLock);
  void OpaqueCallbackHandler();

  void ClearOpaqueCallbackLocked(const WaylandSurfaceLock& aProofOfLock);
  void SetOpaqueCallbackLocked(const WaylandSurfaceLock& aProofOfLock);

  bool DisableUserInputLocked(const WaylandSurfaceLock& aProofOfLock);
  void InvalidateRegionLocked(const WaylandSurfaceLock& aProofOfLock,
                              const gfx::IntRegion& aInvalidRegion);
  void InvalidateLocked(const WaylandSurfaceLock& aProofOfLock);

  // We use two scale systems in Firefox/Wayland. Ceiled (integer) scale and
  // fractional scale. Ceiled scale is easy to implement but comes with
  // rendering overhead while fractional rendering paints buffers with exact
  // scale.
  //
  // Fractional scale is used as rendering optimization.
  // For instance if 225% scale is used, ceiled scale is 3
  // and fractional 2.20.
  //
  // If we paint content with ceiled scale 3 and desktop uses scale 225%,
  // Wayland compositor downscales buffer to 2.20 on rendering
  // but we paint more pixels than necessary (so we use name ceiled).
  //
  // Scale is used by wp_viewport. If a surface has a surface-local size
  // of 100 px by 50 px and wishes to submit buffers with a scale of 1.5,
  // then a buffer of 150px by 75 px should be used and the wp_viewport
  // destination rectangle should be 100 px by 50 px.
  // The wl_surface buffer scale should remain set to 1.
  //
  // For scale 2 (200%) we use surface size 200 x 100 px and set
  // viewport size to 100 x 50 px.
  //
  // We're getting fractional scale number with a small delay from
  // wp_fractional_scale_v1 after first commit to surface.
  // Meanwhile we can use ceiled scale number instead of fractional one or
  // get fractional scale from parent window (if there's any).
  //
  enum ScaleType {
    Disabled = 0,
    Ceiled = 1,
    Fractional = 2,
    Coordinates = 3,
  };

  void SetScaleTypeLocked(const WaylandSurfaceLock& aProofOfLock,
                          ScaleType aScaleType, bool aSetHandler);
  bool IsCoordinatesScaleLocked(const WaylandSurfaceLock& aProofOfLock) const {
    MOZ_DIAGNOSTIC_ASSERT(&aProofOfLock == mSurfaceLock);
    return mScaleType == ScaleType::Coordinates;
  }

  // Right now we support two scale change callbacks.
  // ScaleCallbackType::Widget is used by nsWindow & co to promote scale
  // changes to layout.
  // ScaleCallbackType::Layers is used by HDR compositor to propagate
  // changes to rendered layers/subsurfaces.
  //
  // At least one scale callbacks needs to be set before SetScaleTypeLocked()
  // to run the callback.
  enum ScaleCallbackType {
    Widget = 0,
    Layers = 1,
    CallbackNum = 2,
  };
  void SetScaleCallbackLocked(const WaylandSurfaceLock& aProofOfLock,
                              ScaleCallbackType aCallbackType,
                              std::function<void(void)> aScaleCallback);
  bool HasScaleCallbacksLocked(const WaylandSurfaceLock& aProofOfLock);
  void ClearScaleCallbacksLocked(const WaylandSurfaceLock& aProofOfLock);

  // Returns scale as float point number. If WaylandSurface is not mapped,
  // return fractional scale of parent surface or monitor.
  static constexpr const double sNoScale = -1;
  double GetScale() const;
  uint32_t GetCoordinatesScale() const { return mCoordinatesScale; }
  double GetCoordinatesScaleRounded() const {
    return ((double)mCoordinatesScale) / (1 << 24);
  }
  bool HasCoordinatesScaleLocked(const WaylandSurfaceLock& aProofOfLock) const {
    return !!mCoordinatesScaleManager;
  }

  // Called when screen ceiled scale changes or sets initial scale before we map
  // and paint the surface.
  void SetCeiledScaleLocked(const WaylandSurfaceLock& aProofOfLock,
                            int aScreenCeiledScale);
  // Sets coordinates scale explicitly to the surface,
  bool SetCoordinatesScaleLocked(const WaylandSurfaceLock& aProofOfLock,
                                 uint32_t scale_8_24);

  static void AfterPaintHandler(GdkFrameClock* aClock, void* aData);

  // See https://gitlab.gnome.org/GNOME/gtk/-/merge_requests/3111 why we use it.
  // If child surface covers whole area of parent surface and it's opaque,
  // parent surface will not get any events (frame callbacks) from compositor
  // as it's considered as invisible.
  //
  // Firefox uses the parent wl_surface (owned by GdkWindow) to get input
  // events. Without gdk_wayland_window_add_frame_callback_surface() call,
  // Gdk is not getting any events from compostor and we're frozen.
  //
  // So gdk_wayland_window_add_frame_callback_surface() registers wl_surface
  // owned by WaylandSurface to GtkWindow and requests frame callback
  // for it. Such frame callback is then routed to GdkWindow and it's used
  // to fire events like native GdkWindow ones.
  //
  // To make sure WaylandSurface's wl_surface frame callback is generated,
  // we need to commit the wl_surface regularly as Gdk registers frame callback
  // for it at on_frame_clock_after_paint() event of GdkWindow.
  bool AddOpaqueSurfaceHandlerLocked(const WaylandSurfaceLock& aProofOfLock,
                                     GdkWindow* aGdkWindow,
                                     bool aRegisterCommitHandler);
  bool RemoveOpaqueSurfaceHandlerLocked(const WaylandSurfaceLock& aProofOfLock);

  // Additional callback to call from on_frame_clock_after_paint()
  // and before this wl_surface is commited.
  // It can be used to update subsurfaces from main thread.
  void SetGdkCommitCallbackLocked(
      const WaylandSurfaceLock& aProofOfLock,
      const std::function<void(void)>& aGdkCommitCB);
  void ClearGdkCommitCallbackLocked(const WaylandSurfaceLock& aProofOfLock);

  RefPtr<DMABufFormats> GetDMABufFormats() const { return mFormats; }

  GdkWindow* GetGdkWindow() const;

  static bool IsOpaqueRegionEnabled();

  void SetParentLocked(const WaylandSurfaceLock& aProofOfLock,
                       RefPtr<WaylandSurface> aParent);

  bool EnableColorManagementLocked(const WaylandSurfaceLock& aProofOfLock,
                                   mozilla::gfx::YUVColorSpace aColorSpace,
                                   gfx::TransferFunction aTransferFunction);
  void SetColorRepresentationLocked(const WaylandSurfaceLock& aProofOfLock,
                                    mozilla::gfx::YUVColorSpace aColorSpace,
                                    bool aFullRange,
                                    uint32_t aWPChromaLocation);

  static void ImageDescriptionFailed(
      void* aData, struct wp_image_description_v1* aImageDescription,
      uint32_t aCause, const char* aMsg);
  static void ImageDescriptionReady(
      void* aData, struct wp_image_description_v1* aImageDescription,
      uint32_t aIdentity);

  void AssertCurrentThreadOwnsMutex();

  void ForceCommit() { mSurfaceNeedsCommit = true; }
  void SetCommitStateLocked(const WaylandSurfaceLock& aProofOfLock,
                            bool aCommitAllowed) {
    mCommitAllowed = aCommitAllowed;
  }

 private:
  ~WaylandSurface();

  bool MapLocked(const WaylandSurfaceLock& aProofOfLock,
                 wl_surface* aParentWLSurface,
                 WaylandSurfaceLock* aParentWaylandSurfaceLock,
                 DesktopIntPoint aSubsurfacePosition, bool aSubsurfaceDesync);

  wl_surface* Lock(WaylandSurfaceLock* aWaylandSurfaceLock);
  void Unlock(struct wl_surface** aSurface,
              WaylandSurfaceLock* aWaylandSurfaceLock);
  void Commit(WaylandSurfaceLock* aProofOfLock, bool aForceCommit,
              bool aForceDisplayFlush);

  // Get buffer transaction for WaylandBuffer, create new or recycle one.
  BufferTransaction* GetNextTransactionLocked(
      const WaylandSurfaceLock& aSurfaceLock, WaylandBuffer* aBuffer);
  // Force release/detele all transactions and wl_buffers attached to them.
  void ReleaseAllWaylandTransactionsLocked(WaylandSurfaceLock& aSurfaceLock);

  void SetVSyncCallbackLocked(const WaylandSurfaceLock& aProofOfLock);
  void ClearVSyncCallbackLocked(const WaylandSurfaceLock& aProofOfLock);
  bool HasEmulatedVSyncCallbackLocked(
      const WaylandSurfaceLock& aProofOfLock) const;
  bool IsEmulatedVSyncEnabledLocked(const WaylandSurfaceLock& aProofOfLock);
  void RequestEmulatedVSyncLocked(const WaylandSurfaceLock& aProofOfLock);

  // Configures requested scale type. If aSetHandler is set it also
  // install wayland-protocol handlers to call the scale change callbacks.
  //
  // We usually want to install handler to toplevel surfaces only
  // and propagate the scale change to child surfaces.
  bool ConfigureScaleLocked(const WaylandSurfaceLock& aProofOfLock,
                            ScaleType aScaleType, bool aSetProtocolHandler);
  bool ConfigureCoordinateScaleLocked(const WaylandSurfaceLock& aProofOfLock,
                                      bool aSetProtocolHandler);
  bool ConfigureFractionalScaleLocked(const WaylandSurfaceLock& aProofOfLock,
                                      bool aSetProtocolHandler);

  // Calculate 'stable' rounded size for subsurface based
  // on its size and position.
  LayoutDeviceIntSize GetScaledSize(const DesktopIntSize& aSize) const;

  // Weak ref to owning widget (nsWindow or NativeLayerWayland),
  // used for diagnostics/logging only.
  void* mLoggingWidget = nullptr;

  // mIsMapped means we're supposed to be visible
  // (or not if Wayland compositor decides so).
  mozilla::Atomic<bool, mozilla::Relaxed> mIsMapped{false};

  // mIsVisible means we're really visible as we've got frame callback.
  mozilla::Atomic<bool, mozilla::Relaxed> mIsVisible{false};

  // We used Gdk functions which needs clean up in main thread.
  mozilla::Atomic<bool, mozilla::Relaxed> mIsPendingGdkCleanup{false};

  std::function<void(void)> mGdkCommitCallback;
  std::function<void(WaylandSurfaceLock& aProofOfLock)> mMapCallback;
  std::function<void(void)> mUnmapCallback;

  DesktopIntSize mSize;

  // Parent GdkWindow where we paint to, directly or via subsurface.
  RefPtr<GdkWindow> mGdkWindow;

  // Parent wl_surface owned by mGdkWindow. It's used when we're attached
  // directly to MozContainer.
  wl_surface* mParentSurface = nullptr;

  // Parent WaylandSurface.
  //
  // Layer rendering (compositor) uses mSurface directly attached to
  // wl_surface owned by mParent.
  //
  // For non-compositing rendering (old) mParent is WaylandSurface
  // owned by parent nsWindow.
  RefPtr<WaylandSurface> mParent;

  // wl_surface setup/states
  wl_surface* mSurface = nullptr;
  mozilla::Atomic<bool, mozilla::Relaxed> mSurfaceNeedsCommit{false};
  bool mCommitAllowed = true;

  // When subsurface is desynced, we need to commit to parent surface
  // to see the change in subsurface (this one).
  // In such case we set mSurfaceNeedsCommit to parent for it.
  bool mSubsurfaceDesync = true;

  wl_subsurface* mSubsurface = nullptr;
  DesktopIntPoint mSubsurfacePosition;

  // Wayland buffers recently attached to this surface or held by
  // Wayland compositor.
  // There may be more than one buffer attached, for instance if
  // previous buffer is hold by compositor. We need to keep
  // there buffers live until compositor notify us that we
  // can release them.
  AutoTArray<RefPtr<BufferTransaction>, 3> mBufferTransactions;
  uintptr_t mLatestAttachedBuffer = 0;

  // Indicates mSurface has buffer attached so we can attach subsurface
  // to it and expect to get frame callbacks from Wayland compositor.
  // We set it at AttachLocked() or when we get first frame callback
  // (when EGL is used).
  mozilla::Atomic<bool, mozilla::Relaxed> mBufferAttached{false};

  mozilla::Atomic<wl_egl_window*, mozilla::Relaxed> mEGLWindow{nullptr};

  bool mViewportFollowsSizeChanges = false;
  wp_viewport* mViewport = nullptr;
  DesktopIntRect mViewportSourceRect{-1, -1, -1, -1};
  DesktopIntSize mViewportDestinationSize{-1, -1};

  // Surface flip state on X/Y asix
  bool mBufferTransformFlippedX = false;
  bool mBufferTransformFlippedY = false;

  // Frame callback for mIsVisible flag
  wl_callback* mVisibleFrameCallback = nullptr;

  // VSync callback handler called every frame or by time for emulated ones.
  struct VSyncCallback {
    std::function<void(wl_callback*, uint32_t, bool)> mCb = nullptr;
    bool mEmulated = false;
    bool IsSet() const { return !!mCb; }
  };
  VSyncCallback mVSyncCallbackHandler;

  wl_callback* mVSyncFrameCallback = nullptr;

  bool mVSyncCallbackEnabled = true;
  std::function<void(bool)> mVSyncCallbackStateHandler = nullptr;
  std::function<bool(void)> mVSyncEmulateCheck = nullptr;

  guint mEmulatedVSyncCallbackTimerID = 0;
  constexpr static int sEmulatedVSyncCallbackTimeoutMs = (int)(1000.0 / 60.0);

  // Frame callback used to set opaque region to wl_surface.
  wl_region* mPendingOpaqueRegion = nullptr;
  wl_callback* mOpaqueRegionFrameCallback = nullptr;

  // WaylandSurface is used from Compositor/Rendering/Main threads.
  mozilla::Mutex mMutex{"WaylandSurface"};
  WaylandSurfaceLock* mSurfaceLock = nullptr;

  // We may mark part of mSurface as opaque (non-transparent) if it's supported
  // by Gtk which allows compositor to skip painting of covered parts.
  mozilla::Atomic<bool, mozilla::Relaxed> mIsOpaqueSurfaceHandlerSet{false};
  gulong mGdkAfterPaintId = 0;
  static bool sIsOpaqueRegionEnabled;
  static void (*sGdkWaylandWindowAddCallbackSurface)(GdkWindow*,
                                                     struct wl_surface*);
  static void (*sGdkWaylandWindowRemoveCallbackSurface)(GdkWindow*,
                                                        struct wl_surface*);

  ScaleType mScaleType = ScaleType::Disabled;

  // mScreenScale is set from main thread only but read from
  // different threads.
  mozilla::Atomic<double, mozilla::Relaxed> mScreenScale{sNoScale};
  // Coordinates scale is in fixed-point 8.24 format.
  // Use GetCoordinatesScaleRounded() to convert it to float point.
  mozilla::Atomic<uint32_t, mozilla::Relaxed> mCoordinatesScale{1 << 24};

  // wp_fractional_scale_v1 / xx_fractional_scale_v2 works differently.
  //
  // wp_fractional_scale_v1 is needed for scale changes listener only
  // so it's optional and we don't need it for every surface.
  //
  // xx_fractional_scale_v2 is used to set coordinates scale to particular
  // surface so it must be present.
  wp_fractional_scale_v1* mFractionalScaleListener = nullptr;
  xx_fractional_scale_v2* mCoordinatesScaleManager = nullptr;

  // Callback issued when fractional / coordinates scale changes.
  // Ceiled (integer) scale changes is monitored by nsWindow as it's
  // tied to GtkWindow.
  std::function<void(void)> mScaleCallbacks[ScaleCallbackType::CallbackNum] = {
      nullptr, nullptr};

  bool mUseDMABufFormats = false;
  // Wayland display notifies us when available DRM formats are are changed.
  // For instance if wl_surface becomes fullscreen we may get DRM formats
  // for direct scanout.
  std::function<void(DMABufFormats*)> mDMABufFormatRefreshCallback;
  RefPtr<DMABufFormats> mFormats;

  // HDR support
  bool mHDRSet = false;
  wp_color_management_surface_v1* mColorSurface = nullptr;
  wp_color_representation_surface_v1* mColorRepresentationSurface = nullptr;
  wp_image_description_v1* mImageDescription = nullptr;
};

}  // namespace mozilla::widget

#endif /* MOZ_WAYLAND_SURFACE_H_ */

Messung V0.5 in Prozent
C=66 H=100 G=84

¤ Diese beiden folgenden Angebotsgruppen bietet das Unternehmen0.15Angebot  (Wie Sie bei der Firma Beratungs- und Dienstleistungen beauftragen können 2026-09-29) ¤

*Eine klare Vorstellung vom Zielzustand






Wurzel

Suchen

PVS Prover

Isabelle Prover

NIST Cobol Testsuite

Cephes Mathematical Library

Vienna Development Method

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.






                                                                                                                                                                                                                                                                                                                                                                                                     


Neuigkeiten

     Aktuelles
     Motto des Tages

Open Source Software

     Quellcodebibliothek
     Eigene Quellcodes
     Fremde Quellcodes
     Suchen

Jenseits des Üblichen ....
    

Besucherstatistik

Besucherstatistik

Statistik
#Sources=1126438
#Domains=1897691