# \[SOLVED\] What to use a renderer's scissor for?

**URL:** <https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050>\
**Category:** Questions\
**Tags:** scissor-test, webgl-renderer, webgl\
**Created:** [October 18, 2017, 3:00pm UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050 "2017-10-18T15:00:57Z")\
**Posts on this page:** 14\
**Page:** 1

<div class="post-metadata">

**Author:** ![trusktr](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/trusktr/32/13726_2.png) [@trusktr](https://discourse.threejs.org/u/trusktr)\
**Post date:** [October 18, 2017, 3:00pm UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/1 "2017-10-18T15:00:57Z")

</div>

What are practical use cases for using Scissor?

This helps a little: [https://www.khronos.org/opengl/wiki/Scissor\_Test](https://www.khronos.org/opengl/wiki/Scissor_Test)

Any cool tricks that scissor is specifically good for?

EDIT: I’m not sure how it even works. f.e., it just goes back, but I was expecting the rest of the viewport to stay rendered: [https://codepen.io/trusktr/pen/jGXRGV](https://codepen.io/trusktr/pen/jGXRGV). Seems like I’m missing something simple to make the “overlay” draw on top of the previous stuff.

---

<div class="post-metadata">

**Author:** ![Mugen87](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/mugen87/32/5645_2.png) [@Mugen87](https://discourse.threejs.org/u/Mugen87)\
**Post date:** [October 18, 2017, 4:18pm UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/2 "2017-10-18T16:18:31Z")

</div>

This is explained in so many threads and forums. Give google a try. Example:

> <https://gamedev.stackexchange.com/questions/40704/what-is-the-purpose-of-glscissor>

---

<div class="post-metadata">

**Author:** ![trusktr](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/trusktr/32/13726_2.png) [@trusktr](https://discourse.threejs.org/u/trusktr)\
**Post date:** [October 18, 2017, 7:27pm UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/3 "2017-10-18T19:27:18Z")

</div>

Thanks, I didn’t know it was a GL thing initially. After seeing a bunch of examples of glScissor, I don’t see why in my above example the area outside the scissor is all black. How do I draw the original scene, then draw it again in the scissor area on top of the original scene?

---

<div class="post-metadata">

**Author:** ![Mugen87](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/mugen87/32/5645_2.png) [@Mugen87](https://discourse.threejs.org/u/Mugen87)\
**Post date:** [October 19, 2017, 9:38am UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/4 "2017-10-19T09:38:19Z")

</div>

I’ve updated your code. Have a closer look what’s happening in the `render()` function: [https://codepen.io/anon/pen/EwrbGZ](https://codepen.io/anon/pen/EwrbGZ)

Also have a look at this example: [https://threejs.org/examples/index.html#webgl\_multiple\_views](https://threejs.org/examples/index.html#webgl_multiple_views)

---

<div class="post-metadata">

**Author:** ![trusktr](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/trusktr/32/13726_2.png) [@trusktr](https://discourse.threejs.org/u/trusktr)\
**Post date:** [October 20, 2017, 4:32am UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/5 "2017-10-20T04:32:50Z")

</div>

~~I had forgotten the `scene` and`camera` arguments for the second `render` call in my original example and I’ve fixed it, but the result is the same anyways.~~

~~After looking at yours, here’s my new try but I still can’t get it: [https://codepen.io/trusktr/pen/KXEzVq](https://codepen.io/trusktr/pen/KXEzVq)~~

~~But still no luck. In mine I’m calling setScissor and setViewport before each render call. What am I still missing?~~

EDIT: Ah, I see, I need to call the `setScissor` and `setViewport` functions before each call, otherwise the next animation frame will have the wrong scissor. And `setScissorTest(true)` can be called in init code.

---

<div class="post-metadata">

**Author:** ![trusktr](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/trusktr/32/13726_2.png) [@trusktr](https://discourse.threejs.org/u/trusktr)\
**Post date:** [October 20, 2017, 4:40am UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/6 "2017-10-20T04:40:10Z")

</div>

@Mugen87 So any time we use scissor to draw more stuff than just a single render call, it will _always_ be more expensive.

Is there a way to draw something only once, then use scissor to update only part of the screen so that we can get better performance?

For example, suppose we draw something to the whole display in the first frame, but all frames after that we only want to update the bottom right corner (suppose the only thing changing is a spinning logo in the bottom right corner, otherwise nothing else changes at all).

I’m guessing we’d have to render the initial scene to a texture but still have to draw the texture each frame, then just draw in the bottom right corner with scissor. Is that the best way to only update parts of the screen?

---

<div class="post-metadata">

**Author:** ![Mugen87](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/mugen87/32/5645_2.png) [@Mugen87](https://discourse.threejs.org/u/Mugen87)\
**Post date:** [October 20, 2017, 3:16pm UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/7 "2017-10-20T15:16:29Z")

</div>

> [@trusktr](#):
>
> I’m guessing we’d have to render the initial scene to a texture but still have to draw the texture each frame, then just draw in the bottom right corner with scissor. Is that the best way to only update parts of the screen?

I’m not sure it’s the best way but a texture based approach sounds reasonable in this case.

---

<div class="post-metadata">

**Author:** ![trusktr](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/trusktr/32/13726_2.png) [@trusktr](https://discourse.threejs.org/u/trusktr)\
**Post date:** [October 22, 2017, 11:51pm UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/8 "2017-10-22T23:51:57Z")

</div>

Is there another way to keep static pixels in the viewport, and just update only a portion of the viewport?

---

<div class="post-metadata">

**Author:** ![trusktr](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/trusktr/32/13726_2.png) [@trusktr](https://discourse.threejs.org/u/trusktr)\
**Post date:** [October 23, 2017, 1:09am UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/9 "2017-10-23T01:09:02Z")

</div>

I found [this on OpenGL.org](https://www.opengl.org/discussion_boards/showthread.php/174206-only-redraw-parts-of-the-screen-Scissor).

TLDR:

> if you really have a large amount of static content that is not affected by camera movement or the like, you can render it once into a texture and then each frame the first thing you render is a full screen quad with that texture applied.

And then we render only part of the screen with a scissor.

---

<div class="post-metadata">

**Author:** ![EliasHasle](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/eliashasle/32/3010_2.png) [@EliasHasle](https://discourse.threejs.org/u/EliasHasle)\
**Post date:** [July 2, 2018, 10:32am UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/10 "2018-07-02T10:32:19Z")

</div>

> Is there another way to keep static pixels in the viewport, and just update only a portion of the viewport?

I have not tested it, but would it be an option to disable autoclear on the color buffer, and then just clear the scissored area before updating it?

---

<div class="post-metadata">

**Author:** ![trusktr](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/trusktr/32/13726_2.png) [@trusktr](https://discourse.threejs.org/u/trusktr)\
**Post date:** [March 2, 2019, 7:59am UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/11 "2019-03-02T07:59:30Z")

</div>

Here’s a very interesting use of scissor: [https://keithclark.co.uk/labs/3d-model-custom-element/examples/tests/](https://keithclark.co.uk/labs/3d-model-custom-element/examples/tests/)

Look for the “Perspective scrolling test” example, then scroll horizontally, and the WebGL ducks are clipped (thanks to scissor).

---

<div class="post-metadata">

**Author:** ![EliasHasle](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/eliashasle/32/3010_2.png) [@EliasHasle](https://discourse.threejs.org/u/EliasHasle)\
**Post date:** [August 27, 2019, 2:31pm UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/12 "2019-08-27T14:31:01Z")

</div>

> Look for the “Perspective scrolling test” example, then scroll horizontally, and the WebGL ducks are clipped (thanks to scissor).

Hm. Do you have any reason to believe that this is because of scissor? This is expected behavior for a `canvas` in a `div` which has `style.overflow="scroll"`.

---

<div class="post-metadata">

**Author:** ![trusktr](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/trusktr/32/13726_2.png) [@trusktr](https://discourse.threejs.org/u/trusktr)\
**Post date:** [November 16, 2022, 7:03pm UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/13 "2022-11-16T19:03:39Z")

</div>

@EliasHasle Sorry for the late reply, but on that page, there is only a single canvas covering the whole window, and each of the multiple 3D scenes is drawn onto that single canvas, including the scene that appears cut off when scrolled.

This screenshot shows the only canvas in the inspector, highlighted in blue, covering the whole page:

 ![Screen Shot 2022-11-16 at 11.02.29 AM](https://canada1.discourse-cdn.com/flex035/uploads/threejs/original/3X/1/0/10be4231c30b568f231e02bb385ae9b1c3e90512.jpeg)

The reason for this technique is that, if there are too many WebGL canvases on a page (on my system, the limit is 32), then adding any more than 32 causes the first ones to crash in FIFO order due to the limit. So, to prevent that issue, all the scenes share a single canvas, and they are rendered to a portion of the single canvas based on the position where they should be based on the DOM container positions.

---

<div class="post-metadata">

**Author:** ![tobiascornille](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.threejs.org/tobiascornille/32/18217_2.png) [@tobiascornille](https://discourse.threejs.org/u/tobiascornille)\
**Post date:** [December 14, 2022, 9:00am UTC](https://discourse.threejs.org/t/solved-what-to-use-a-renderers-scissor-for/1050/14 "2022-12-14T09:00:59Z")

</div>

I can confirm this works, although you also need to enable [`preserveDrawingBuffer`](https://threejs.org/docs/#api/en/renderers/WebGLRenderer.preserveDrawingBuffer) when creating your `WebGLRenderer`.
