우주공학/Python

[Python 위성] 내 머리 위를 지나갈까? 위성 가시성(Visibility) 분석과 최저 고도각

univ 2026. 1. 7. 16:00
반응형

1. 들어가는 글: 위성은 어디까지 볼 수 있을까?

지난 포스팅에서 우리는 위성이 지구 위를 지나가는 길인 지상 궤적(Ground Track)을 그려보았습니다. 하지만 궤적 위에 있다고 해서 무조건 위성과 통신할 수 있는 것은 아닙니다.

https://univ.tistory.com/4

 

[Python 위성] 지상 궤적(Ground Track) 시각화: 위성 궤도는 왜 물결 모양일까?

1. 들어가는 글: 3차원 궤도를 2차원 지도로 옮길 때지난 시간에는 파이썬 Skyfield 라이브러리를 이용해 국제우주정거장(ISS)의 실시간 좌표(위도, 경도)를 찍어보는 실습을 했습니다.https://univ.tistor

univ.tistory.com

 

서울에 있는 지상국이 태평양 상공에 있는 위성을 볼 수 없는 것처럼, 지구는 둥글기 때문에 물리적인 시야(Line of Sight)가 확보되어야 합니다. 위성이 지상의 특정 지점을 볼 수 있는 영역을 'Footprint(발자국)'라고 부릅니다.

오늘은 파이썬을 이용해 "지금 이 순간 국제우주정거장(ISS)이 서울에서 보일까?"를 판단하는 알고리즘을 구현해 보겠습니다.

2. 핵심 개념: 고도각(Elevation Angle)과 마스킹

위성이 보이는지 안 보이는지를 판단하는 기준은 아주 간단합니다. 지평선 위로 위성이 올라왔느냐를 따지면 됩니다.

① 고도각 (Elevation, Εl)

지평선을 0˚, 머리 꼭대기(천정)를 90˚로 했을 때 위성이 위치한 각도입니다.

  • Εl  > 0˚ : 위성이 지평선 위에 있음 (이론적으로 통신 가능)
  • Εl  < 0˚ : 위성이 지평선 아래에 있음 (지구에 가려짐)

② 최저 고도각 (Elevation Mask Angle)

하지만 이론과 실제는 다릅니다. 실제 도심지에는 높은 빌딩이나 산이 있고, 대기권의 전파 감쇠 때문에 지평선 근처(0˚ ~ 5˚)의 위성은 통신 품질이 매우 나쁩니다.

그래서 실무에서는 "5도 혹은 10도 이상 떠올랐을 때만 보인다"라고 가정하는데, 이 기준을 Elevation Mask라고 합니다.

3. 파이썬 구현: 서울에서 ISS가 보일까?

이번 코드의 핵심은 위성(Satellite)과 지상 관측소(Observer) 사이의 상대적 위치를 계산하는 것입니다. Skyfield의 최신 문법인 wgs84 모듈을 사용합니다.

Python
 
from skyfield.api import load, EarthSatellite, wgs84

# 1. TLE 데이터 및 시간 설정
line1 = '1 25544U 98067A   26005.53262344  .00012388  00000-0  23158-3 0  9996'
line2 = '2 25544  51.6326  24.6699 0007562 343.7680  16.3066 15.49114570546545'
ts = load.timescale()
t = ts.now() # 현재 시간

# 위성 객체 생성
satellite = EarthSatellite(line1, line2, 'ISS (ZARYA)', ts)

# 2. 관측소(지상국) 위치 설정: 대한민국 서울 (위도 37.5, 경도 127.0)
seoul = wgs84.latlon(37.5665, 126.9780)

# 3. 상대 위치 계산 (Vector Geometry)
# 위성 위치에서 서울 위치를 빼면, 서울에서 바라본 위성 벡터가 나옵니다.
difference = satellite - seoul
topocentric = difference.at(t)

# 4. 고도각(Alt)과 방위각(Az) 추출
alt, az, distance = topocentric.altaz()

# 5. 가시성 판단 (Elevation Mask 10도 적용)
elevation_mask = 10.0

print(f"[분석 시각: {t.utc_strftime('%Y-%m-%d %H:%M:%S')} UTC]")
print(f"서울 기준 ISS 고도각: {alt.degrees:.2f}도")

if alt.degrees > elevation_mask:
    print("결과: ✅ 현재 서울에서 ISS 관측/통신 가능!")
    print(f"방위각(Azimuth): {az.degrees:.2f}도 방향을 보세요.")
else:
    print("결과: ❌ 현재 서울에서는 보이지 않음.")
    if alt.degrees < 0:
        print("사유: 지평선 아래에 있음")
    else:
        print(f"사유: 떴으나 건물/산에 가려질 높이임 ({alt.degrees:.2f} < {elevation_mask})")

4. 코드 해설

wgs84.latlon(37.5665, 126.9780)

지구 타원체 모델(WGS84) 위에 서울 시청의 좌표를 찍어 '관측소 객체'를 만듭니다.

difference = satellite - seoul

파이썬의 강력한 점입니다. 위성 객체에서 지상 객체를 빼기(-)만 하면, 자동으로 기하학적 벡터 연산을 수행하여 '상대 거리와 방향'을 계산해 줍니다.

.altaz()

상대 위치 벡터를 우리가 이해하기 쉬운 고도(Altitude/Elevation), 방위(Azimuth), 거리(Distance)로 변환해 줍니다. 여기서 alt 값이 바로 우리가 찾는 고도각( Εl )입니다.

5. 결과 분석 및 활용

코드를 실행했을 때 결과: ❌가 나올 확률이 훨씬 높습니다. 저궤도 위성(LEO)은 속도가 워낙 빨라(약 7.6km/s) 한반도 상공을 지나가는 시간은 하루에 몇 번, 기껏해야 10분 내외이기 때문입니다.

이 알고리즘은 실제 위성 관제소에서 임무 스케줄(Mission Schedule)을 짤 때 가장 기본이 되는 로직입니다.

  • "언제 위성에 명령을 보낼 수 있지?"
  • "언제 위성 사진을 다운로드 받을 수 있지?"
  • 이 모든 질문의 답이 바로 if alt > mask: 조건문에서 시작됩니다.

6. 마무리

이제 우리는 특정 시점에 위성이 보이는지 안 보이는지를 판단할 수 있게 되었습니다.

그렇다면 자연스럽게 다음 질문이 생깁니다. "그래서 정확히 언제 보이는데?"

지금 당장 안 보인다면, 앞으로 몇 시간 뒤에 서울 상공에 나타날지 예측할 수 있어야 진짜 엔지니어겠죠?

다음 포스팅에서는 Skyfield의 강력한 기능을 이용해 향후 24시간 동안의 '위성 통신 가능 시간(Pass Prediction)'을 예측하고 표로 출력하는 법을 다뤄보겠습니다.

반응형