OpenGL-모서리 감지


12

임의의 메쉬를로드하고 가장자리를 따라 두꺼운 검은 선을 그려 툰 쉐이딩처럼 보이게하고 싶습니다. 스텐실 버퍼를 사용하여 객체 주위에 검은 실루엣을 그렸습니다. 결과는 여기에서 볼 수 있습니다.

여기에 이미지 설명을 입력하십시오

그러나 누락 된 것은 객체 자체의 검은 선입니다. 정규 불연속 검사에 대해 생각했습니다. 인접 픽셀이 현재 픽셀과 다른 법선 벡터를 갖는지 확인합니다. 그렇다면 가장자리를 찾았습니다. 불행히도 OpenGL이나 GLSL 버텍스 / 프래그먼트 셰이더 에서이 접근법을 어떻게 구현할 수 있는지 잘 모르겠습니다.

이 방법에 대한 도움이나 가장자리 탐지에 관한 도움에 매우 기쁩니다.

편집 : 메쉬에 텍스처를 사용하지 않습니다.

더 정확하게 말하자면, 가능한 한 많이 보이는 CAD / CAM 솔루션을 만들고 싶습니다 (Top Solid https://www.youtube.com/watch?v=-qTJZtYUDB4 ).

여기에 이미지 설명을 입력하십시오


"가장자리"를 더 자세하게 정의해야한다고 생각합니다. 간단한 와이어 프레임과 어떻게 다릅니 까? cifz 답변에는 화면 공간 사후 프로세스에 대한 좋은 설명이 있지만 질문에서 적용 가능한지 결정하기가 어렵습니다.
— Andreas

글쎄, 가장자리와 나는 고체를 형성하는 "주름"과 "마루"를 의미합니다. 와이어 프레임에는 모든 삼각형면이 표시되지만 원하는 것은 아닙니다.
— enne87

좋아, 정확히 내가 요청한 것은 :-) 주름과 융기 부분에서 와이어 프레임을 생성합니다. 까다로운 부분은 여전히 ​​주름 / 리지가 무엇인지 확인하는 것입니다. 그렇게하는 방법에 대한 아이디어가 있습니까?
— Andreas

1
cad 프로그램은 대부분 셰이더를 사용하여이 작업을 수행하지 않습니다. 대신 모델의 단단한 가장자리를 알고 해당 정보의 메쉬 위에 선을 그립니다.
— joojaa

joojaa이 기술에 대한 정보가 더 있습니까? 이중 곡면 자유 곡면의 경우 어떻게됩니까? 또한 자유로운 형태로 잘라내거나 잘라지는 원뿔이나 실린더가있을 때 어떤 일이 발생하는지 잘 모르겠습니다. stackoverflow.com/questions/43795262/…
— 두산 Bosnjak 'pailhead'Jul

답변:


18

일반적으로 가장자리 감지 기능이 다운되어 높은 경사도 값으로 이미지 영역을 감지합니다.

우리의 경우 이미지 함수의 파생물로 그라디언트를 대략적으로 볼 수 있으므로 그라디언트의 크기는 이미지가 로컬 에서 얼마나 많이 변경 되는지에 대한 정보를 제공합니다 (인접한 픽셀 / 텍셀과 관련).
이제 가장자리는 불연속의 표시라고 말 했으므로 이제 그라디언트를 정의 했으므로이 정보 만 있으면됩니다. 이미지의 그라디언트를 찾으면 이진 값 에지 / 비 에지 값을 얻기 위해 임계 값을 적용하기 만하면됩니다.

이 그라디언트는 실제로 당신이 요구하는 것인데 어떻게 대답하지 않습니까?

많은 방법! 여기에 몇 가지 :)

내장 셰이더 기능

hlsl과 glsl은 모두 미분 함수를 제공합니다. GLSL 에는 x와 y 방향의 그라디언트 정보를 제공하는 dFdx와 dFdy 가 있습니다. 일반적으로 이러한 기능은 2x2 조각으로 평가됩니다.
단일 방향에 관심이 없으면 영역의 그라디언트가 얼마나 강한 지 나타내는 컴팩트 한 결과를 얻는 좋은 방법 은 dFdy와 dFdy의 절대 값의 합 외에 다른 것을 제공하지 않습니다.
특정 채널이 아닌 전체 이미지의 가장자리에 관심이있을 수 있으므로 이미지 기능을 루마로 변환 할 수 있습니다. 이를 염두에두고, 가장자리 감지와 관련하여 쉐이더는 다음과 같은 것을 포함 할 수 있습니다.

  float luminance = dot(yourFinalColour,vec3(0.2126, 0.7152, 0.0722));
  float gradient = fwidth(luminance );
  float isEdge = gradient > threshold;

임계 값이 높으면 가장자리가 거칠고 반대로 임계 값이 낮 으면 잘못된 가장자리를 감지 할 수 있습니다. 요구 사항에 더 적합한 임계 값을 찾기 위해 실험해야합니다.

이러한 기능이 작동하는 이유는 언급 할 가치가 있지만 지금은 시간이 없습니다. 나중에이 답변을 업데이트 할 가능성이 큽니다.

화면 공간 후 처리

이보다 더 멋진 경험을 할 수 있습니다. 이제 이미지 처리에서 가장자리 감지 필드가 엄청납니다. 필요에 따라 에지 감지를 감지하는 수십 가지 좋은 방법을 인용 할 수는 있지만, 지금 당장 간단하게 유지하십시오. 관심이 있으시면 더 많은 옵션을 인용 할 수 있습니다!

따라서 아이디어는 위의 것과 비슷하지만 더 넓은 이웃을보고 원하는 경우 해리 운딩 샘플에 가중치 세트를 사용할 수 있다는 차이점이 있습니다. 일반적으로 좋은 그라디언트 정보를 제공하는 커널을 사용하여 이미지를 컨볼 루션으로 실행합니다.
가장 일반적인 선택은 Sobel 커널입니다

                                   여기에 이미지 설명을 입력하십시오

각각 x 및 y 방향의 그라디언트를 제공합니다.

                                  오래된 pdf에서 나는 오래 전에 썼다.

와 같이 기울기에서 단일 값을 얻을 수 있습니다.GradientMagnitude=(Gradientx)2+(Gradienty)2

그런 다음 위에서 언급 한 것과 같은 방식으로 임계 값을 지정할 수 있습니다.

보시 다시피이 커널은 중앙 픽셀에 더 많은 가중치를 부여하므로 그라디언트 + 약간의 스무딩을 효과적으로 계산하는 데 도움이됩니다.

위의 내용은 잘 작동하지만 스무딩이 마음에 들지 않으면 Prewitt 커널을 사용할 수 있습니다.

                                                   여기에 이미지 설명을 입력하십시오

(참고로 서두르면 곧 이미지 대신 적절한 형식의 텍스트를 작성합니다!)

실제로 실시간 그래픽이 아닌 이미지 프로세스 방식으로 에지 감지를 찾을 수있는 커널과 기술이 훨씬 더 많으므로 dFdx / y 함수를 사용하면 더 복잡한 방법을 배제 할 수 있습니다. .


아주 좋은 설명 cifz, 그러나 특정 상황에서 그래디언트가 보이지 않으면 어떻게합니까? 예를 들어, 큐브 뒷면에 광원이 없으므로 그래디언트가 보이지 않습니다. 그런 다음 이미지 기반 가장자리 감지 프로세스가 작동하지 않습니다. 맞습니까?
— enne87

디퍼 드 렌더러를 사용하는 경우 일반 버퍼에서 동일하게 또는 다시 수행 할 수 있으며 프리 패스가있는 경우 알고리즘을 깊이에 적용 할 수 있습니다. 화면 공간 접근 방식이 모든 경우에 이상적이지는 않을 수도 있습니다. :) 실행 가능한 솔루션은이 효과의 예산, 장면의 복잡도에 따라 다릅니다.
— cifz

잠재적으로 이것이 게임의 중심에 있다면, 매우 쉽지만 잠재적으로 과세되면 각 정점 (로드 시간에 오프라인)에 대한 이웃 법선의 그라디언트를 계산 하고이 요소를 추가 정점 속성으로 전달합니다.
— cifz

당신의 도움을 위해 다시 cifz를 움직입니다. 글쎄, 내가 달성하고자하는 것은 다음과 비슷한 CAD / CAM 솔루션을 개발하는 것입니다 : youtube.com/watch?v=-qTJZtYUDB4 그리고 나는 그들이 모든 검은 가장자리, 주름을 렌더링하기 위해 어떻게 관리했는지 알고 싶습니다. 능선. cifz, 스크린 공간 접근 방식 중 하나를 사용하여이 모양을 달성 한 그래픽 프로그래밍 전문가라고 생각하십니까? 아니면 이웃 법선의 기울기를 계산하여? 나는 이것이 어떻게 이루어질 수 있는지 정말로 알고 싶다. 다시 감사합니다!
— enne87

1
누구에게도 비용을 지불 할 필요는 없으며 온라인에서 몇 가지 자습서를 읽고 책을 구입하고 열심히 공부하십시오. :) 결국에는 매우 보람이있을 것입니다!
— cifz

3

: 그냥 경우에 사람이 ELSO 또한 가장자리를 감지 할 필요가 여기에 와이어 프레임을 표시하는 방법 좋은 기사이며 이 문서에서는 가장자리를 표시하는 방법에 대해 설명합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.