Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,11 @@
# @antv/g-device-api

## 1.6.14

### Patch Changes

- 6d118ff: Flip Y in renderpass in webgpu renderer.

## 1.6.13

### Patch Changes
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@antv/g-device-api",
"version": "1.6.13",
"version": "1.6.14",
"description": "A Device API references WebGPU implementations",
"keywords": [
"antv",
Expand Down
21 changes: 20 additions & 1 deletion src/webgpu/RenderPass.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ export class RenderPass_WebGPU implements RenderPass {
private gfxColorResolveToLevel: number[] = [];
private gfxDepthStencilAttachment: TextureShared_WebGPU | null = null;
private gfxDepthStencilResolveTo: TextureShared_WebGPU | null = null;
private _viewportFlipHeight: number | undefined;

constructor(private device: Device_WebGPU) {
this.gpuColorAttachments = [];
Expand Down Expand Up @@ -205,6 +206,23 @@ export class RenderPass_WebGPU implements RenderPass {
)
? getPlatformQuerySet(descriptor.occlusionQueryPool)
: undefined;

// Viewport/scissor Y flip must use the active render target height. Using swapChainHeight
// for offscreen passes places the viewport outside the attachment (nothing draws).
const firstColor =
this.gfxColorAttachment.length > 0 ? this.gfxColorAttachment[0] : null;
const level0 =
this.gfxColorAttachmentLevel.length > 0
? this.gfxColorAttachmentLevel[0] || 0
: 0;
if (firstColor !== null && firstColor !== undefined) {
this._viewportFlipHeight = Math.max(1, firstColor.height >>> level0);
} else if (descriptor.depthStencilAttachment) {
const ds = descriptor.depthStencilAttachment as unknown as Attachment_WebGPU;
this._viewportFlipHeight = Math.max(1, ds.height >>> 0);
Comment on lines +220 to +222

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

The descriptor.depthStencilAttachment has already been cast and stored in this.gfxDepthStencilAttachment at line 143. Using the stored property directly avoids redundant casting and improves code clarity.

Suggested change
} else if (descriptor.depthStencilAttachment) {
const ds = descriptor.depthStencilAttachment as unknown as Attachment_WebGPU;
this._viewportFlipHeight = Math.max(1, ds.height >>> 0);
} else if (this.gfxDepthStencilAttachment) {
this._viewportFlipHeight = Math.max(1, this.gfxDepthStencilAttachment.height >>> 0);

} else {
this._viewportFlipHeight = this.device['swapChainHeight'];

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Accessing the private member swapChainHeight via string indexing (this.device['swapChainHeight']) is a workaround that bypasses TypeScript's encapsulation and type checking. It is recommended to expose this value through a public getter in the Device_WebGPU class to maintain proper access control. This pattern is also repeated in the flipY method at line 242.

}
}

beginRenderPass(
Expand All @@ -220,7 +238,8 @@ export class RenderPass_WebGPU implements RenderPass {
}

private flipY(y: number, h: number) {
const height = this.gfxColorAttachment[0].height;
const height =
this._viewportFlipHeight ?? this.device['swapChainHeight'];
return height - y - h;
}

Expand Down
Loading