@@ -40,22 +40,21 @@ export interface TgpuBuffer<TData extends AnyData> extends TgpuNamable {
4040 readonly label : string | undefined ;
4141
4242 readonly buffer : GPUBuffer ;
43- readonly device : GPUDevice ;
4443 readonly destroyed : boolean ;
4544
4645 $usage < T extends ( 'uniform' | 'storage' | 'vertex' ) [ ] > (
4746 ...usages : T
4847 ) : this & UnionToIntersection < LiteralToUsageType < T [ number ] > > ;
4948 $addFlags ( flags : GPUBufferUsageFlags ) : this;
50- $device ( device : GPUDevice ) : this;
5149
52- write ( data : Infer < TData > | TgpuBuffer < TData > ) : void ;
50+ write ( data : Infer < TData > ) : void ;
51+ copyFrom ( srcBuffer : TgpuBuffer < TData > ) : void ;
5352 read ( ) : Promise < Infer < TData > > ;
5453 destroy ( ) : void ;
5554}
5655
57- export function createBufferImpl < TData extends AnyData > (
58- group : ExperimentalTgpuRoot | undefined ,
56+ export function INTERNAL_createBuffer < TData extends AnyData > (
57+ group : ExperimentalTgpuRoot ,
5958 typeSchema : TData ,
6059 initialOrBuffer ?: Infer < TData > | GPUBuffer ,
6160) : TgpuBuffer < TData > {
@@ -88,8 +87,8 @@ class TgpuBufferImpl<TData extends AnyData> implements TgpuBuffer<TData> {
8887 public readonly resourceType = 'buffer' ;
8988 public flags : GPUBufferUsageFlags =
9089 GPUBufferUsage . COPY_DST | GPUBufferUsage . COPY_SRC ;
91- private _device : GPUDevice | null = null ;
9290 private _buffer : GPUBuffer | null = null ;
91+ private _ownBuffer : boolean ;
9392 private _destroyed = false ;
9493
9594 private _label : string | undefined ;
@@ -100,13 +99,15 @@ class TgpuBufferImpl<TData extends AnyData> implements TgpuBuffer<TData> {
10099 public usableAsVertex = false ;
101100
102101 constructor (
103- private readonly _group : ExperimentalTgpuRoot | undefined ,
102+ private readonly _group : ExperimentalTgpuRoot ,
104103 public readonly dataType : TData ,
105104 public readonly initialOrBuffer ?: Infer < TData > | GPUBuffer | undefined ,
106105 ) {
107106 if ( isGPUBuffer ( initialOrBuffer ) ) {
107+ this . _ownBuffer = false ;
108108 this . _buffer = initialOrBuffer ;
109109 } else {
110+ this . _ownBuffer = true ;
110111 this . initial = initialOrBuffer ;
111112 }
112113 }
@@ -116,18 +117,14 @@ class TgpuBufferImpl<TData extends AnyData> implements TgpuBuffer<TData> {
116117 }
117118
118119 get buffer ( ) {
119- if ( ! this . _device ) {
120- throw new Error (
121- 'Create this buffer using `root.createBuffer` instead of `tgpu.createBuffer`.' ,
122- ) ;
123- }
120+ const device = this . _group . device ;
124121
125122 if ( this . _destroyed ) {
126123 throw new Error ( 'This buffer has been destroyed' ) ;
127124 }
128125
129126 if ( ! this . _buffer ) {
130- this . _buffer = this . _device . createBuffer ( {
127+ this . _buffer = device . createBuffer ( {
131128 size : sizeOf ( this . dataType ) ,
132129 usage : this . flags ,
133130 mappedAtCreation : ! ! this . initial ,
@@ -144,15 +141,6 @@ class TgpuBufferImpl<TData extends AnyData> implements TgpuBuffer<TData> {
144141 return this . _buffer ;
145142 }
146143
147- get device ( ) {
148- if ( ! this . _device ) {
149- throw new Error (
150- 'This buffer has not been assigned a device. Use .$device(device) to assign a device' ,
151- ) ;
152- }
153- return this . _device ;
154- }
155-
156144 get destroyed ( ) {
157145 return this . _destroyed ;
158146 }
@@ -185,56 +173,42 @@ class TgpuBufferImpl<TData extends AnyData> implements TgpuBuffer<TData> {
185173 return this ;
186174 }
187175
188- $device ( device : GPUDevice ) {
189- this . _device = device ;
190- return this ;
191- }
192-
193- write ( dataOrBuffer : Infer < TData > | TgpuBuffer < TData > ) : void {
176+ write ( data : Infer < TData > ) : void {
194177 const gpuBuffer = this . buffer ;
195- const device = this . device ;
178+ const device = this . _group . device ;
196179
197180 if ( gpuBuffer . mapState === 'mapped' ) {
198181 const mapped = gpuBuffer . getMappedRange ( ) ;
199- if ( isBuffer ( dataOrBuffer ) ) {
200- throw new Error ( 'Cannot copy to a mapped buffer.' ) ;
201- }
202- writeData ( new BufferWriter ( mapped ) , this . dataType , dataOrBuffer ) ;
182+ writeData ( new BufferWriter ( mapped ) , this . dataType , data ) ;
203183 return ;
204184 }
205185
206186 const size = sizeOf ( this . dataType ) ;
207- if ( isBuffer ( dataOrBuffer ) ) {
208- const sourceBuffer = dataOrBuffer . buffer ;
209-
210- if ( this . _group ) {
211- const encoder = this . _group . commandEncoder ;
212- encoder . copyBufferToBuffer ( sourceBuffer , 0 , gpuBuffer , 0 , size ) ;
213- } else {
214- const commandEncoder = device . createCommandEncoder ( ) ;
215- commandEncoder . copyBufferToBuffer ( sourceBuffer , 0 , gpuBuffer , 0 , size ) ;
216- device . queue . submit ( [ commandEncoder . finish ( ) ] ) ;
217- }
218- } else {
219- if ( this . _group ) {
220- // Flushing any commands yet to be encoded.
221- this . _group . flush ( ) ;
222- }
223187
224- const hostBuffer = new ArrayBuffer ( size ) ;
225- writeData ( new BufferWriter ( hostBuffer ) , this . dataType , dataOrBuffer ) ;
226- device . queue . writeBuffer ( gpuBuffer , 0 , hostBuffer , 0 , size ) ;
188+ // Flushing any commands yet to be encoded.
189+ this . _group . flush ( ) ;
190+
191+ const hostBuffer = new ArrayBuffer ( size ) ;
192+ writeData ( new BufferWriter ( hostBuffer ) , this . dataType , data ) ;
193+ device . queue . writeBuffer ( gpuBuffer , 0 , hostBuffer , 0 , size ) ;
194+ }
195+
196+ copyFrom ( srcBuffer : TgpuBuffer < TData > ) : void {
197+ if ( this . buffer . mapState === 'mapped' ) {
198+ throw new Error ( 'Cannot copy to a mapped buffer.' ) ;
227199 }
200+
201+ const size = sizeOf ( this . dataType ) ;
202+ const encoder = this . _group . commandEncoder ;
203+ encoder . copyBufferToBuffer ( srcBuffer . buffer , 0 , this . buffer , 0 , size ) ;
228204 }
229205
230206 async read ( ) : Promise < Infer < TData > > {
231- if ( this . _group ) {
232- // Flushing any commands yet to be encoded.
233- this . _group . flush ( ) ;
234- }
207+ // Flushing any commands yet to be encoded.
208+ this . _group . flush ( ) ;
235209
236210 const gpuBuffer = this . buffer ;
237- const device = this . device ;
211+ const device = this . _group . device ;
238212
239213 if ( gpuBuffer . mapState === 'mapped' ) {
240214 const mapped = gpuBuffer . getMappedRange ( ) ;
@@ -283,7 +257,9 @@ class TgpuBufferImpl<TData extends AnyData> implements TgpuBuffer<TData> {
283257 return ;
284258 }
285259 this . _destroyed = true ;
286- this . _buffer ?. destroy ( ) ;
260+ if ( this . _ownBuffer ) {
261+ this . _buffer ?. destroy ( ) ;
262+ }
287263 }
288264
289265 toString ( ) : string {
0 commit comments