IDL/New Graphics

NG 체계의 그래픽 개체의 특성 및 활용

이상우_idl 2021. 10. 7. 14:56
728x90
반응형

오늘은 NG 체계에서 정의되는 각종 그래픽 개체들의 특성 특히 그래픽 개체 변수에 관한 얘기를 살짝 좀 해보고, 그러한 특성을 활용하는 팁도 함께 소개해보고자 합니다. 일단 다음과 같이 간단하게 플롯 개체를 정의하고 표출하는 과정을 보면서 얘기해보도록 하겠습니다.

 

x = FINDGEN(101)/10
y = x^2
win = WINDOW(DIMENSIONS=[600, 500], /NO_TOOLBAR)
p = PLOT(x, y, COLOR='blue', /CURRENT)

 

이 과정을 실행하면 WINDOW 함수에 의하여 그래픽 창이 뜨고 PLOT 함수에 의하여 플롯 그림이 표출됩니다. 표출된 그림의 모습은 생략합니다. 그 대신에 PLOT 함수로 정의된 플롯 개체인 p에 주목을 해보고자 합니다. NG 체계에서는 항상 이와 같이 그래픽 함수를 사용하여 그래픽 개체를 정의하면 화면으로도 해당 그림이 표출됩니다. 그래서 아무래도 유저들 입장에서는 그림 표출 자체에 주로 신경을 쓰게 되기 때문에, 그래픽 함수로 정의된 개체(여기서는 p)에 대해서는 별로 신경을 안쓰는 경우가 많습니다. 그러면 여기서 앞의 예제와 비슷하면서도 약간 다른 예제를 보겠습니다.

 

x = FINDGEN(101)/10
y1 = x^2
y2 = x*5
win = WINDOW(DIMENSIONS=[600, 500], /NO_TOOLBAR)
p = PLOT(x, y1, COLOR='blue', /CURRENT)
p = PLOT(x, y2, COLOR='green', /OVERPLOT)

 

여기서는 x, y1에 대한 플롯을 먼저 표출하면서 색상을 파란색으로 처리하고, 동일한 XY 공간에 x, y2 플롯을 중첩 표출하면서 색상을 초록색으로 처리하였습니다. 이 과정에 의하여 표출된 그림은 다음과 같습니다.

 

 

이와 같이 별다른 문제없이 표출 결과를 얻을 수 있습니다. 그런데 여기서 후속 설정 즉 그래픽 개체가 생성된 이후에 특정 속성을 변경하는 시도를 하나 해보고자 합니다. 예를 들어 첫번째로 표출되었던 파란색 플롯의 선의 굵기를 키워보고 싶다고 가정합니다. 어떻게 해야 할까요? 일단 생각나는 처리 방법은 다음과 같습니다.

 

p.THICK = 3

 

이와 같이 p라는 개체에 대하여 THICK 속성의 값을 3으로 설정한 것입니다. 그 결과는 다음 그림과 같습니다.

 

 

이 그림을 보면 우리의 의도와는 달리 나중에 표출된 초록색 플롯 선이 더 굵어진 것을 볼 수 있습니다. 왜 그럴까요? 그 이유는 첫번째 및 두번째 플롯 개체를 정의할 때 좌변의 변수명을 둘 다 p로 정의했기 때문입니다.

 

p = PLOT(x, y1, COLOR='blue', /CURRENT)
p = PLOT(x, y2, COLOR='green', /OVERPLOT)

 

그러다보니 IDL에서는 처음에 정의된 p 대신 나중에 정의된 p만 메모리 상에서 기억하게 됩니다. 즉 이와 같이 그래픽 개체의 이름이 중복될 경우에는 가장 최근에 생성된 개체에 대한 기억만 남게 된다는 것입니다. 따라서 이런 방식으로는 전체적인 표출 결과를 얻는 것까지는 그럭저럭 되겠지만, 일단 그림이 표출된 이후에 첫번째 플롯에 대한 각종 속성들을 후속 변경하는 것은 불가능해집니다. 그렇기 때문에 우리의 의도대로 첫번째 플롯의 속성을 후속 변경하고자 한다면 애초에 두 플롯 개체의 이름을 서로 다르게 정의해야 합니다. 예를 들면 다음과 같습니다.

 

p1 = PLOT(x, y1, COLOR='blue', /CURRENT)
p2 = PLOT(x, y2, COLOR='green', /OVERPLOT)

 

이렇게 하면 다음과 같이 첫번째 플롯인 p1에 대한 속성을 후속 변경하는 것도 얼마든지 가능합니다.

 

p1.THICK = 3

 

그 결과는 다음 그림과 같습니다.

 

 

따라서 이와 같이 동일한 성격의 그래픽 개체들을 다수 정의하여 표출해야 하는 경우에는 각 개체의 변수명을 서로 다르게 정의하는 것이 바람직하다는 것을 기억하시면 좋을 것 같습니다. 그러면 비슷한 또 다른 예제를 보겠습니다. 그 과정은 다음과 같습니다.

 

x = FINDGEN(101)/10
y1 = x^2
y2 = x*5
y3 = x*3+20
win = WINDOW(DIMENSIONS=[600, 500], /NO_TOOLBAR)
p1 = PLOT(x, y1, COLOR='blue', /CURRENT)
p2 = PLOT(x, y2, COLOR='green', /OVERPLOT)
p3 = PLOT(x, y3, COLOR='red', /OVERPLOT)

 

여기서는 총 3종의 플롯 개체들을 정의하고 표출합니다. 결과는 다음 그림과 같습니다.

 

 

그런데 이와 같이 동일한 성격의 다수의 그래픽 개체들을 정의해야 하는 경우, 좌변의 변수명을 p1, p2, p3와 같은 식으로 직접 정의하는 방법도 있겠지만, 갯수가 더 많고 이름을 일일이 정의하는 것이 귀찮게 느껴질 경우도 있습니다. 그럴 경우에는 그래픽 개체의 이름들로 구성될 객체(Object) 배열을 아예 미리 정의해놓고 사용하는 방법이 있습니다. 일단 방법 자체는 다음과 같습니다.

 

win = WINDOW(DIMENSIONS=[600, 500], /NO_TOOLBAR)
ps = OBJARR(3)
ps[0] = PLOT(x, y1, COLOR='blue', /CURRENT)
ps[1] = PLOT(x, y2, COLOR='green', /OVERPLOT)
ps[2] = PLOT(x, y3, COLOR='red', /OVERPLOT)

 

여기서는 OBJARR 함수를 사용하여 객체(Object)들로 구성된 ps라는 배열을 정의하고, 각 플롯 개체를 ps의 각 원소에 대응시키는 방법을 사용하고 있습니다. 이런 방식이 가능한 이유는 NG 체계의 그래픽 함수로 정의되는 그래픽 개체가 근본적으로는 IDL의 객체(Object)의 성격을 갖고 있기 때문입니다. 그래서 우리가 마치 정수들의 배열을 INTARR 함수로 정의하는 것처럼 객체(정확히는 null object)들의 배열을 OBJARR 함수로 정의하여 이 배열을 사용한 것입니다. 물론 표출 결과는 어차피 똑같습니다. 그리고 앞서 이미 해봤던 것처럼 특정한 플롯의 두께를 후속 조정하려면 다음과 같은 문법을 사용하여 해당 개체에 대한 THICK 속성을 설정하면 됩니다.

 

ps[0].THICK = 3

 

그 결과는 충분히 예상 가능한데 다음 그림과 같습니다.

 

 

하여간 그래서 NG 체계에서의 그래픽 구현 및 활용에 있어서 이런 방법도 있다는 것을 알아두시면 여러모로 도움이 될 것 같아 소개해보았습니다.

반응형