mirror of
https://git.sr.ht/~eliasnaur/gio
synced 2026-07-05 01:15:35 +00:00
gpu,gpu/backend: implement generic backend.NewDevice
NewDevice creates a Device given an API, which is the necessary GPU resources for a backend. Convert gpu.New to take an API instead of a backend.Device directly. In turn, this frees us to later unexport the backend package along with the backend implementations (for now just gioui.org/gpu/gl for OpenGL). It also allows programs that embed Gio (such as gioui.org/example/glfw) to freely choose a backend, not just OpenGL. Signed-off-by: Elias Naur <mail@eliasnaur.com>
This commit is contained in:
+15
@@ -0,0 +1,15 @@
|
||||
// SPDX-License-Identifier: Unlicense OR MIT
|
||||
|
||||
package gpu
|
||||
|
||||
import "gioui.org/gpu/backend"
|
||||
|
||||
// An API carries the necessary GPU API specific resources to create a Device.
|
||||
// There is an API type for each supported GPU API such as OpenGL and Direct3D.
|
||||
type API = backend.API
|
||||
|
||||
// OpenGL denotes the OpenGL or OpenGL ES API.
|
||||
type OpenGL = backend.OpenGL
|
||||
|
||||
// Direct3D11 denotes the Direct3D API.
|
||||
type Direct3D11 = backend.Direct3D11
|
||||
@@ -0,0 +1,56 @@
|
||||
// SPDX-License-Identifier: Unlicense OR MIT
|
||||
|
||||
package backend
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"unsafe"
|
||||
|
||||
"gioui.org/internal/glimpl"
|
||||
)
|
||||
|
||||
// See gpu/api.go for documentation for the API types
|
||||
|
||||
type API interface {
|
||||
implementsAPI()
|
||||
}
|
||||
|
||||
type OpenGL struct {
|
||||
// Context contains the WebGL context for WebAssembly platforms. It is
|
||||
// empty for all other platforms; an OpenGL context is assumed current when
|
||||
// calling NewDevice.
|
||||
Context glimpl.Context
|
||||
}
|
||||
|
||||
type Direct3D11 struct {
|
||||
// Device contains a *ID3D11Device.
|
||||
Device unsafe.Pointer
|
||||
}
|
||||
|
||||
// API specific device constructors.
|
||||
var (
|
||||
NewOpenGLDevice func(api OpenGL) (Device, error)
|
||||
NewDirect3D11Device func(api Direct3D11) (Device, error)
|
||||
)
|
||||
|
||||
// NewDevice creates a new Device given the api.
|
||||
//
|
||||
// Note that the device does not assume ownership of the resources contained in
|
||||
// api; the caller must ensure the resources are valid until the device is
|
||||
// released.
|
||||
func NewDevice(api API) (Device, error) {
|
||||
switch api := api.(type) {
|
||||
case OpenGL:
|
||||
if NewOpenGLDevice != nil {
|
||||
return NewOpenGLDevice(api)
|
||||
}
|
||||
case Direct3D11:
|
||||
if NewDirect3D11Device != nil {
|
||||
return NewDirect3D11Device(api)
|
||||
}
|
||||
}
|
||||
return nil, fmt.Errorf("backend: no backend available for the API %T", api)
|
||||
}
|
||||
|
||||
func (OpenGL) implementsAPI() {}
|
||||
func (Direct3D11) implementsAPI() {}
|
||||
+6
-6
@@ -123,12 +123,12 @@ const (
|
||||
storageBindings = 32
|
||||
)
|
||||
|
||||
// NewBackend returns a new Backend.
|
||||
//
|
||||
// Pass a WebGL context if GOOS is "js", otherwise pass nil for the current
|
||||
// context.
|
||||
func NewBackend(ctx Context) (*Backend, error) {
|
||||
f, err := glimpl.NewFunctions(ctx)
|
||||
func init() {
|
||||
backend.NewOpenGLDevice = newOpenGLDevice
|
||||
}
|
||||
|
||||
func newOpenGLDevice(api backend.OpenGL) (backend.Device, error) {
|
||||
f, err := glimpl.NewFunctions(api.Context)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
+11
-4
@@ -28,6 +28,9 @@ import (
|
||||
"gioui.org/layout"
|
||||
"gioui.org/op"
|
||||
"gioui.org/op/clip"
|
||||
|
||||
// Register backend.
|
||||
_ "gioui.org/gpu/gl"
|
||||
)
|
||||
|
||||
type GPU interface {
|
||||
@@ -380,14 +383,18 @@ const (
|
||||
materialTexture
|
||||
)
|
||||
|
||||
func New(ctx backend.Device) (GPU, error) {
|
||||
func New(api API) (GPU, error) {
|
||||
d, err := backend.NewDevice(api)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
forceCompute := os.Getenv("GIORENDERER") == "forcecompute"
|
||||
feats := ctx.Caps().Features
|
||||
feats := d.Caps().Features
|
||||
switch {
|
||||
case !forceCompute && feats.Has(backend.FeatureFloatRenderTargets):
|
||||
return newGPU(ctx)
|
||||
return newGPU(d)
|
||||
case feats.Has(backend.FeatureCompute):
|
||||
return newCompute(ctx)
|
||||
return newCompute(d)
|
||||
default:
|
||||
return nil, errors.New("gpu: no support for float render targets nor compute")
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user