1use std::borrow::Cow;
6use std::fmt;
7use std::num::{NonZeroU32, NonZeroU64};
8use std::ops::Deref;
9
10use base::Epoch;
11pub use base::generic_channel::GenericReceiver as WebGLReceiver;
13pub use base::generic_channel::GenericSender as WebGLSender;
15pub use base::generic_channel::SendResult as WebGLSendResult;
17use base::id::PainterId;
18use euclid::default::{Rect, Size2D};
19use glow::{
20 self as gl, NativeBuffer, NativeFence, NativeFramebuffer, NativeProgram, NativeQuery,
21 NativeRenderbuffer, NativeSampler, NativeShader, NativeTexture, NativeVertexArray,
22};
23use ipc_channel::ipc::{IpcBytesReceiver, IpcBytesSender, IpcSender, IpcSharedMemory};
24use malloc_size_of_derive::MallocSizeOf;
25use pixels::{PixelFormat, SnapshotAlphaMode};
26use serde::{Deserialize, Serialize};
27use webrender_api::ImageKey;
28use webxr_api::{
29 ContextId as WebXRContextId, Error as WebXRError, LayerId as WebXRLayerId,
30 LayerInit as WebXRLayerInit, SubImages as WebXRSubImages,
31};
32
33pub fn webgl_channel<T>() -> Option<(WebGLSender<T>, WebGLReceiver<T>)>
35where
36 T: for<'de> Deserialize<'de> + Serialize,
37{
38 base::generic_channel::channel()
39}
40
41#[derive(Clone, Debug, Deserialize, Serialize)]
43pub struct WebGLChan(pub WebGLSender<WebGLMsg>);
44
45impl WebGLChan {
46 #[inline]
47 pub fn send(&self, msg: WebGLMsg) -> WebGLSendResult {
48 self.0.send(msg)
49 }
50}
51
52#[derive(Clone, Debug, Deserialize, Serialize)]
54pub struct WebGLPipeline(pub WebGLChan);
55
56impl WebGLPipeline {
57 pub fn channel(&self) -> WebGLChan {
58 self.0.clone()
59 }
60}
61
62#[derive(Clone, Debug, Deserialize, Serialize)]
63pub struct WebGLCommandBacktrace {
64 #[cfg(feature = "webgl_backtrace")]
65 pub backtrace: String,
66 #[cfg(feature = "webgl_backtrace")]
67 pub js_backtrace: Option<String>,
68}
69
70#[derive(Clone)]
72pub struct WebGLThreads(pub WebGLSender<WebGLMsg>);
73
74impl WebGLThreads {
75 pub fn pipeline(&self) -> WebGLPipeline {
77 WebGLPipeline(WebGLChan(self.0.clone()))
79 }
80
81 pub fn exit(&self, sender: IpcSender<()>) -> WebGLSendResult {
83 self.0.send(WebGLMsg::Exit(sender))
84 }
85
86 pub fn finished_rendering_to_context(&self, context_id: WebGLContextId) -> WebGLSendResult {
89 self.0
90 .send(WebGLMsg::FinishedRenderingToContext(context_id))
91 }
92}
93
94#[derive(Debug, Deserialize, Serialize)]
96pub enum WebGLMsg {
97 CreateContext(
99 PainterId,
100 WebGLVersion,
101 Size2D<u32>,
102 GLContextAttributes,
103 WebGLSender<Result<WebGLCreateContextResult, String>>,
104 ),
105 SetImageKey(WebGLContextId, ImageKey),
107 ResizeContext(WebGLContextId, Size2D<u32>, WebGLSender<Result<(), String>>),
109 RemoveContext(WebGLContextId),
111 WebGLCommand(WebGLContextId, WebGLCommand, WebGLCommandBacktrace),
113 WebXRCommand(WebXRCommand),
116 SwapBuffers(Vec<WebGLContextId>, Option<Epoch>, u64),
122 FinishedRenderingToContext(WebGLContextId),
126 Exit(IpcSender<()>),
128}
129
130#[derive(Clone, Copy, Debug, Deserialize, MallocSizeOf, PartialEq, Serialize)]
131pub enum GlType {
132 Gl,
133 Gles,
134}
135
136#[derive(Clone, Debug, Deserialize, Serialize)]
138pub struct WebGLCreateContextResult {
139 pub sender: WebGLMsgSender,
141 pub limits: GLLimits,
143 pub glsl_version: WebGLSLVersion,
145 pub api_type: GlType,
147}
148
149#[derive(Clone, Copy, Debug, Deserialize, Eq, MallocSizeOf, PartialEq, PartialOrd, Serialize)]
151pub enum WebGLVersion {
152 WebGL1,
155 WebGL2,
158}
159
160#[derive(
162 Clone, Copy, Debug, Deserialize, Eq, MallocSizeOf, Ord, PartialEq, PartialOrd, Serialize,
163)]
164pub struct WebGLSLVersion {
165 pub major: u32,
167 pub minor: u32,
169}
170
171#[derive(Clone, Debug, Deserialize, MallocSizeOf, Serialize)]
173pub struct WebGLMsgSender {
174 ctx_id: WebGLContextId,
175 #[ignore_malloc_size_of = "channels are hard"]
176 sender: WebGLChan,
177}
178
179impl WebGLMsgSender {
180 pub fn new(id: WebGLContextId, sender: WebGLChan) -> Self {
181 WebGLMsgSender { ctx_id: id, sender }
182 }
183
184 pub fn context_id(&self) -> WebGLContextId {
186 self.ctx_id
187 }
188
189 #[inline]
191 pub fn send(&self, command: WebGLCommand, backtrace: WebGLCommandBacktrace) -> WebGLSendResult {
192 self.sender
193 .send(WebGLMsg::WebGLCommand(self.ctx_id, command, backtrace))
194 }
195
196 #[inline]
198 pub fn set_image_key(&self, image_key: ImageKey) {
199 let _ = self
200 .sender
201 .send(WebGLMsg::SetImageKey(self.ctx_id, image_key));
202 }
203
204 #[inline]
206 pub fn send_resize(
207 &self,
208 size: Size2D<u32>,
209 sender: WebGLSender<Result<(), String>>,
210 ) -> WebGLSendResult {
211 self.sender
212 .send(WebGLMsg::ResizeContext(self.ctx_id, size, sender))
213 }
214
215 #[inline]
216 pub fn send_remove(&self) -> WebGLSendResult {
217 self.sender.send(WebGLMsg::RemoveContext(self.ctx_id))
218 }
219}
220
221#[derive(Deserialize, Serialize)]
222pub struct TruncatedDebug<T>(T);
223
224impl<T> From<T> for TruncatedDebug<T> {
225 fn from(v: T) -> TruncatedDebug<T> {
226 TruncatedDebug(v)
227 }
228}
229
230impl<T: fmt::Debug> fmt::Debug for TruncatedDebug<T> {
231 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
232 let mut s = format!("{:?}", self.0);
233 if s.len() > 20 {
234 s.truncate(20);
235 s.push_str("...");
236 }
237 write!(f, "{}", s)
238 }
239}
240
241impl<T> Deref for TruncatedDebug<T> {
242 type Target = T;
243 fn deref(&self) -> &T {
244 &self.0
245 }
246}
247
248#[derive(Debug, Deserialize, Serialize)]
250pub enum WebGLCommand {
251 GetContextAttributes(WebGLSender<GLContextAttributes>),
252 ActiveTexture(u32),
253 BlendColor(f32, f32, f32, f32),
254 BlendEquation(u32),
255 BlendEquationSeparate(u32, u32),
256 BlendFunc(u32, u32),
257 BlendFuncSeparate(u32, u32, u32, u32),
258 AttachShader(WebGLProgramId, WebGLShaderId),
259 DetachShader(WebGLProgramId, WebGLShaderId),
260 BindAttribLocation(WebGLProgramId, u32, String),
261 BufferData(u32, IpcBytesReceiver, u32),
262 BufferSubData(u32, isize, IpcBytesReceiver),
263 GetBufferSubData(u32, usize, usize, IpcBytesSender),
264 CopyBufferSubData(u32, u32, i64, i64, i64),
265 Clear(u32),
266 ClearColor(f32, f32, f32, f32),
267 ClearDepth(f32),
268 ClearStencil(i32),
269 ColorMask(bool, bool, bool, bool),
270 CullFace(u32),
271 FrontFace(u32),
272 DepthFunc(u32),
273 DepthMask(bool),
274 DepthRange(f32, f32),
275 Enable(u32),
276 Disable(u32),
277 CompileShader(WebGLShaderId, String),
278 CopyTexImage2D(u32, i32, u32, i32, i32, i32, i32, i32),
279 CopyTexSubImage2D(u32, i32, i32, i32, i32, i32, i32, i32),
280 CreateBuffer(WebGLSender<Option<WebGLBufferId>>),
281 CreateFramebuffer(WebGLSender<Option<WebGLFramebufferId>>),
282 CreateRenderbuffer(WebGLSender<Option<WebGLRenderbufferId>>),
283 CreateTexture(WebGLSender<Option<WebGLTextureId>>),
284 CreateProgram(WebGLSender<Option<WebGLProgramId>>),
285 CreateShader(u32, WebGLSender<Option<WebGLShaderId>>),
286 DeleteBuffer(WebGLBufferId),
287 DeleteFramebuffer(WebGLFramebufferId),
288 DeleteRenderbuffer(WebGLRenderbufferId),
289 DeleteTexture(WebGLTextureId),
290 DeleteProgram(WebGLProgramId),
291 DeleteShader(WebGLShaderId),
292 BindBuffer(u32, Option<WebGLBufferId>),
293 BindFramebuffer(u32, WebGLFramebufferBindingRequest),
294 BindRenderbuffer(u32, Option<WebGLRenderbufferId>),
295 BindTexture(u32, Option<WebGLTextureId>),
296 BlitFrameBuffer(i32, i32, i32, i32, i32, i32, i32, i32, u32, u32),
297 DisableVertexAttribArray(u32),
298 EnableVertexAttribArray(u32),
299 FramebufferRenderbuffer(u32, u32, u32, Option<WebGLRenderbufferId>),
300 FramebufferTexture2D(u32, u32, u32, Option<WebGLTextureId>, i32),
301 GetExtensions(WebGLSender<String>),
302 GetShaderPrecisionFormat(u32, u32, WebGLSender<(i32, i32, i32)>),
303 GetFragDataLocation(WebGLProgramId, String, WebGLSender<i32>),
304 GetUniformLocation(WebGLProgramId, String, WebGLSender<i32>),
305 GetShaderInfoLog(WebGLShaderId, WebGLSender<String>),
306 GetProgramInfoLog(WebGLProgramId, WebGLSender<String>),
307 GetFramebufferAttachmentParameter(u32, u32, u32, WebGLSender<i32>),
308 GetRenderbufferParameter(u32, u32, WebGLSender<i32>),
309 CreateTransformFeedback(WebGLSender<u32>),
310 DeleteTransformFeedback(u32),
311 IsTransformFeedback(u32, WebGLSender<bool>),
312 BindTransformFeedback(u32, u32),
313 BeginTransformFeedback(u32),
314 EndTransformFeedback(),
315 PauseTransformFeedback(),
316 ResumeTransformFeedback(),
317 GetTransformFeedbackVarying(WebGLProgramId, u32, WebGLSender<(i32, u32, String)>),
318 TransformFeedbackVaryings(WebGLProgramId, Vec<String>, u32),
319 PolygonOffset(f32, f32),
320 RenderbufferStorage(u32, u32, i32, i32),
321 RenderbufferStorageMultisample(u32, i32, u32, i32, i32),
322 ReadPixels(
323 Rect<u32>,
324 u32,
325 u32,
326 IpcSender<(IpcSharedMemory, SnapshotAlphaMode)>,
327 ),
328 ReadPixelsPP(Rect<i32>, u32, u32, usize),
329 SampleCoverage(f32, bool),
330 Scissor(i32, i32, u32, u32),
331 StencilFunc(u32, i32, u32),
332 StencilFuncSeparate(u32, u32, i32, u32),
333 StencilMask(u32),
334 StencilMaskSeparate(u32, u32),
335 StencilOp(u32, u32, u32),
336 StencilOpSeparate(u32, u32, u32, u32),
337 FenceSync(WebGLSender<WebGLSyncId>),
338 IsSync(WebGLSyncId, WebGLSender<bool>),
339 ClientWaitSync(WebGLSyncId, u32, u64, WebGLSender<u32>),
340 WaitSync(WebGLSyncId, u32, i64),
341 GetSyncParameter(WebGLSyncId, u32, WebGLSender<u32>),
342 DeleteSync(WebGLSyncId),
343 Hint(u32, u32),
344 LineWidth(f32),
345 PixelStorei(u32, i32),
346 LinkProgram(WebGLProgramId, WebGLSender<ProgramLinkInfo>),
347 Uniform1f(i32, f32),
348 Uniform1fv(i32, Vec<f32>),
349 Uniform1i(i32, i32),
350 Uniform1ui(i32, u32),
351 Uniform1iv(i32, Vec<i32>),
352 Uniform1uiv(i32, Vec<u32>),
353 Uniform2f(i32, f32, f32),
354 Uniform2fv(i32, Vec<f32>),
355 Uniform2i(i32, i32, i32),
356 Uniform2ui(i32, u32, u32),
357 Uniform2iv(i32, Vec<i32>),
358 Uniform2uiv(i32, Vec<u32>),
359 Uniform3f(i32, f32, f32, f32),
360 Uniform3fv(i32, Vec<f32>),
361 Uniform3i(i32, i32, i32, i32),
362 Uniform3ui(i32, u32, u32, u32),
363 Uniform3iv(i32, Vec<i32>),
364 Uniform3uiv(i32, Vec<u32>),
365 Uniform4f(i32, f32, f32, f32, f32),
366 Uniform4fv(i32, Vec<f32>),
367 Uniform4i(i32, i32, i32, i32, i32),
368 Uniform4ui(i32, u32, u32, u32, u32),
369 Uniform4iv(i32, Vec<i32>),
370 Uniform4uiv(i32, Vec<u32>),
371 UniformMatrix2fv(i32, Vec<f32>),
372 UniformMatrix3fv(i32, Vec<f32>),
373 UniformMatrix4fv(i32, Vec<f32>),
374 UniformMatrix3x2fv(i32, Vec<f32>),
375 UniformMatrix4x2fv(i32, Vec<f32>),
376 UniformMatrix2x3fv(i32, Vec<f32>),
377 UniformMatrix4x3fv(i32, Vec<f32>),
378 UniformMatrix2x4fv(i32, Vec<f32>),
379 UniformMatrix3x4fv(i32, Vec<f32>),
380 UseProgram(Option<WebGLProgramId>),
381 ValidateProgram(WebGLProgramId),
382 VertexAttrib(u32, f32, f32, f32, f32),
383 VertexAttribI(u32, i32, i32, i32, i32),
384 VertexAttribU(u32, u32, u32, u32, u32),
385 VertexAttribPointer(u32, i32, u32, bool, i32, u32),
386 VertexAttribPointer2f(u32, i32, bool, i32, u32),
387 SetViewport(i32, i32, i32, i32),
388 TexImage3D {
389 target: u32,
390 level: u32,
391 internal_format: TexFormat,
392 size: Size2D<u32>,
393 depth: u32,
394 format: TexFormat,
395 data_type: TexDataType,
396 effective_data_type: u32,
398 unpacking_alignment: u32,
399 alpha_treatment: Option<AlphaTreatment>,
400 y_axis_treatment: YAxisTreatment,
401 pixel_format: Option<PixelFormat>,
402 data: TruncatedDebug<IpcSharedMemory>,
403 },
404 TexImage2D {
405 target: u32,
406 level: u32,
407 internal_format: TexFormat,
408 size: Size2D<u32>,
409 format: TexFormat,
410 data_type: TexDataType,
411 effective_data_type: u32,
413 unpacking_alignment: u32,
414 alpha_treatment: Option<AlphaTreatment>,
415 y_axis_treatment: YAxisTreatment,
416 pixel_format: Option<PixelFormat>,
417 data: TruncatedDebug<IpcSharedMemory>,
418 },
419 TexImage2DPBO {
420 target: u32,
421 level: u32,
422 internal_format: TexFormat,
423 size: Size2D<u32>,
424 format: TexFormat,
425 effective_data_type: u32,
426 unpacking_alignment: u32,
427 offset: i64,
428 },
429 TexSubImage2D {
430 target: u32,
431 level: u32,
432 xoffset: i32,
433 yoffset: i32,
434 size: Size2D<u32>,
435 format: TexFormat,
436 data_type: TexDataType,
437 effective_data_type: u32,
439 unpacking_alignment: u32,
440 alpha_treatment: Option<AlphaTreatment>,
441 y_axis_treatment: YAxisTreatment,
442 pixel_format: Option<PixelFormat>,
443 data: TruncatedDebug<IpcSharedMemory>,
444 },
445 CompressedTexImage2D {
446 target: u32,
447 level: u32,
448 internal_format: u32,
449 size: Size2D<u32>,
450 data: TruncatedDebug<IpcSharedMemory>,
451 },
452 CompressedTexSubImage2D {
453 target: u32,
454 level: i32,
455 xoffset: i32,
456 yoffset: i32,
457 size: Size2D<u32>,
458 format: u32,
459 data: TruncatedDebug<IpcSharedMemory>,
460 },
461 DrawingBufferWidth(WebGLSender<i32>),
462 DrawingBufferHeight(WebGLSender<i32>),
463 Finish(WebGLSender<()>),
464 Flush,
465 GenerateMipmap(u32),
466 CreateVertexArray(WebGLSender<Option<WebGLVertexArrayId>>),
467 DeleteVertexArray(WebGLVertexArrayId),
468 BindVertexArray(Option<WebGLVertexArrayId>),
469 GetParameterBool(ParameterBool, WebGLSender<bool>),
470 GetParameterBool4(ParameterBool4, WebGLSender<[bool; 4]>),
471 GetParameterInt(ParameterInt, WebGLSender<i32>),
472 GetParameterInt2(ParameterInt2, WebGLSender<[i32; 2]>),
473 GetParameterInt4(ParameterInt4, WebGLSender<[i32; 4]>),
474 GetParameterFloat(ParameterFloat, WebGLSender<f32>),
475 GetParameterFloat2(ParameterFloat2, WebGLSender<[f32; 2]>),
476 GetParameterFloat4(ParameterFloat4, WebGLSender<[f32; 4]>),
477 GetProgramValidateStatus(WebGLProgramId, WebGLSender<bool>),
478 GetProgramActiveUniforms(WebGLProgramId, WebGLSender<i32>),
479 GetCurrentVertexAttrib(u32, WebGLSender<[f32; 4]>),
480 GetTexParameterFloat(u32, TexParameterFloat, WebGLSender<f32>),
481 GetTexParameterInt(u32, TexParameterInt, WebGLSender<i32>),
482 GetTexParameterBool(u32, TexParameterBool, WebGLSender<bool>),
483 GetInternalFormatIntVec(u32, u32, InternalFormatIntVec, WebGLSender<Vec<i32>>),
484 TexParameteri(u32, u32, i32),
485 TexParameterf(u32, u32, f32),
486 TexStorage2D(u32, u32, TexFormat, u32, u32),
487 TexStorage3D(u32, u32, TexFormat, u32, u32, u32),
488 DrawArrays {
489 mode: u32,
490 first: i32,
491 count: i32,
492 },
493 DrawArraysInstanced {
494 mode: u32,
495 first: i32,
496 count: i32,
497 primcount: i32,
498 },
499 DrawElements {
500 mode: u32,
501 count: i32,
502 type_: u32,
503 offset: u32,
504 },
505 DrawElementsInstanced {
506 mode: u32,
507 count: i32,
508 type_: u32,
509 offset: u32,
510 primcount: i32,
511 },
512 VertexAttribDivisor {
513 index: u32,
514 divisor: u32,
515 },
516 GetUniformBool(WebGLProgramId, i32, WebGLSender<bool>),
517 GetUniformBool2(WebGLProgramId, i32, WebGLSender<[bool; 2]>),
518 GetUniformBool3(WebGLProgramId, i32, WebGLSender<[bool; 3]>),
519 GetUniformBool4(WebGLProgramId, i32, WebGLSender<[bool; 4]>),
520 GetUniformInt(WebGLProgramId, i32, WebGLSender<i32>),
521 GetUniformInt2(WebGLProgramId, i32, WebGLSender<[i32; 2]>),
522 GetUniformInt3(WebGLProgramId, i32, WebGLSender<[i32; 3]>),
523 GetUniformInt4(WebGLProgramId, i32, WebGLSender<[i32; 4]>),
524 GetUniformUint(WebGLProgramId, i32, WebGLSender<u32>),
525 GetUniformUint2(WebGLProgramId, i32, WebGLSender<[u32; 2]>),
526 GetUniformUint3(WebGLProgramId, i32, WebGLSender<[u32; 3]>),
527 GetUniformUint4(WebGLProgramId, i32, WebGLSender<[u32; 4]>),
528 GetUniformFloat(WebGLProgramId, i32, WebGLSender<f32>),
529 GetUniformFloat2(WebGLProgramId, i32, WebGLSender<[f32; 2]>),
530 GetUniformFloat3(WebGLProgramId, i32, WebGLSender<[f32; 3]>),
531 GetUniformFloat4(WebGLProgramId, i32, WebGLSender<[f32; 4]>),
532 GetUniformFloat9(WebGLProgramId, i32, WebGLSender<[f32; 9]>),
533 GetUniformFloat16(WebGLProgramId, i32, WebGLSender<[f32; 16]>),
534 GetUniformFloat2x3(WebGLProgramId, i32, WebGLSender<[f32; 2 * 3]>),
535 GetUniformFloat2x4(WebGLProgramId, i32, WebGLSender<[f32; 2 * 4]>),
536 GetUniformFloat3x2(WebGLProgramId, i32, WebGLSender<[f32; 3 * 2]>),
537 GetUniformFloat3x4(WebGLProgramId, i32, WebGLSender<[f32; 3 * 4]>),
538 GetUniformFloat4x2(WebGLProgramId, i32, WebGLSender<[f32; 4 * 2]>),
539 GetUniformFloat4x3(WebGLProgramId, i32, WebGLSender<[f32; 4 * 3]>),
540 GetUniformBlockIndex(WebGLProgramId, String, WebGLSender<u32>),
541 GetUniformIndices(WebGLProgramId, Vec<String>, WebGLSender<Vec<u32>>),
542 GetActiveUniforms(WebGLProgramId, Vec<u32>, u32, WebGLSender<Vec<i32>>),
543 GetActiveUniformBlockName(WebGLProgramId, u32, WebGLSender<String>),
544 GetActiveUniformBlockParameter(WebGLProgramId, u32, u32, WebGLSender<Vec<i32>>),
545 UniformBlockBinding(WebGLProgramId, u32, u32),
546 InitializeFramebuffer {
547 color: bool,
548 depth: bool,
549 stencil: bool,
550 },
551 BeginQuery(u32, WebGLQueryId),
552 DeleteQuery(WebGLQueryId),
553 EndQuery(u32),
554 GenerateQuery(WebGLSender<WebGLQueryId>),
555 GetQueryState(WebGLSender<u32>, WebGLQueryId, u32),
556 GenerateSampler(WebGLSender<WebGLSamplerId>),
557 DeleteSampler(WebGLSamplerId),
558 BindSampler(u32, WebGLSamplerId),
559 SetSamplerParameterFloat(WebGLSamplerId, u32, f32),
560 SetSamplerParameterInt(WebGLSamplerId, u32, i32),
561 GetSamplerParameterFloat(WebGLSamplerId, u32, WebGLSender<f32>),
562 GetSamplerParameterInt(WebGLSamplerId, u32, WebGLSender<i32>),
563 BindBufferBase(u32, u32, Option<WebGLBufferId>),
564 BindBufferRange(u32, u32, Option<WebGLBufferId>, i64, i64),
565 ClearBufferfv(u32, i32, Vec<f32>),
566 ClearBufferiv(u32, i32, Vec<i32>),
567 ClearBufferuiv(u32, i32, Vec<u32>),
568 ClearBufferfi(u32, i32, f32, i32),
569 InvalidateFramebuffer(u32, Vec<u32>),
570 InvalidateSubFramebuffer(u32, Vec<u32>, i32, i32, i32, i32),
571 FramebufferTextureLayer(u32, u32, Option<WebGLTextureId>, i32, i32),
572 ReadBuffer(u32),
573 DrawBuffers(Vec<u32>),
574}
575
576#[derive(Debug, Deserialize, Serialize)]
578pub enum WebXRCommand {
579 CreateLayerManager(WebGLSender<Result<WebXRLayerManagerId, WebXRError>>),
580 DestroyLayerManager(WebXRLayerManagerId),
581 CreateLayer(
582 WebXRLayerManagerId,
583 WebXRContextId,
584 WebXRLayerInit,
585 WebGLSender<Result<WebXRLayerId, WebXRError>>,
586 ),
587 DestroyLayer(WebXRLayerManagerId, WebXRContextId, WebXRLayerId),
588 BeginFrame(
589 WebXRLayerManagerId,
590 Vec<(WebXRContextId, WebXRLayerId)>,
591 WebGLSender<Result<Vec<WebXRSubImages>, WebXRError>>,
592 ),
593 EndFrame(
594 WebXRLayerManagerId,
595 Vec<(WebXRContextId, WebXRLayerId)>,
596 WebGLSender<Result<(), WebXRError>>,
597 ),
598}
599
600macro_rules! nonzero_type {
601 (u32) => {
602 NonZeroU32
603 };
604 (u64) => {
605 NonZeroU64
606 };
607}
608
609macro_rules! define_resource_id {
610 ($name:ident, $type:tt) => {
611 #[derive(Clone, Copy, Eq, Hash, PartialEq)]
612 pub struct $name(nonzero_type!($type));
613
614 impl $name {
615 #[inline]
616 pub fn new(id: nonzero_type!($type)) -> Self {
617 Self(id)
618 }
619
620 #[inline]
621 pub fn maybe_new(id: $type) -> Option<Self> {
622 <nonzero_type!($type)>::new(id).map($name)
623 }
624
625 #[inline]
626 pub fn get(self) -> $type {
627 self.0.get()
628 }
629 }
630
631 impl<'de> ::serde::Deserialize<'de> for $name {
632 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
633 where
634 D: ::serde::Deserializer<'de>,
635 {
636 let id = <$type>::deserialize(deserializer)?;
637 if let Some(id) = <nonzero_type!($type)>::new(id) {
638 Ok($name(id))
639 } else {
640 Err(::serde::de::Error::custom("expected a non-zero value"))
641 }
642 }
643 }
644
645 impl ::serde::Serialize for $name {
646 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
647 where
648 S: ::serde::Serializer,
649 {
650 self.get().serialize(serializer)
651 }
652 }
653
654 impl ::std::fmt::Debug for $name {
655 fn fmt(&self, fmt: &mut ::std::fmt::Formatter) -> Result<(), ::std::fmt::Error> {
656 fmt.debug_tuple(stringify!($name))
657 .field(&self.get())
658 .finish()
659 }
660 }
661
662 impl ::std::fmt::Display for $name {
663 fn fmt(&self, fmt: &mut ::std::fmt::Formatter) -> Result<(), ::std::fmt::Error> {
664 write!(fmt, "{}", self.get())
665 }
666 }
667
668 impl ::malloc_size_of::MallocSizeOf for $name {
669 fn size_of(&self, _ops: &mut ::malloc_size_of::MallocSizeOfOps) -> usize {
670 0
671 }
672 }
673 };
674 ($name:ident, $type:tt, $glow:tt) => {
675 impl $name {
676 #[inline]
677 pub fn glow(self) -> $glow {
678 $glow(self.0)
679 }
680
681 #[inline]
682 pub fn from_glow(glow: $glow) -> Self {
683 Self(glow.0)
684 }
685 }
686 define_resource_id!($name, $type);
687 };
688}
689
690define_resource_id!(WebGLBufferId, u32, NativeBuffer);
691define_resource_id!(WebGLFramebufferId, u32, NativeFramebuffer);
692define_resource_id!(WebGLRenderbufferId, u32, NativeRenderbuffer);
693define_resource_id!(WebGLTextureId, u32, NativeTexture);
694define_resource_id!(WebGLProgramId, u32, NativeProgram);
695define_resource_id!(WebGLQueryId, u32, NativeQuery);
696define_resource_id!(WebGLSamplerId, u32, NativeSampler);
697define_resource_id!(WebGLShaderId, u32, NativeShader);
698define_resource_id!(WebGLSyncId, u64);
699impl WebGLSyncId {
700 #[inline]
701 pub fn glow(&self) -> NativeFence {
702 NativeFence(self.0.get() as _)
703 }
704
705 #[inline]
706 pub fn from_glow(glow: NativeFence) -> Self {
707 Self::maybe_new(glow.0 as _).expect("Glow should have valid fence")
708 }
709}
710define_resource_id!(WebGLVertexArrayId, u32, NativeVertexArray);
711define_resource_id!(WebXRLayerManagerId, u32);
712
713#[derive(
714 Clone, Copy, Debug, Deserialize, Eq, Hash, MallocSizeOf, Ord, PartialEq, PartialOrd, Serialize,
715)]
716pub struct WebGLContextId(pub u64);
717
718impl From<WebXRContextId> for WebGLContextId {
719 fn from(id: WebXRContextId) -> Self {
720 Self(id.0)
721 }
722}
723
724impl From<WebGLContextId> for WebXRContextId {
725 fn from(id: WebGLContextId) -> Self {
726 Self(id.0)
727 }
728}
729
730#[derive(Clone, Copy, Debug, Deserialize, PartialEq, Serialize)]
731pub enum WebGLError {
732 InvalidEnum,
733 InvalidFramebufferOperation,
734 InvalidOperation,
735 InvalidValue,
736 OutOfMemory,
737 ContextLost,
738}
739
740#[derive(Clone, Copy, Debug, Deserialize, Eq, PartialEq, Serialize)]
741pub enum WebGLFramebufferBindingRequest {
742 Explicit(WebGLFramebufferId),
743 Default,
744}
745
746pub type WebGLResult<T> = Result<T, WebGLError>;
747
748#[derive(Clone, Debug, Deserialize, Serialize)]
750pub struct ProgramLinkInfo {
751 pub linked: bool,
753 pub active_attribs: Box<[ActiveAttribInfo]>,
755 pub active_uniforms: Box<[ActiveUniformInfo]>,
757 pub active_uniform_blocks: Box<[ActiveUniformBlockInfo]>,
759 pub transform_feedback_length: i32,
761 pub transform_feedback_mode: i32,
763}
764
765#[derive(Clone, Debug, Deserialize, MallocSizeOf, Serialize)]
767pub struct ActiveAttribInfo {
768 pub name: String,
770 pub size: i32,
772 pub type_: u32,
774 pub location: Option<u32>,
776}
777
778#[derive(Clone, Debug, Deserialize, MallocSizeOf, Serialize)]
780pub struct ActiveUniformInfo {
781 pub base_name: Box<str>,
783 pub size: Option<i32>,
785 pub type_: u32,
787 pub bind_index: Option<u32>,
789}
790
791impl ActiveUniformInfo {
792 pub fn name(&self) -> Cow<'_, str> {
793 if self.size.is_some() {
794 let mut name = String::from(&*self.base_name);
795 name.push_str("[0]");
796 Cow::Owned(name)
797 } else {
798 Cow::Borrowed(&self.base_name)
799 }
800 }
801}
802
803#[derive(Clone, Debug, Deserialize, MallocSizeOf, Serialize)]
805pub struct ActiveUniformBlockInfo {
806 pub name: String,
808 pub size: i32,
810}
811
812macro_rules! parameters {
813 ($name:ident { $(
814 $variant:ident($kind:ident { $(
815 $param:ident = gl::$value:ident,
816 )+ }),
817 )+ }) => {
818 #[derive(Clone, Copy, Debug, Deserialize, Serialize)]
819 pub enum $name { $(
820 $variant($kind),
821 )+}
822
823 $(
824 #[derive(Clone, Copy, Debug, Deserialize, Serialize)]
825 #[repr(u32)]
826 pub enum $kind { $(
827 $param = gl::$value,
828 )+}
829 )+
830
831 impl $name {
832 pub fn from_u32(value: u32) -> WebGLResult<Self> {
833 match value {
834 $($(gl::$value => Ok($name::$variant($kind::$param)),)+)+
835 _ => Err(WebGLError::InvalidEnum)
836 }
837 }
838 }
839 }
840}
841
842parameters! {
843 Parameter {
844 Bool(ParameterBool {
845 DepthWritemask = gl::DEPTH_WRITEMASK,
846 SampleCoverageInvert = gl::SAMPLE_COVERAGE_INVERT,
847 TransformFeedbackActive = gl::TRANSFORM_FEEDBACK_ACTIVE,
848 TransformFeedbackPaused = gl::TRANSFORM_FEEDBACK_PAUSED,
849 RasterizerDiscard = gl::RASTERIZER_DISCARD,
850 }),
851 Bool4(ParameterBool4 {
852 ColorWritemask = gl::COLOR_WRITEMASK,
853 }),
854 Int(ParameterInt {
855 ActiveTexture = gl::ACTIVE_TEXTURE,
856 AlphaBits = gl::ALPHA_BITS,
857 BlendDstAlpha = gl::BLEND_DST_ALPHA,
858 BlendDstRgb = gl::BLEND_DST_RGB,
859 BlendEquationAlpha = gl::BLEND_EQUATION_ALPHA,
860 BlendEquationRgb = gl::BLEND_EQUATION_RGB,
861 BlendSrcAlpha = gl::BLEND_SRC_ALPHA,
862 BlendSrcRgb = gl::BLEND_SRC_RGB,
863 BlueBits = gl::BLUE_BITS,
864 CullFaceMode = gl::CULL_FACE_MODE,
865 DepthBits = gl::DEPTH_BITS,
866 DepthFunc = gl::DEPTH_FUNC,
867 FragmentShaderDerivativeHint = gl::FRAGMENT_SHADER_DERIVATIVE_HINT,
868 FrontFace = gl::FRONT_FACE,
869 GenerateMipmapHint = gl::GENERATE_MIPMAP_HINT,
870 GreenBits = gl::GREEN_BITS,
871 RedBits = gl::RED_BITS,
872 SampleBuffers = gl::SAMPLE_BUFFERS,
873 Samples = gl::SAMPLES,
874 StencilBackFail = gl::STENCIL_BACK_FAIL,
875 StencilBackFunc = gl::STENCIL_BACK_FUNC,
876 StencilBackPassDepthFail = gl::STENCIL_BACK_PASS_DEPTH_FAIL,
877 StencilBackPassDepthPass = gl::STENCIL_BACK_PASS_DEPTH_PASS,
878 StencilBackRef = gl::STENCIL_BACK_REF,
879 StencilBackValueMask = gl::STENCIL_BACK_VALUE_MASK,
880 StencilBackWritemask = gl::STENCIL_BACK_WRITEMASK,
881 StencilBits = gl::STENCIL_BITS,
882 StencilClearValue = gl::STENCIL_CLEAR_VALUE,
883 StencilFail = gl::STENCIL_FAIL,
884 StencilFunc = gl::STENCIL_FUNC,
885 StencilPassDepthFail = gl::STENCIL_PASS_DEPTH_FAIL,
886 StencilPassDepthPass = gl::STENCIL_PASS_DEPTH_PASS,
887 StencilRef = gl::STENCIL_REF,
888 StencilValueMask = gl::STENCIL_VALUE_MASK,
889 StencilWritemask = gl::STENCIL_WRITEMASK,
890 SubpixelBits = gl::SUBPIXEL_BITS,
891 TransformFeedbackBinding = gl::TRANSFORM_FEEDBACK_BINDING,
892 MaxTransformFeedbackInterleavedComponents = gl::MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS,
893 MaxTransformFeedbackSeparateAttribs = gl::MAX_TRANSFORM_FEEDBACK_SEPARATE_ATTRIBS,
894 MaxTransformFeedbackSeparateComponents = gl::MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS,
895 TransformFeedbackBufferSize = gl::TRANSFORM_FEEDBACK_BUFFER_SIZE,
896 TransformFeedbackBufferStart = gl::TRANSFORM_FEEDBACK_BUFFER_START,
897 PackRowLength = gl::PACK_ROW_LENGTH,
898 PackSkipPixels = gl::PACK_SKIP_PIXELS,
899 PackSkipRows = gl::PACK_SKIP_ROWS,
900 UnpackImageHeight = gl::UNPACK_IMAGE_HEIGHT,
901 UnpackRowLength = gl::UNPACK_ROW_LENGTH,
902 UnpackSkipImages = gl::UNPACK_SKIP_IMAGES,
903 UnpackSkipPixels = gl::UNPACK_SKIP_PIXELS,
904 UnpackSkipRows = gl::UNPACK_SKIP_ROWS,
905 }),
906 Int2(ParameterInt2 {
907 MaxViewportDims = gl::MAX_VIEWPORT_DIMS,
908 }),
909 Int4(ParameterInt4 {
910 ScissorBox = gl::SCISSOR_BOX,
911 Viewport = gl::VIEWPORT,
912 }),
913 Float(ParameterFloat {
914 DepthClearValue = gl::DEPTH_CLEAR_VALUE,
915 LineWidth = gl::LINE_WIDTH,
916 MaxTextureMaxAnisotropyExt = gl::MAX_TEXTURE_MAX_ANISOTROPY_EXT,
917 PolygonOffsetFactor = gl::POLYGON_OFFSET_FACTOR,
918 PolygonOffsetUnits = gl::POLYGON_OFFSET_UNITS,
919 SampleCoverageValue = gl::SAMPLE_COVERAGE_VALUE,
920 }),
921 Float2(ParameterFloat2 {
922 AliasedPointSizeRange = gl::ALIASED_POINT_SIZE_RANGE,
923 AliasedLineWidthRange = gl::ALIASED_LINE_WIDTH_RANGE,
924 DepthRange = gl::DEPTH_RANGE,
925 }),
926 Float4(ParameterFloat4 {
927 BlendColor = gl::BLEND_COLOR,
928 ColorClearValue = gl::COLOR_CLEAR_VALUE,
929 }),
930 }
931}
932
933parameters! {
934 TexParameter {
935 Float(TexParameterFloat {
936 TextureMaxAnisotropyExt = gl::TEXTURE_MAX_ANISOTROPY_EXT,
937 TextureMaxLod = gl::TEXTURE_MAX_LOD,
938 TextureMinLod = gl::TEXTURE_MIN_LOD,
939 }),
940 Int(TexParameterInt {
941 TextureWrapS = gl::TEXTURE_WRAP_S,
942 TextureWrapT = gl::TEXTURE_WRAP_T,
943 TextureWrapR = gl::TEXTURE_WRAP_R,
944 TextureBaseLevel = gl::TEXTURE_BASE_LEVEL,
945 TextureMinFilter = gl::TEXTURE_MIN_FILTER,
946 TextureMagFilter = gl::TEXTURE_MAG_FILTER,
947 TextureMaxLevel = gl::TEXTURE_MAX_LEVEL,
948 TextureCompareFunc = gl::TEXTURE_COMPARE_FUNC,
949 TextureCompareMode = gl::TEXTURE_COMPARE_MODE,
950 TextureImmutableLevels = gl::TEXTURE_IMMUTABLE_LEVELS,
951 }),
952 Bool(TexParameterBool {
953 TextureImmutableFormat = gl::TEXTURE_IMMUTABLE_FORMAT,
954 }),
955 }
956}
957
958impl TexParameter {
959 pub fn required_webgl_version(self) -> WebGLVersion {
960 match self {
961 Self::Float(TexParameterFloat::TextureMaxAnisotropyExt) |
962 Self::Int(TexParameterInt::TextureWrapS) |
963 Self::Int(TexParameterInt::TextureWrapT) => WebGLVersion::WebGL1,
964 _ => WebGLVersion::WebGL2,
965 }
966 }
967}
968
969parameters! {
970 InternalFormatParameter {
971 IntVec(InternalFormatIntVec {
972 Samples = gl::SAMPLES,
973 }),
974 }
975}
976
977#[macro_export]
978macro_rules! gl_enums {
979 ($(pub enum $name:ident { $($variant:ident = $mod:ident::$constant:ident,)+ })*) => {
980 $(
981 #[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, malloc_size_of_derive::MallocSizeOf)]
982 #[derive(PartialEq, Serialize)]
983 #[repr(u32)]
984 pub enum $name { $($variant = $mod::$constant,)+ }
985
986 impl $name {
987 pub fn from_gl_constant(constant: u32) -> Option<Self> {
988 Some(match constant {
989 $($mod::$constant => $name::$variant, )+
990 _ => return None,
991 })
992 }
993
994 #[inline]
995 pub fn as_gl_constant(&self) -> u32 {
996 *self as u32
997 }
998 }
999 )*
1000 }
1001}
1002
1003mod gl_ext_constants {
1005 pub const COMPRESSED_RGB_ETC1_WEBGL: u32 = 0x8D64;
1006
1007 pub const ALPHA16F_ARB: u32 = 0x881C;
1008 pub const ALPHA32F_ARB: u32 = 0x8816;
1009 pub const LUMINANCE16F_ARB: u32 = 0x881E;
1010 pub const LUMINANCE32F_ARB: u32 = 0x8818;
1011 pub const LUMINANCE_ALPHA16F_ARB: u32 = 0x881F;
1012 pub const LUMINANCE_ALPHA32F_ARB: u32 = 0x8819;
1013}
1014
1015gl_enums! {
1016 pub enum TexFormat {
1017 DepthComponent = gl::DEPTH_COMPONENT,
1018 DepthStencil = gl::DEPTH_STENCIL,
1019 Alpha = gl::ALPHA,
1020 Alpha32f = gl_ext_constants::ALPHA32F_ARB,
1021 Alpha16f = gl_ext_constants::ALPHA16F_ARB,
1022 Red = gl::RED,
1023 RedInteger = gl::RED_INTEGER,
1024 RG = gl::RG,
1025 RGInteger = gl::RG_INTEGER,
1026 RGB = gl::RGB,
1027 RGBInteger = gl::RGB_INTEGER,
1028 RGBA = gl::RGBA,
1029 RGBAInteger = gl::RGBA_INTEGER,
1030 Luminance = gl::LUMINANCE,
1031 LuminanceAlpha = gl::LUMINANCE_ALPHA,
1032 Luminance32f = gl_ext_constants::LUMINANCE32F_ARB,
1033 Luminance16f = gl_ext_constants::LUMINANCE16F_ARB,
1034 LuminanceAlpha32f = gl_ext_constants::LUMINANCE_ALPHA32F_ARB,
1035 LuminanceAlpha16f = gl_ext_constants::LUMINANCE_ALPHA16F_ARB,
1036 CompressedRgbS3tcDxt1 = gl::COMPRESSED_RGB_S3TC_DXT1_EXT,
1037 CompressedRgbaS3tcDxt1 = gl::COMPRESSED_RGBA_S3TC_DXT1_EXT,
1038 CompressedRgbaS3tcDxt3 = gl::COMPRESSED_RGBA_S3TC_DXT3_EXT,
1039 CompressedRgbaS3tcDxt5 = gl::COMPRESSED_RGBA_S3TC_DXT5_EXT,
1040 CompressedRgbEtc1 = gl_ext_constants::COMPRESSED_RGB_ETC1_WEBGL,
1041 R8 = gl::R8,
1042 R8SNorm = gl::R8_SNORM,
1043 R16f = gl::R16F,
1044 R32f = gl::R32F,
1045 R8ui = gl::R8UI,
1046 R8i = gl::R8I,
1047 R16ui = gl::R16UI,
1048 R16i = gl::R16I,
1049 R32ui = gl::R32UI,
1050 R32i = gl::R32I,
1051 RG8 = gl::RG8,
1052 RG8SNorm = gl::RG8_SNORM,
1053 RG16f = gl::RG16F,
1054 RG32f = gl::RG32F,
1055 RG8ui = gl::RG8UI,
1056 RG8i = gl::RG8I,
1057 RG16ui = gl::RG16UI,
1058 RG16i = gl::RG16I,
1059 RG32ui = gl::RG32UI,
1060 RG32i = gl::RG32I,
1061 RGB8 = gl::RGB8,
1062 SRGB8 = gl::SRGB8,
1063 RGB565 = gl::RGB565,
1064 RGB8SNorm = gl::RGB8_SNORM,
1065 R11fG11fB10f = gl::R11F_G11F_B10F,
1066 RGB9E5 = gl::RGB9_E5,
1067 RGB16f = gl::RGB16F,
1068 RGB32f = gl::RGB32F,
1069 RGB8ui = gl::RGB8UI,
1070 RGB8i = gl::RGB8I,
1071 RGB16ui = gl::RGB16UI,
1072 RGB16i = gl::RGB16I,
1073 RGB32ui = gl::RGB32UI,
1074 RGB32i = gl::RGB32I,
1075 RGBA8 = gl::RGBA8,
1076 SRGB8Alpha8 = gl::SRGB8_ALPHA8,
1077 RGBA8SNorm = gl::RGBA8_SNORM,
1078 RGB5A1 = gl::RGB5_A1,
1079 RGBA4 = gl::RGBA4,
1080 RGB10A2 = gl::RGB10_A2,
1081 RGBA16f = gl::RGBA16F,
1082 RGBA32f = gl::RGBA32F,
1083 RGBA8ui = gl::RGBA8UI,
1084 RGBA8i = gl::RGBA8I,
1085 RGB10A2ui = gl::RGB10_A2UI,
1086 RGBA16ui = gl::RGBA16UI,
1087 RGBA16i = gl::RGBA16I,
1088 RGBA32i = gl::RGBA32I,
1089 RGBA32ui = gl::RGBA32UI,
1090 DepthComponent16 = gl::DEPTH_COMPONENT16,
1091 DepthComponent24 = gl::DEPTH_COMPONENT24,
1092 DepthComponent32f = gl::DEPTH_COMPONENT32F,
1093 Depth24Stencil8 = gl::DEPTH24_STENCIL8,
1094 Depth32fStencil8 = gl::DEPTH32F_STENCIL8,
1095 }
1096
1097 pub enum TexDataType {
1098 Byte = gl::BYTE,
1099 Int = gl::INT,
1100 Short = gl::SHORT,
1101 UnsignedByte = gl::UNSIGNED_BYTE,
1102 UnsignedInt = gl::UNSIGNED_INT,
1103 UnsignedInt10f11f11fRev = gl::UNSIGNED_INT_10F_11F_11F_REV,
1104 UnsignedInt2101010Rev = gl::UNSIGNED_INT_2_10_10_10_REV,
1105 UnsignedInt5999Rev = gl::UNSIGNED_INT_5_9_9_9_REV,
1106 UnsignedInt248 = gl::UNSIGNED_INT_24_8,
1107 UnsignedShort = gl::UNSIGNED_SHORT,
1108 UnsignedShort4444 = gl::UNSIGNED_SHORT_4_4_4_4,
1109 UnsignedShort5551 = gl::UNSIGNED_SHORT_5_5_5_1,
1110 UnsignedShort565 = gl::UNSIGNED_SHORT_5_6_5,
1111 Float = gl::FLOAT,
1112 HalfFloat = gl::HALF_FLOAT_OES,
1113 Float32UnsignedInt248Rev = gl::FLOAT_32_UNSIGNED_INT_24_8_REV,
1114 }
1115}
1116
1117impl TexFormat {
1118 pub fn components(&self) -> u32 {
1121 match self.to_unsized() {
1122 TexFormat::DepthStencil => 2,
1123 TexFormat::LuminanceAlpha => 2,
1124 TexFormat::RG | TexFormat::RGInteger => 2,
1125 TexFormat::RGB | TexFormat::RGBInteger => 3,
1126 TexFormat::RGBA | TexFormat::RGBAInteger => 4,
1127 _ => 1,
1128 }
1129 }
1130
1131 pub fn is_compressed(&self) -> bool {
1133 let gl_const = self.as_gl_constant();
1134 matches!(
1135 gl_const,
1136 gl::COMPRESSED_RGB_S3TC_DXT1_EXT |
1137 gl::COMPRESSED_RGBA_S3TC_DXT1_EXT |
1138 gl::COMPRESSED_RGBA_S3TC_DXT3_EXT |
1139 gl::COMPRESSED_RGBA_S3TC_DXT5_EXT |
1140 gl_ext_constants::COMPRESSED_RGB_ETC1_WEBGL
1141 )
1142 }
1143
1144 pub fn is_sized(&self) -> bool {
1146 !matches!(
1147 self,
1148 TexFormat::DepthComponent |
1149 TexFormat::DepthStencil |
1150 TexFormat::Alpha |
1151 TexFormat::Red |
1152 TexFormat::RG |
1153 TexFormat::RGB |
1154 TexFormat::RGBA |
1155 TexFormat::Luminance |
1156 TexFormat::LuminanceAlpha
1157 )
1158 }
1159
1160 pub fn to_unsized(self) -> TexFormat {
1161 match self {
1162 TexFormat::R8 => TexFormat::Red,
1163 TexFormat::R8SNorm => TexFormat::Red,
1164 TexFormat::R16f => TexFormat::Red,
1165 TexFormat::R32f => TexFormat::Red,
1166 TexFormat::R8ui => TexFormat::RedInteger,
1167 TexFormat::R8i => TexFormat::RedInteger,
1168 TexFormat::R16ui => TexFormat::RedInteger,
1169 TexFormat::R16i => TexFormat::RedInteger,
1170 TexFormat::R32ui => TexFormat::RedInteger,
1171 TexFormat::R32i => TexFormat::RedInteger,
1172 TexFormat::RG8 => TexFormat::RG,
1173 TexFormat::RG8SNorm => TexFormat::RG,
1174 TexFormat::RG16f => TexFormat::RG,
1175 TexFormat::RG32f => TexFormat::RG,
1176 TexFormat::RG8ui => TexFormat::RGInteger,
1177 TexFormat::RG8i => TexFormat::RGInteger,
1178 TexFormat::RG16ui => TexFormat::RGInteger,
1179 TexFormat::RG16i => TexFormat::RGInteger,
1180 TexFormat::RG32ui => TexFormat::RGInteger,
1181 TexFormat::RG32i => TexFormat::RGInteger,
1182 TexFormat::RGB8 => TexFormat::RGB,
1183 TexFormat::SRGB8 => TexFormat::RGB,
1184 TexFormat::RGB565 => TexFormat::RGB,
1185 TexFormat::RGB8SNorm => TexFormat::RGB,
1186 TexFormat::R11fG11fB10f => TexFormat::RGB,
1187 TexFormat::RGB9E5 => TexFormat::RGB,
1188 TexFormat::RGB16f => TexFormat::RGB,
1189 TexFormat::RGB32f => TexFormat::RGB,
1190 TexFormat::RGB8ui => TexFormat::RGBInteger,
1191 TexFormat::RGB8i => TexFormat::RGBInteger,
1192 TexFormat::RGB16ui => TexFormat::RGBInteger,
1193 TexFormat::RGB16i => TexFormat::RGBInteger,
1194 TexFormat::RGB32ui => TexFormat::RGBInteger,
1195 TexFormat::RGB32i => TexFormat::RGBInteger,
1196 TexFormat::RGBA8 => TexFormat::RGBA,
1197 TexFormat::SRGB8Alpha8 => TexFormat::RGBA,
1198 TexFormat::RGBA8SNorm => TexFormat::RGBA,
1199 TexFormat::RGB5A1 => TexFormat::RGBA,
1200 TexFormat::RGBA4 => TexFormat::RGBA,
1201 TexFormat::RGB10A2 => TexFormat::RGBA,
1202 TexFormat::RGBA16f => TexFormat::RGBA,
1203 TexFormat::RGBA32f => TexFormat::RGBA,
1204 TexFormat::RGBA8ui => TexFormat::RGBAInteger,
1205 TexFormat::RGBA8i => TexFormat::RGBAInteger,
1206 TexFormat::RGB10A2ui => TexFormat::RGBAInteger,
1207 TexFormat::RGBA16ui => TexFormat::RGBAInteger,
1208 TexFormat::RGBA16i => TexFormat::RGBAInteger,
1209 TexFormat::RGBA32i => TexFormat::RGBAInteger,
1210 TexFormat::RGBA32ui => TexFormat::RGBAInteger,
1211 TexFormat::DepthComponent16 => TexFormat::DepthComponent,
1212 TexFormat::DepthComponent24 => TexFormat::DepthComponent,
1213 TexFormat::DepthComponent32f => TexFormat::DepthComponent,
1214 TexFormat::Depth24Stencil8 => TexFormat::DepthStencil,
1215 TexFormat::Depth32fStencil8 => TexFormat::DepthStencil,
1216 TexFormat::Alpha32f => TexFormat::Alpha,
1217 TexFormat::Alpha16f => TexFormat::Alpha,
1218 TexFormat::Luminance32f => TexFormat::Luminance,
1219 TexFormat::Luminance16f => TexFormat::Luminance,
1220 TexFormat::LuminanceAlpha32f => TexFormat::LuminanceAlpha,
1221 TexFormat::LuminanceAlpha16f => TexFormat::LuminanceAlpha,
1222 _ => self,
1223 }
1224 }
1225
1226 pub fn compatible_data_types(self) -> &'static [TexDataType] {
1227 match self {
1228 TexFormat::RGB => &[
1229 TexDataType::UnsignedByte,
1230 TexDataType::UnsignedShort565,
1231 TexDataType::Float,
1232 TexDataType::HalfFloat,
1233 ][..],
1234 TexFormat::RGBA => &[
1235 TexDataType::UnsignedByte,
1236 TexDataType::UnsignedShort4444,
1237 TexDataType::UnsignedShort5551,
1238 TexDataType::Float,
1239 TexDataType::HalfFloat,
1240 ][..],
1241 TexFormat::LuminanceAlpha => &[
1242 TexDataType::UnsignedByte,
1243 TexDataType::Float,
1244 TexDataType::HalfFloat,
1245 ][..],
1246 TexFormat::Luminance => &[
1247 TexDataType::UnsignedByte,
1248 TexDataType::Float,
1249 TexDataType::HalfFloat,
1250 ][..],
1251 TexFormat::Alpha => &[
1252 TexDataType::UnsignedByte,
1253 TexDataType::Float,
1254 TexDataType::HalfFloat,
1255 ][..],
1256 TexFormat::LuminanceAlpha32f => &[TexDataType::Float][..],
1257 TexFormat::LuminanceAlpha16f => &[TexDataType::HalfFloat][..],
1258 TexFormat::Luminance32f => &[TexDataType::Float][..],
1259 TexFormat::Luminance16f => &[TexDataType::HalfFloat][..],
1260 TexFormat::Alpha32f => &[TexDataType::Float][..],
1261 TexFormat::Alpha16f => &[TexDataType::HalfFloat][..],
1262 TexFormat::R8 => &[TexDataType::UnsignedByte][..],
1263 TexFormat::R8SNorm => &[TexDataType::Byte][..],
1264 TexFormat::R16f => &[TexDataType::HalfFloat, TexDataType::Float][..],
1265 TexFormat::R32f => &[TexDataType::Float][..],
1266 TexFormat::R8ui => &[TexDataType::UnsignedByte][..],
1267 TexFormat::R8i => &[TexDataType::Byte][..],
1268 TexFormat::R16ui => &[TexDataType::UnsignedShort][..],
1269 TexFormat::R16i => &[TexDataType::Short][..],
1270 TexFormat::R32ui => &[TexDataType::UnsignedInt][..],
1271 TexFormat::R32i => &[TexDataType::Int][..],
1272 TexFormat::RG8 => &[TexDataType::UnsignedByte][..],
1273 TexFormat::RG8SNorm => &[TexDataType::Byte][..],
1274 TexFormat::RG16f => &[TexDataType::HalfFloat, TexDataType::Float][..],
1275 TexFormat::RG32f => &[TexDataType::Float][..],
1276 TexFormat::RG8ui => &[TexDataType::UnsignedByte][..],
1277 TexFormat::RG8i => &[TexDataType::Byte][..],
1278 TexFormat::RG16ui => &[TexDataType::UnsignedShort][..],
1279 TexFormat::RG16i => &[TexDataType::Short][..],
1280 TexFormat::RG32ui => &[TexDataType::UnsignedInt][..],
1281 TexFormat::RG32i => &[TexDataType::Int][..],
1282 TexFormat::RGB8 => &[TexDataType::UnsignedByte][..],
1283 TexFormat::SRGB8 => &[TexDataType::UnsignedByte][..],
1284 TexFormat::RGB565 => &[TexDataType::UnsignedByte, TexDataType::UnsignedShort565][..],
1285 TexFormat::RGB8SNorm => &[TexDataType::Byte][..],
1286 TexFormat::R11fG11fB10f => &[
1287 TexDataType::UnsignedInt10f11f11fRev,
1288 TexDataType::HalfFloat,
1289 TexDataType::Float,
1290 ][..],
1291 TexFormat::RGB9E5 => &[
1292 TexDataType::UnsignedInt5999Rev,
1293 TexDataType::HalfFloat,
1294 TexDataType::Float,
1295 ][..],
1296 TexFormat::RGB16f => &[TexDataType::HalfFloat, TexDataType::Float][..],
1297 TexFormat::RGB32f => &[TexDataType::Float][..],
1298 TexFormat::RGB8ui => &[TexDataType::UnsignedByte][..],
1299 TexFormat::RGB8i => &[TexDataType::Byte][..],
1300 TexFormat::RGB16ui => &[TexDataType::UnsignedShort][..],
1301 TexFormat::RGB16i => &[TexDataType::Short][..],
1302 TexFormat::RGB32ui => &[TexDataType::UnsignedInt][..],
1303 TexFormat::RGB32i => &[TexDataType::Int][..],
1304 TexFormat::RGBA8 => &[TexDataType::UnsignedByte][..],
1305 TexFormat::SRGB8Alpha8 => &[TexDataType::UnsignedByte][..],
1306 TexFormat::RGBA8SNorm => &[TexDataType::Byte][..],
1307 TexFormat::RGB5A1 => &[
1308 TexDataType::UnsignedByte,
1309 TexDataType::UnsignedShort5551,
1310 TexDataType::UnsignedInt2101010Rev,
1311 ][..],
1312 TexFormat::RGBA4 => &[TexDataType::UnsignedByte, TexDataType::UnsignedShort4444][..],
1313 TexFormat::RGB10A2 => &[TexDataType::UnsignedInt2101010Rev][..],
1314 TexFormat::RGBA16f => &[TexDataType::HalfFloat, TexDataType::Float][..],
1315 TexFormat::RGBA32f => &[TexDataType::Float][..],
1316 TexFormat::RGBA8ui => &[TexDataType::UnsignedByte][..],
1317 TexFormat::RGBA8i => &[TexDataType::Byte][..],
1318 TexFormat::RGB10A2ui => &[TexDataType::UnsignedInt2101010Rev][..],
1319 TexFormat::RGBA16ui => &[TexDataType::UnsignedShort][..],
1320 TexFormat::RGBA16i => &[TexDataType::Short][..],
1321 TexFormat::RGBA32i => &[TexDataType::Int][..],
1322 TexFormat::RGBA32ui => &[TexDataType::UnsignedInt][..],
1323 TexFormat::DepthComponent16 => {
1324 &[TexDataType::UnsignedShort, TexDataType::UnsignedInt][..]
1325 },
1326 TexFormat::DepthComponent24 => &[TexDataType::UnsignedInt][..],
1327 TexFormat::DepthComponent32f => &[TexDataType::Float][..],
1328 TexFormat::Depth24Stencil8 => &[TexDataType::UnsignedInt248][..],
1329 TexFormat::Depth32fStencil8 => &[TexDataType::Float32UnsignedInt248Rev][..],
1330 TexFormat::CompressedRgbS3tcDxt1 |
1331 TexFormat::CompressedRgbaS3tcDxt1 |
1332 TexFormat::CompressedRgbaS3tcDxt3 |
1333 TexFormat::CompressedRgbaS3tcDxt5 => &[TexDataType::UnsignedByte][..],
1334 _ => &[][..],
1335 }
1336 }
1337
1338 pub fn required_webgl_version(self) -> WebGLVersion {
1339 match self {
1340 TexFormat::DepthComponent |
1341 TexFormat::Alpha |
1342 TexFormat::RGB |
1343 TexFormat::RGBA |
1344 TexFormat::Luminance |
1345 TexFormat::LuminanceAlpha |
1346 TexFormat::CompressedRgbS3tcDxt1 |
1347 TexFormat::CompressedRgbaS3tcDxt1 |
1348 TexFormat::CompressedRgbaS3tcDxt3 |
1349 TexFormat::CompressedRgbaS3tcDxt5 => WebGLVersion::WebGL1,
1350 _ => WebGLVersion::WebGL2,
1351 }
1352 }
1353
1354 pub fn usable_as_internal(self) -> bool {
1355 !self.compatible_data_types().is_empty()
1356 }
1357}
1358
1359#[derive(PartialEq)]
1360pub enum SizedDataType {
1361 Int8,
1362 Int16,
1363 Int32,
1364 Uint8,
1365 Uint16,
1366 Uint32,
1367 Float32,
1368}
1369
1370impl TexDataType {
1371 pub fn sized_data_type(&self) -> SizedDataType {
1373 match self {
1374 TexDataType::Byte => SizedDataType::Int8,
1375 TexDataType::UnsignedByte => SizedDataType::Uint8,
1376 TexDataType::Short => SizedDataType::Int16,
1377 TexDataType::UnsignedShort |
1378 TexDataType::UnsignedShort4444 |
1379 TexDataType::UnsignedShort5551 |
1380 TexDataType::UnsignedShort565 => SizedDataType::Uint16,
1381 TexDataType::Int => SizedDataType::Int32,
1382 TexDataType::UnsignedInt |
1383 TexDataType::UnsignedInt10f11f11fRev |
1384 TexDataType::UnsignedInt2101010Rev |
1385 TexDataType::UnsignedInt5999Rev |
1386 TexDataType::UnsignedInt248 => SizedDataType::Uint32,
1387 TexDataType::HalfFloat => SizedDataType::Uint16,
1388 TexDataType::Float | TexDataType::Float32UnsignedInt248Rev => SizedDataType::Float32,
1389 }
1390 }
1391
1392 pub fn element_size(&self) -> u32 {
1394 use self::*;
1395 match *self {
1396 TexDataType::Byte | TexDataType::UnsignedByte => 1,
1397 TexDataType::Short |
1398 TexDataType::UnsignedShort |
1399 TexDataType::UnsignedShort4444 |
1400 TexDataType::UnsignedShort5551 |
1401 TexDataType::UnsignedShort565 => 2,
1402 TexDataType::Int |
1403 TexDataType::UnsignedInt |
1404 TexDataType::UnsignedInt10f11f11fRev |
1405 TexDataType::UnsignedInt2101010Rev |
1406 TexDataType::UnsignedInt5999Rev => 4,
1407 TexDataType::UnsignedInt248 => 4,
1408 TexDataType::Float => 4,
1409 TexDataType::HalfFloat => 2,
1410 TexDataType::Float32UnsignedInt248Rev => 4,
1411 }
1412 }
1413
1414 pub fn components_per_element(&self) -> u32 {
1417 match *self {
1418 TexDataType::Byte => 1,
1419 TexDataType::UnsignedByte => 1,
1420 TexDataType::Short => 1,
1421 TexDataType::UnsignedShort => 1,
1422 TexDataType::UnsignedShort565 => 3,
1423 TexDataType::UnsignedShort5551 => 4,
1424 TexDataType::UnsignedShort4444 => 4,
1425 TexDataType::Int => 1,
1426 TexDataType::UnsignedInt => 1,
1427 TexDataType::UnsignedInt10f11f11fRev => 3,
1428 TexDataType::UnsignedInt2101010Rev => 4,
1429 TexDataType::UnsignedInt5999Rev => 4,
1430 TexDataType::UnsignedInt248 => 2,
1431 TexDataType::Float => 1,
1432 TexDataType::HalfFloat => 1,
1433 TexDataType::Float32UnsignedInt248Rev => 2,
1434 }
1435 }
1436
1437 pub fn required_webgl_version(self) -> WebGLVersion {
1438 match self {
1439 TexDataType::UnsignedByte |
1440 TexDataType::UnsignedShort4444 |
1441 TexDataType::UnsignedShort5551 |
1442 TexDataType::UnsignedShort565 |
1443 TexDataType::Float |
1444 TexDataType::HalfFloat => WebGLVersion::WebGL1,
1445 _ => WebGLVersion::WebGL2,
1446 }
1447 }
1448}
1449
1450#[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, MallocSizeOf, PartialEq, Serialize)]
1451pub enum AlphaTreatment {
1452 Premultiply,
1453 Unmultiply,
1454}
1455
1456#[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, MallocSizeOf, PartialEq, Serialize)]
1457pub enum YAxisTreatment {
1458 AsIs,
1459 Flipped,
1460}
1461
1462#[derive(Clone, Copy, Debug, Deserialize, Serialize)]
1463pub struct GLContextAttributes {
1464 pub alpha: bool,
1465 pub depth: bool,
1466 pub stencil: bool,
1467 pub antialias: bool,
1468 pub premultiplied_alpha: bool,
1469 pub preserve_drawing_buffer: bool,
1470}
1471
1472#[derive(Clone, Debug, Deserialize, Serialize)]
1473pub struct GLLimits {
1474 pub max_vertex_attribs: u32,
1475 pub max_tex_size: u32,
1476 pub max_3d_tex_size: u32,
1477 pub max_cube_map_tex_size: u32,
1478 pub max_combined_texture_image_units: u32,
1479 pub max_fragment_uniform_vectors: u32,
1480 pub max_renderbuffer_size: u32,
1481 pub max_texture_image_units: u32,
1482 pub max_varying_vectors: u32,
1483 pub max_vertex_texture_image_units: u32,
1484 pub max_vertex_uniform_vectors: u32,
1485 pub max_client_wait_timeout_webgl: std::time::Duration,
1486 pub max_transform_feedback_separate_attribs: u32,
1487 pub max_vertex_output_vectors: u32,
1488 pub max_fragment_input_vectors: u32,
1489 pub max_draw_buffers: u32,
1490 pub max_color_attachments: u32,
1491 pub max_uniform_buffer_bindings: u32,
1492 pub min_program_texel_offset: i32,
1493 pub max_program_texel_offset: u32,
1494 pub max_uniform_block_size: u64,
1495 pub max_combined_uniform_blocks: u32,
1496 pub max_combined_vertex_uniform_components: u64,
1497 pub max_combined_fragment_uniform_components: u64,
1498 pub max_vertex_uniform_blocks: u32,
1499 pub max_vertex_uniform_components: u32,
1500 pub max_fragment_uniform_blocks: u32,
1501 pub max_fragment_uniform_components: u32,
1502 pub max_3d_texture_size: u32,
1503 pub max_array_texture_layers: u32,
1504 pub uniform_buffer_offset_alignment: u32,
1505 pub max_element_index: u64,
1506 pub max_elements_indices: u32,
1507 pub max_elements_vertices: u32,
1508 pub max_fragment_input_components: u32,
1509 pub max_samples: u32,
1510 pub max_server_wait_timeout: std::time::Duration,
1511 pub max_texture_lod_bias: f32,
1512 pub max_varying_components: u32,
1513 pub max_vertex_output_components: u32,
1514}