2019-02-26 10:10:57 +00:00
#!/usr/bin/python3
2019-01-28 13:18:19 +00:00
# coding=UTF-8
'''
2019-01-31 03:14:54 +00:00
Multi Laser planetarium in python3 for LJ .
v0 .01
Sam Neurohack
2019-02-26 10:10:57 +00:00
Accuracy could be tested against apparent data and starchart at https : / / www . calsky . com / cs . cgi ? cha = 7 & sec = 3 & sub = 2
2019-01-31 03:14:54 +00:00
Remember to set the same observer position and time .
See Readme for more information
2019-01-28 13:18:19 +00:00
2019-01-30 02:39:56 +00:00
Todo :
2019-02-26 10:10:57 +00:00
- use debug mode and check altaz calculated values against online sites .
2019-01-30 02:39:56 +00:00
- Validate aa2radec ( ) with online calculator . Rewrite it to remove need for Astropy .
- Findout how to use OSC in python 3.
2019-03-19 13:24:11 +00:00
- North sky is hardcoded .
2019-01-30 02:39:56 +00:00
- Code WebUI page .
- UpdateStars ( ) in each laser sky . Get magnitude . See UpdateSolar for example .
2019-01-31 03:14:54 +00:00
- All Draw operations should also check visibility in the given laser altitude range .
2019-01-30 02:39:56 +00:00
- Rewrite CityPosition ( ) with proper search in a python dictionnary .
- Better python code . Better varuable to understand easily Update ( ) methods .
2019-01-28 13:18:19 +00:00
LICENCE : CC
2019-01-31 03:14:54 +00:00
Remember : LJ will automatically warp geometry according to alignement data . See webUI .
2019-01-28 13:18:19 +00:00
'''
2019-01-31 03:14:54 +00:00
import redis
2019-01-28 13:18:19 +00:00
import lj3
import numpy as np
import math , time
2019-03-19 13:24:11 +00:00
print ( " Importing astropy... " )
2019-01-28 13:18:19 +00:00
from astropy . coordinates import SkyCoord , EarthLocation , AltAz
from astropy import units as u
from astropy . time import Time
2019-03-19 13:24:11 +00:00
print ( " Importing skyfield... " )
2019-01-28 13:18:19 +00:00
from skyfield . api import Star , load , Topos , Angle
from skyfield . data import hipparcos
2019-02-10 15:53:51 +00:00
from osc4py3 . as_eventloop import *
from osc4py3 import oscbuildparse
2019-02-26 10:10:57 +00:00
#from osc4py3 import oscmethod as osm
from osc4py3 . oscmethod import *
2019-01-30 02:39:56 +00:00
import json
2019-01-28 13:18:19 +00:00
'''
is_py2 = sys . version [ 0 ] == ' 2 '
if is_py2 :
from Queue import Queue
else :
from queue import Queue
'''
#
# Arguments handler
#
import argparse
print ( " " )
print ( " Arguments parsing if needed... " )
argsparser = argparse . ArgumentParser ( description = " Planetarium for LJ " )
argsparser . add_argument ( " -r " , " --redisIP " , help = " IP of the Redis server used by LJ (127.0.0.1 by default) " , type = str )
argsparser . add_argument ( " -c " , " --client " , help = " LJ client number (0 by default) " , type = int )
2019-03-19 13:24:11 +00:00
argsparser . add_argument ( " -L " , " --Lasers " , help = " Number of lasers connected (4 by default). " , type = int )
2019-02-26 10:10:57 +00:00
argsparser . add_argument ( " -v " , " --verbose " , help = " Verbosity level (0 by default) " , type = int )
2019-02-10 15:53:51 +00:00
argsparser . add_argument ( " -i " , " --input " , help = " inputs OSC Port (8005 by default) " , type = int )
2019-01-30 02:39:56 +00:00
#argsparser.add_argument("-n","--name",help="City Name of the observer",type=str)
#argsparser.add_argument("-r","--redisIP",help="Country code of the observer ",type=str)
2019-01-28 13:18:19 +00:00
args = argsparser . parse_args ( )
if args . client :
ljclient = args . client
else :
ljclient = 0
2019-02-26 10:10:57 +00:00
if args . Lasers :
lasernumber = args . Lasers
2019-01-28 13:18:19 +00:00
else :
2019-03-19 13:24:11 +00:00
lasernumber = 4
2019-01-28 13:18:19 +00:00
2019-02-26 10:10:57 +00:00
if args . verbose :
debug = args . verbose
2019-01-31 03:14:54 +00:00
else :
debug = 0
2019-02-10 15:53:51 +00:00
if args . input :
OSCinPort = args . input
else :
OSCinPort = 8005
2019-01-28 13:18:19 +00:00
# Redis Computer IP
if args . redisIP != None :
redisIP = args . redisIP
else :
redisIP = ' 127.0.0.1 '
lj3 . Config ( redisIP , ljclient )
#
# Inits Laser
#
fov = 256
viewer_distance = 2.2
2019-02-10 15:53:51 +00:00
width = 750
height = 750
2019-01-28 13:18:19 +00:00
centerX = width / 2
centerY = height / 2
samparray = [ 0 ] * 100
2019-01-30 02:39:56 +00:00
2019-01-28 13:18:19 +00:00
# If you want to use rgb for color :
def rgb2int ( r , g , b ) :
return int ( ' 0x %02x %02x %02x ' % ( r , g , b ) , 0 )
white = rgb2int ( 255 , 255 , 255 )
red = rgb2int ( 255 , 0 , 0 )
blue = rgb2int ( 0 , 0 , 255 )
green = rgb2int ( 0 , 255 , 0 )
2019-01-30 02:39:56 +00:00
2019-01-28 13:18:19 +00:00
def Proj ( x , y , z , angleX , angleY , angleZ ) :
rad = angleX * math . pi / 180
cosa = math . cos ( rad )
sina = math . sin ( rad )
y2 = y
y = y2 * cosa - z * sina
z = y2 * sina + z * cosa
rad = angleY * math . pi / 180
cosa = math . cos ( rad )
sina = math . sin ( rad )
z2 = z
z = z2 * cosa - x * sina
x = z2 * sina + x * cosa
rad = angleZ * math . pi / 180
cosa = math . cos ( rad )
sina = math . sin ( rad )
x2 = x
x = x2 * cosa - y * sina
y = x2 * sina + y * cosa
""" Transforms this 3D point to 2D using a perspective projection. """
factor = fov / ( viewer_distance + z )
x = x * factor + centerX
y = - y * factor + centerY
return ( x , y )
#
2019-01-30 02:39:56 +00:00
# All the coordinates base functions
2019-01-28 13:18:19 +00:00
#
2019-01-30 02:39:56 +00:00
'''
To minize number of sky objects coordinates conversion : Change planetarium FOV in Ra Dec to select objects
2019-02-10 15:53:51 +00:00
( planets , hipparcos , . . ) . Then get only those objects in AltAz coordinates .
2019-01-31 03:14:54 +00:00
aa2radec use Astropy to compute Equatorial Right Ascension and Declinaison coordinates from given observator Altitude and Azimuth .
2019-01-30 02:39:56 +00:00
Example ra , dec = aa2radec ( azimuth = 0 , altitude = 90 , lati = 48.85341 , longi = 2.3488 , elevation = 100 , t = AstroPyNow )
with AstroPyNow = Time . now ( )
'''
2019-01-31 03:14:54 +00:00
def aa2radec ( azimuth , altitude , t ) :
#AstrObserver = EarthLocation(lat=lati * u.deg, lon=longi *u.deg, height= elevation*u.m,)
2019-03-19 13:24:11 +00:00
#print("Oserver",AstrObserver )
print ( " time " , t )
ObjectCoord = SkyCoord ( alt = altitude * u . deg , az = azimuth * u . deg , obstime = t , frame = ' altaz ' , location = AstrObserver )
2019-01-30 02:39:56 +00:00
#print("icrs",ObjectCoord.icrs)
2019-03-19 13:24:11 +00:00
print ( " Altitude " , altitude )
print ( " Altitude " , altitude * u . deg )
print ( " Azimuth " , azimuth )
print ( " Azimuth " , azimuth * u . deg )
2019-01-30 02:39:56 +00:00
#print("ICRS Right Ascension", ObjectCoord.icrs.ra)
#print("ICRS Declination", ObjectCoord.icrs.dec)
2019-03-19 13:24:11 +00:00
#print()
2019-01-28 13:18:19 +00:00
return ObjectCoord . icrs . ra . degree , ObjectCoord . icrs . dec . degree
2019-01-30 02:39:56 +00:00
2019-01-31 03:14:54 +00:00
# Use Skyfield to compute given object apparent positions (ra,dec,alt,az) and distance from given gps earth position (in decimal degrees) at UTC time (in skyfield format)
def EarthObjPosition ( object , t ) :
2019-01-28 13:18:19 +00:00
2019-01-30 02:39:56 +00:00
#print (object, 'at', t.utc_iso())
2019-01-31 03:14:54 +00:00
#SkyObserver = earth + Topos(gpslat, gpslong)
2019-01-30 02:39:56 +00:00
astrometric = earth . at ( t ) . observe ( object )
ra , dec , distance = astrometric . radec ( )
'''
print ( " Right ascencion " , ra )
print ( " RA in degree " , ra . _degrees )
print ( " RA in radians " , ra . radians )
print ( " declinaison " , dec )
print ( distance )
'''
2019-01-31 03:14:54 +00:00
ApparentPosition = SkyObserver . at ( t ) . observe ( object ) . apparent ( )
#alt, az, distance = ApparentPosition.altaz('standard')
alt , az , distance = ApparentPosition . altaz ( )
2019-01-30 02:39:56 +00:00
'''
print ( " UTC " , t . utc_iso ( ) )
print ( " Altitude " , alt )
print ( " Altitude in radians " , alt . radians )
print ( " Altitude in degrees " , alt . degrees )
print ( " Altitude in dms " , alt . dms ( 0 ) )
print ( " Altitude in signed_dms " , alt . signed_dms ( 0 ) )
print ( " Azimuth " , az . dstr ( ) )
print ( " Distance from position " , distance )
'''
2019-01-31 03:14:54 +00:00
# If you want degree hours min : print (object,alt,az)
# or you can do return ra._degrees, dec, alt.degrees, az, distance
return alt . degrees , az . degrees , distance
2019-01-30 02:39:56 +00:00
# Add Radec coordinates for all lasers from user defined Altaz coordinates in LaserSkies variable at given earth position and time.
# LaserSkies : [LeftAzi, RightAzi, TopAlt, BotAlt, LeftRa, RightRa, TopDec, BottomDec]
# 0 1 2 3 4 5 6 7
2019-01-31 03:14:54 +00:00
def RadecSkies ( LaserSkies , AstroSkyTime ) :
2019-01-30 02:39:56 +00:00
print ( )
print ( " Converting " , lasernumber , " LaserSkies limits in Right Ascension & Declination (radec) coordinates " )
for laser in range ( lasernumber ) :
2019-03-19 13:24:11 +00:00
2019-02-10 15:53:51 +00:00
if debug > 0 :
2019-03-19 13:24:11 +00:00
print ( " " )
2019-02-10 15:53:51 +00:00
print ( " Laser " , laser )
2019-01-30 02:39:56 +00:00
# Left top point
2019-01-31 03:14:54 +00:00
LaserSkies [ laser ] [ 4 ] , LaserSkies [ laser ] [ 6 ] = aa2radec ( azimuth = LaserSkies [ laser ] [ 0 ] , altitude = LaserSkies [ laser ] [ 2 ] , t = AstroSkyTime )
2019-03-19 13:24:11 +00:00
2019-01-30 02:39:56 +00:00
# Right Bottom point
2019-01-31 03:14:54 +00:00
LaserSkies [ laser ] [ 5 ] , LaserSkies [ laser ] [ 7 ] = aa2radec ( azimuth = LaserSkies [ laser ] [ 1 ] , altitude = LaserSkies [ laser ] [ 3 ] , t = AstroSkyTime )
2019-02-10 15:53:51 +00:00
if debug > 0 :
2019-03-19 13:24:11 +00:00
print ( " Top left Altaz : " , LaserSkies [ laser ] [ 2 ] , LaserSkies [ laser ] [ 0 ] )
print ( " Top left radec : " , LaserSkies [ laser ] [ 4 ] , LaserSkies [ laser ] [ 6 ] )
print ( " Bottom right Altaz : " , LaserSkies [ laser ] [ 3 ] , LaserSkies [ laser ] [ 1 ] )
print ( " Bottom right radec : " , LaserSkies [ laser ] [ 5 ] , LaserSkies [ laser ] [ 7 ] )
2019-01-31 03:14:54 +00:00
if debug > 0 :
print ( LaserSkies )
2019-01-30 02:39:56 +00:00
print ( " Done. " )
2019-01-28 13:18:19 +00:00
def azimuth2scrX ( leftAzi , rightAzi , s ) :
2019-02-10 15:53:51 +00:00
2019-01-31 03:14:54 +00:00
a1 , a2 = leftAzi , rightAzi
2019-02-10 15:53:51 +00:00
b1 , b2 = 0 , width
#if debug > 0:
# print(leftAzi, rightAzi, s, b1 + ((s - a1) * (b2 - b1) / (a2 - a1)))
2019-03-19 13:24:11 +00:00
if s != 0 :
return b1 + ( ( s - a1 ) * ( b2 - b1 ) / ( a2 - a1 ) )
else :
return width / 2
2019-01-30 02:39:56 +00:00
2019-01-28 13:18:19 +00:00
2019-01-30 02:39:56 +00:00
2019-01-28 13:18:19 +00:00
def altitude2scrY ( topAlti , botAlti , s ) :
2019-02-10 15:53:51 +00:00
a1 , a2 = topAlti , botAlti
b1 , b2 = 0 , height
#if debug > 0:
# print(topAlti,botAlti,s, b1 + ((s - a1) * (b2 - b1) / (a2 - a1)))
2019-01-28 13:18:19 +00:00
return b1 + ( ( s - a1 ) * ( b2 - b1 ) / ( a2 - a1 ) )
2019-01-30 02:39:56 +00:00
2019-02-10 15:53:51 +00:00
2019-01-30 02:39:56 +00:00
#
# Solar System
#
2019-01-31 03:14:54 +00:00
SolarObjectShape = [ ( - 50 , 30 ) , ( - 30 , - 30 ) , ( 30 , - 30 ) , ( 10 , 30 ) , ( - 50 , 30 ) ]
2019-01-30 02:39:56 +00:00
2019-02-10 15:53:51 +00:00
# Planets Radius in km
SolarObjectradius = [
( ' Sun ' , 695500.0 ) ,
( ' Mercury ' , 2440.0 ) ,
( ' Venus ' , 6051.8 ) ,
( ' Earth ' , 6371.01 ) ,
( ' Mars ' , 3389.9 ) ,
( ' Jupiter ' , 69911.0 ) ,
( ' Saturn ' , 58232.0 ) ,
( ' Uranus ' , 25362.0 ) ,
( ' Neptune ' , 24624.0 ) ,
( ' 134340 Pluto ' , 1195.0 ) ,
]
2019-01-30 02:39:56 +00:00
def LoadSolar ( ) :
global planets , SolarObjects , earth
print ( " Loading Solar System (de421)... " )
# de421.bps https://naif.jpl.nasa.gov/pub/naif/generic_kernels/spk/planets/a_old_versions/de421.bsp
planets = load ( ' data/de421.bsp ' )
earth = planets [ ' earth ' ]
print ( ' Loaded. ' )
# de421 objects
# [Object name, object altitude, object azimuth]
SolarObjects = [ [ ' MERCURY ' , 0.0 , 0.0 ] , [ ' VENUS ' , 0.0 , 0.0 ] , [ ' JUPITER BARYCENTER ' , 0.0 , 0.0 ] , [ ' SATURN BARYCENTER ' , 0.0 , 0.0 ] , [ ' URANUS BARYCENTER ' , 0.0 , 0.0 ] , [ ' NEPTUNE BARYCENTER ' , 0.0 , 0.0 ] , [ ' PLUTO BARYCENTER ' , 0.0 , 0.0 ] , [ ' SUN ' , 0.0 , 0.0 ] , [ ' MOON ' , 0.0 , 0.0 ] , [ ' MARS ' , 0.0 , 0.0 ] ]
def UpdateSolar ( ) :
global SolarObjects
2019-03-19 13:24:11 +00:00
# Compute Alt Az coordinates for all solar objects for Observer.
2019-01-30 02:39:56 +00:00
for number , object in enumerate ( SolarObjects ) :
#print(object[0],number)
2019-01-31 03:14:54 +00:00
SolarObjects [ number ] [ 1 ] , SolarObjects [ number ] [ 2 ] , distance = EarthObjPosition ( planets [ object [ 0 ] ] , SkyfieldTime )
if debug > 0 :
PrintSolar ( )
def PrintSolar ( ) :
2019-01-30 02:39:56 +00:00
for number , object in enumerate ( SolarObjects ) :
2019-01-31 03:14:54 +00:00
print ( SolarObjects [ number ] [ 0 ] , " is at (alt,az) " , SolarObjects [ number ] [ 1 ] , SolarObjects [ number ] [ 2 ] )
# Draw the SolarShapeObject for any Solar object is in the laser Sky
def DrawSolar ( laser ) :
for number , object in enumerate ( SolarObjects ) :
2019-01-30 02:39:56 +00:00
2019-01-31 03:14:54 +00:00
# Solar object is in given laser sky azimuth and altitude range ?
if LaserSkies [ laser ] [ 0 ] < SolarObjects [ number ] [ 2 ] < LaserSkies [ laser ] [ 1 ] and LaserSkies [ laser ] [ 3 ] < SolarObjects [ number ] [ 1 ] < LaserSkies [ laser ] [ 2 ] :
#print ("drawing",SolarObjects[number][0],SolarObjects[number][1],SolarObjects[number][2],"on laser",laser)
lj3 . rPolyLineOneColor ( SolarObjectShape , c = white , PL = laser , closed = False , xpos = azimuth2scrX ( LaserSkies [ laser ] [ 0 ] , LaserSkies [ laser ] [ 1 ] , SolarObjects [ number ] [ 2 ] ) , ypos = altitude2scrY ( LaserSkies [ laser ] [ 2 ] , LaserSkies [ laser ] [ 3 ] , SolarObjects [ number ] [ 1 ] ) , resize = 2 , rotx = 0 , roty = 0 , rotz = 0 )
2019-01-30 02:39:56 +00:00
#
2019-01-31 03:14:54 +00:00
# Stars
2019-01-30 02:39:56 +00:00
#
2019-02-26 10:10:57 +00:00
StarsObjectShape = [ ( - 10 , 10 ) , ( - 10 , - 10 ) , ( 10 , - 10 ) , ( 10 , 10 ) , ( - 10 , 10 ) ]
2019-01-31 03:14:54 +00:00
2019-01-30 02:39:56 +00:00
def LoadHipparcos ( ts ) :
global hipdata
print ( " Loading hipparcos catalog... " )
#hipparcosURL = 'ftp://cdsarc.u-strasbg.fr/cats/I/239/hip_main.dat.gz'
hipparcosURL = ' data/hip_main.dat.gz '
with load . open ( hipparcosURL ) as f :
hipdata = hipparcos . load_dataframe ( f )
2019-02-10 15:53:51 +00:00
#print("Loaded.")
2019-01-30 02:39:56 +00:00
hipparcos_epoch = ts . tt ( 1991.25 )
# CODE IMPORTED HERE FROM TESTS. NEEDS TO ADAPT
# Star selection
def StarSelect ( ) :
2019-02-10 15:53:51 +00:00
global StarsObjects , hipdatafilt
2019-01-30 02:39:56 +00:00
2019-02-10 15:53:51 +00:00
StarsObjects = [ [ ] ]
#hipparcos_epoch = ts.tt(1991.25)
#barnards_star = Star.from_dataframe(hipdata.loc[87937])
#polaris = Star.from_dataframe(hipdata.loc[11767])
2019-01-30 02:39:56 +00:00
print ( )
2019-02-10 15:53:51 +00:00
print ( " Stars selection... " )
hipdatafilt = hipdata [ hipdata [ ' magnitude ' ] < = 3.5 ]
print ( ( ' {} stars with magnitude <= 3.5 ' . format ( len ( hipdatafilt ) ) ) )
Starnames = hipdatafilt . index
StarsObjects [ 0 ] = [ Starnames [ 0 ] , 0 , 0 ]
for index in range ( len ( Starnames ) - 1 ) :
StarsObjects . append ( [ Starnames [ index + 1 ] , 0 , 0 ] )
2019-01-30 02:39:56 +00:00
2019-02-10 15:53:51 +00:00
def UpdateStars ( ts ) :
2019-01-31 03:14:54 +00:00
global StarsObjects
2019-02-10 15:53:51 +00:00
hipparcos_epoch = ts . tt ( 1991.25 )
2019-03-19 13:24:11 +00:00
# Compute Alt Az coordinates for all stars objects for Observer.
2019-01-31 03:14:54 +00:00
for number , object in enumerate ( StarsObjects ) :
#print(object[0],number)
2019-02-10 15:53:51 +00:00
StarsObjects [ number ] [ 1 ] , StarsObjects [ number ] [ 2 ] , distance = EarthObjPosition ( Star . from_dataframe ( hipdatafilt . loc [ StarsObjects [ number ] [ 0 ] ] ) , SkyfieldTime )
2019-01-31 03:14:54 +00:00
if debug > 0 :
2019-02-10 15:53:51 +00:00
PrintStars ( )
2019-01-31 03:14:54 +00:00
def PrintStars ( ) :
for number , object in enumerate ( StarsObjects ) :
print ( StarsObjects [ number ] [ 0 ] , " is at (alt,az) " , StarsObjects [ number ] [ 1 ] , StarsObjects [ number ] [ 2 ] )
def DrawStars ( laser ) :
for number , object in enumerate ( StarsObjects ) :
2019-02-10 15:53:51 +00:00
# Star object is in given lasersky altitude range ?
if LaserSkies [ laser ] [ 3 ] < StarsObjects [ number ] [ 1 ] < LaserSkies [ laser ] [ 2 ] :
# Star object is in given lasersky azimuth range ?
if LaserSkies [ laser ] [ 0 ] < StarsObjects [ number ] [ 2 ] < LaserSkies [ laser ] [ 1 ] :
#print ("drawing",StarsObjects[number][0],StarsObjects[number][1],StarsObjects[number][2],"on laser",laser)
lj3 . rPolyLineOneColor ( StarsObjectShape , c = white , PL = laser , closed = False , xpos = azimuth2scrX ( LaserSkies [ laser ] [ 0 ] , LaserSkies [ laser ] [ 1 ] , StarsObjects [ number ] [ 2 ] ) , ypos = altitude2scrY ( LaserSkies [ laser ] [ 2 ] , LaserSkies [ laser ] [ 3 ] , StarsObjects [ number ] [ 1 ] ) , resize = 0.05 , rotx = 0 , roty = 0 , rotz = 0 )
# Star object is in given lasersky North azimuth ?
if LaserSkies [ laser ] [ 0 ] > LaserSkies [ laser ] [ 1 ] and StarsObjects [ number ] [ 2 ] < LaserSkies [ laser ] [ 1 ] :
#print ("drawing",StarsObjects[number][0],StarsObjects[number][1],StarsObjects[number][2],"on laser",laser)
lj3 . rPolyLineOneColor ( StarsObjectShape , c = white , PL = laser , closed = False , xpos = azimuth2scrX ( LaserSkies [ laser ] [ 0 ] , LaserSkies [ laser ] [ 1 ] , StarsObjects [ number ] [ 2 ] ) , ypos = altitude2scrY ( LaserSkies [ laser ] [ 2 ] , LaserSkies [ laser ] [ 3 ] , StarsObjects [ number ] [ 1 ] ) , resize = 0.05 , rotx = 0 , roty = 0 , rotz = 0 )
#
2019-03-19 13:24:11 +00:00
# Template for Anything you want system.
2019-02-10 15:53:51 +00:00
#
AnythingObjectShape = [ ( - 50 , 30 ) , ( - 30 , - 30 ) , ( 30 , - 30 ) , ( 10 , 30 ) , ( - 50 , 30 ) ]
def LoadAnything ( ) :
global planets , AnythingObjects , earth
print ( " Loading Anything System... " )
# de421.bps https://naif.jpl.nasa.gov/pub/naif/generic_kernels/spk/planets/a_old_versions/de421.bsp
# planets = load('data/de421.bsp')
earth = planets [ ' earth ' ]
print ( ' Loaded. ' )
# [Object name, object altitude, object azimuth]
AnythingObjects = [ [ ' MERCURY ' , 0.0 , 0.0 ] , [ ' VENUS ' , 0.0 , 0.0 ] , [ ' JUPITER BARYCENTER ' , 0.0 , 0.0 ] , [ ' SATURN BARYCENTER ' , 0.0 , 0.0 ] , [ ' URANUS BARYCENTER ' , 0.0 , 0.0 ] , [ ' NEPTUNE BARYCENTER ' , 0.0 , 0.0 ] , [ ' PLUTO BARYCENTER ' , 0.0 , 0.0 ] , [ ' SUN ' , 0.0 , 0.0 ] , [ ' MOON ' , 0.0 , 0.0 ] , [ ' MARS ' , 0.0 , 0.0 ] ]
def UpdateAnything ( ) :
global AnythingObjects
# Compute Alt Az coordinates for all Anything objects for obsehttps://www.startpage.com/do/searchrver.
for number , object in enumerate ( AnythingObjects ) :
#print(object[0],number)
AnythingObjects [ number ] [ 1 ] , AnythingObjects [ number ] [ 2 ] , distance = EarthObjPosition ( planets [ object [ 0 ] ] , SkyfieldTime )
if debug > 0 :
PrintAnything ( )
def PrintAnything ( ) :
for number , object in enumerate ( AnythingObjects ) :
print ( AnythingObjects [ number ] [ 0 ] , " is at (alt,az) " , AnythingObjects [ number ] [ 1 ] , AnythingObjects [ number ] [ 2 ] )
# Draw the AnythingShapeObject for any Anything object is in the laser Sky
def DrawAnything ( laser ) :
for number , object in enumerate ( AnythingObjects ) :
# Anything object is in given laser sky azimuth and altitude range ?
if LaserSkies [ laser ] [ 0 ] < AnythingObjects [ number ] [ 2 ] < LaserSkies [ laser ] [ 1 ] and LaserSkies [ laser ] [ 3 ] < AnythingObjects [ number ] [ 1 ] < LaserSkies [ laser ] [ 2 ] :
#print ("drawing",AnythingObjects[number][0],AnythingObjects[number][1],AnythingObjects[number][2],"on laser",laser)
lj3 . rPolyLineOneColor ( AnythingObjectShape , c = white , PL = laser , closed = False , xpos = azimuth2scrX ( LaserSkies [ laser ] [ 0 ] , LaserSkies [ laser ] [ 1 ] , AnythingObjects [ number ] [ 2 ] ) , ypos = altitude2scrY ( LaserSkies [ laser ] [ 2 ] , LaserSkies [ laser ] [ 3 ] , AnythingObjects [ number ] [ 1 ] ) , resize = 2 , rotx = 0 , roty = 0 , rotz = 0 )
2019-01-31 03:14:54 +00:00
#
2019-01-30 02:39:56 +00:00
# On Earth Gps positions
2019-01-31 03:14:54 +00:00
# from https://github.com/lutangar/cities.json
2019-01-30 02:39:56 +00:00
#
2019-03-19 13:24:11 +00:00
2019-01-30 02:39:56 +00:00
def LoadCities ( ) :
2019-01-31 03:14:54 +00:00
global world
2019-01-30 02:39:56 +00:00
print ( " Loading World Cities GPS position... " )
f = open ( " data/cities.json " , " r " )
s = f . read ( )
2019-01-31 03:14:54 +00:00
world = json . loads ( s )
2019-02-10 15:53:51 +00:00
#print("Loaded.")
2019-01-30 02:39:56 +00:00
2019-01-31 03:14:54 +00:00
# Get longitude and latitude of given City in given country. Need to better understand python dictionnaries.
2019-01-30 02:39:56 +00:00
def CityPositiion ( cityname , countrycode ) :
2019-01-31 03:14:54 +00:00
for city in range ( len ( world [ ' cities ' ] ) ) :
if world [ ' cities ' ] [ city ] [ ' name ' ] == cityname and world [ ' cities ' ] [ city ] [ ' country ' ] == countrycode :
2019-01-30 02:39:56 +00:00
'''
2019-01-31 03:14:54 +00:00
print ( world [ ' cities ' ] [ city ] [ ' country ' ] )
print ( world [ ' cities ' ] [ city ] [ ' name ' ] )
print ( world [ ' cities ' ] [ city ] [ ' lat ' ] )
print ( world [ ' cities ' ] [ city ] [ ' lng ' ] )
2019-01-30 02:39:56 +00:00
'''
2019-01-31 03:14:54 +00:00
return float ( world [ ' cities ' ] [ city ] [ ' lat ' ] ) , float ( world [ ' cities ' ] [ city ] [ ' lng ' ] )
2019-01-30 02:39:56 +00:00
2019-02-10 15:53:51 +00:00
# Add Kompass orientation to given laser point list if it is in laser sky at Y axis 300
# point lasers to
2019-01-31 03:14:54 +00:00
def DrawOrientation ( laser ) :
2019-01-30 02:39:56 +00:00
2019-02-10 15:53:51 +00:00
#print("LaserSkies 0",LaserSkies[laser][0],"LaserSkies 1",LaserSkies[laser][1])
2019-01-30 02:39:56 +00:00
# North direction is in given laser sky azimuth range?
2019-02-10 15:53:51 +00:00
if LaserSkies [ laser ] [ 1 ] < LaserSkies [ laser ] [ 0 ] :
#print ("N az",azimuth2scrX(LaserSkies[laser][0],LaserSkies[laser][1],0))
2019-03-19 13:24:11 +00:00
lj3 . Text ( " NORTH " , white , laser , azimuth2scrX ( LaserSkies [ laser ] [ 0 ] , LaserSkies [ laser ] [ 1 ] , 0 ) , 770 , resize = 0.5 , rotx = 0 , roty = 0 , rotz = 0 )
2019-01-30 02:39:56 +00:00
# East direction is in given laser sky azimuth range ?
2019-02-10 15:53:51 +00:00
if LaserSkies [ laser ] [ 0 ] < = 90 < LaserSkies [ laser ] [ 1 ] :
#print ("E az",azimuth2scrX(LaserSkies[laser][0],LaserSkies[laser][1],0))
lj3 . Text ( " EAST " , white , laser , azimuth2scrX ( LaserSkies [ laser ] [ 0 ] , LaserSkies [ laser ] [ 1 ] , 90 ) , 770 , resize = 0.5 , rotx = 0 , roty = 0 , rotz = 0 )
2019-01-30 02:39:56 +00:00
# South direction is in given laser sky azimuth range ?
2019-02-10 15:53:51 +00:00
if LaserSkies [ laser ] [ 0 ] < = 180 < LaserSkies [ laser ] [ 1 ] :
#print ("S az",azimuth2scrX(LaserSkies[laser][0],LaserSkies[laser][1],0))
lj3 . Text ( " SOUTH " , white , laser , azimuth2scrX ( LaserSkies [ laser ] [ 0 ] , LaserSkies [ laser ] [ 1 ] , 180 ) , 770 , resize = 0.5 , rotx = 0 , roty = 0 , rotz = 0 )
2019-01-30 02:39:56 +00:00
# West direction is in given laser sky azimuth range ?
2019-02-10 15:53:51 +00:00
if LaserSkies [ laser ] [ 0 ] < = 270 < LaserSkies [ laser ] [ 1 ] :
#print ("W az",azimuth2scrX(LaserSkies[laser][0],LaserSkies[laser][1],0))
lj3 . Text ( " WEST " , white , laser , azimuth2scrX ( LaserSkies [ laser ] [ 0 ] , LaserSkies [ laser ] [ 1 ] , 270 ) , 770 , resize = 0.5 , rotx = 0 , roty = 0 , rotz = 0 )
2019-01-30 02:39:56 +00:00
2019-01-31 03:14:54 +00:00
# Compute LaserSkies Coordinates for observer
def InitObserver ( SkyCity , SkyCountryCode , time , ts ) :
global LaserSkies , Skylat , Skylong , SkyfieldTime , AstrObserver , SkyObserver
2019-01-30 02:39:56 +00:00
# Observer position i.e : Paris FR
#Skylat = 48.85341 # decimal degree
#Skylong = 2.3488 # decimal degree
2019-02-10 15:53:51 +00:00
#print()
2019-01-30 02:39:56 +00:00
print ( " Observer GPS position and time... " )
Skylat , Skylong = CityPositiion ( SkyCity , SkyCountryCode )
print ( " GPS Position of " , SkyCity , " in " , SkyCountryCode , " : " , Skylat , Skylong )
# City GPS altitude not in Cities database... Let's say it's :
2019-01-31 03:14:54 +00:00
Skyelevation = 0 # meters
2019-01-30 02:39:56 +00:00
# Observer Time : Now
# Other time in Astropy style
# times = '1999-01-01T00:00:00.123456789'
# t = Time(times, format='isot', scale='utc')
2019-02-10 15:53:51 +00:00
#print()
2019-01-30 02:39:56 +00:00
AstroSkyTime = time
2019-01-31 03:14:54 +00:00
print ( " AstroPy time " , AstroSkyTime )
2019-01-30 02:39:56 +00:00
SkyfieldTime = ts . from_astropy ( AstroSkyTime )
2019-01-31 03:14:54 +00:00
print ( " SkyfieldTime from AstropyUTC " , SkyfieldTime . utc_iso ( ) )
AstrObserver = EarthLocation ( lat = Skylat * u . deg , lon = Skylong * u . deg , height = Skyelevation * u . m , )
SkyObserver = earth + Topos ( Skylat , Skylong )
2019-01-30 02:39:56 +00:00
# Computer for all Laser "skies" their Right Ascension/Declinaison coordinates from their Altitude/azimuth Coordinates.
# to later select their visible objects in radec catalogs like hipparcos.
2019-02-10 15:53:51 +00:00
# LaserSky definition for one laser (in decimal degrees) : [RightAzi, LeftAzi, TopAlt, BotAlt, LeftRa, RightRa, TopDec, BottomDec]
2019-01-30 02:39:56 +00:00
# With 4 lasers with each one a quarter of the 360 ° real sky, there is 4 LaserSky :
2019-03-19 13:24:11 +00:00
print ( )
print ( " LaserSkies Radec conversion " )
LaserSkies = [ [ 45 , 135.0 , 90.0 , 0.0 , 0.0 , 0.0 , 0.0 , 0.0 ] , [ 135 , 225 , 90 , 0 , 0 , 0 , 0 , 0 ] , [ 225 , 315 , 90.0 , 0 , 0 , 0 , 0 , 0 ] , [ 315 , 45 , 90.0 , 0 , 0 , 0 , 0 , 0 ] ]
2019-01-31 03:14:54 +00:00
RadecSkies ( LaserSkies , AstroSkyTime )
2019-02-26 10:10:57 +00:00
# Change Observer position by adding deltas (Gpslong, gpslat, elevation in decimal degree/meters)
def UpdateObserver ( gpslatdelta , gpslongdelta , elevationdelta , time , ts ) :
global LaserSkies , Skylat , Skylong , SkyfieldTime , AstrObserver , SkyObserver
Skylat + = gpslatdelta
Skylong + = gpslongdelta
Skyelevation + = elevationdelta
AstroSkyTime = time
print ( " AstroPy time " , AstroSkyTime )
SkyfieldTime = ts . from_astropy ( AstroSkyTime )
print ( " SkyfieldTime from AstropyUTC " , SkyfieldTime . utc_iso ( ) )
AstrObserver = EarthLocation ( lat = Skylat * u . deg , lon = Skylong * u . deg , height = Skyelevation * u . m , )
SkyObserver = earth + Topos ( Skylat , Skylong )
RadecSkies ( LaserSkies , AstroSkyTime )
UpdateSolar ( )
UpdateStars ( )
UpdateAnything ( )
2019-01-31 03:14:54 +00:00
def NewTime ( timeshift ) :
2019-01-30 02:39:56 +00:00
2019-01-31 03:14:54 +00:00
SkyfieldTime + = timeshift
2019-02-10 15:53:51 +00:00
if DisplaySolar :
UpdateSolar ( )
if DisplayStars :
UpdateStars ( )
if DisplayAnything :
UpdateAnything ( )
2019-03-17 03:19:57 +00:00
# /quit
def OSCquit ( ) :
2019-02-10 15:53:51 +00:00
2019-03-17 03:19:57 +00:00
WebStatus ( " Planet stopping " )
print ( " Stopping OSC... " )
lj3 . OSCstop ( )
sys . exit ( )
2019-01-28 13:18:19 +00:00
2019-02-26 10:10:57 +00:00
def OSCUI ( value ) :
# Will receive message address, and message data flattened in s, x, y
print ( " Planetarium OSC server got /planet/planetUI with value " , value )
2019-01-28 13:18:19 +00:00
2019-02-10 15:53:51 +00:00
def WebStatus ( message ) :
2019-03-17 03:19:57 +00:00
lj3 . SendLJ ( " /status " , message )
2019-01-28 13:18:19 +00:00
2019-02-10 15:53:51 +00:00
#
# Main part
#
try :
2019-02-26 10:10:57 +00:00
WebStatus ( " Planetarium " )
2019-01-31 03:14:54 +00:00
2019-02-26 10:10:57 +00:00
# OSC Server callbacks
print ( " Starting OSC at 127.0.0.1 port " , OSCinPort , " ... " )
osc_startup ( )
osc_udp_server ( " 127.0.0.1 " , OSCinPort , " InPort " )
osc_method ( " /planet/planetUI* " , OSCUI )
2019-03-17 03:19:57 +00:00
osc_method ( " /ping* " , lj3 . OSCping )
osc_method ( " /quit " , OSCquit )
2019-02-26 10:10:57 +00:00
2019-03-19 13:24:11 +00:00
WebStatus ( " Loading Cities... " )
2019-01-30 02:39:56 +00:00
ts = load . timescale ( )
LoadCities ( )
2019-02-26 10:10:57 +00:00
2019-01-30 02:39:56 +00:00
SkyCity = ' Paris '
SkyCountryCode = ' FR '
2019-02-26 10:10:57 +00:00
WebStatus ( SkyCity )
2019-03-19 13:24:11 +00:00
WebStatus ( " Loading Solar System... " )
2019-02-10 15:53:51 +00:00
LoadSolar ( )
2019-02-26 10:10:57 +00:00
2019-03-19 13:24:11 +00:00
WebStatus ( " Finding observer position.. " )
2019-01-31 03:14:54 +00:00
InitObserver ( SkyCity , SkyCountryCode , Time . now ( ) , ts )
2019-01-30 02:39:56 +00:00
2019-03-19 13:24:11 +00:00
WebStatus ( " Loading Stars... " )
2019-02-10 15:53:51 +00:00
LoadHipparcos ( ts )
StarSelect ( )
2019-03-19 13:24:11 +00:00
WebStatus ( " Computing observer skies " )
2019-01-31 03:14:54 +00:00
print ( " Updating solar system (de421) objects position for observer at " , Skylat , Skylong , " time " , SkyfieldTime . utc_iso ( ) )
2019-01-30 02:39:56 +00:00
UpdateSolar ( )
2019-02-26 10:10:57 +00:00
2019-01-31 03:14:54 +00:00
print ( " Updating stars for observer at " , Skylat , Skylong , " time " , SkyfieldTime . utc_iso ( ) )
2019-02-10 15:53:51 +00:00
UpdateStars ( ts )
2019-02-26 10:10:57 +00:00
WebStatus ( " Ready " )
2019-03-17 03:19:57 +00:00
lj3 . SendLJ ( " /planet/start " , 1 )
2019-01-31 03:14:54 +00:00
print ( " Done. " )
2019-01-30 02:39:56 +00:00
# UpdateStars() Todo
2019-02-10 15:53:51 +00:00
DisplayStars = True
DisplaySolar = False
2019-01-30 02:39:56 +00:00
DisplayOrientation = True
2019-02-10 15:53:51 +00:00
DisplayAnything = False
2019-02-26 10:10:57 +00:00
print ( " Start displaying on " , lasernumber , " lasers " )
2019-01-28 13:18:19 +00:00
while 1 :
2019-01-30 02:39:56 +00:00
for laser in range ( lasernumber ) :
2019-02-26 10:10:57 +00:00
#print ("Drawing laser",lasernumber)
2019-01-30 02:39:56 +00:00
if DisplayOrientation :
2019-01-31 03:14:54 +00:00
DrawOrientation ( laser )
2019-02-26 10:10:57 +00:00
lj3 . OSCframe ( )
2019-01-30 02:39:56 +00:00
if DisplaySolar :
2019-01-31 03:14:54 +00:00
DrawSolar ( laser )
2019-02-26 10:10:57 +00:00
lj3 . OSCframe ( )
2019-01-30 02:39:56 +00:00
if DisplayStars :
2019-02-10 15:53:51 +00:00
DrawStars ( laser )
2019-02-26 10:10:57 +00:00
lj3 . OSCframe ( )
2019-02-10 15:53:51 +00:00
if DisplayAnything :
DrawAnything ( )
2019-02-26 10:10:57 +00:00
lj3 . OSCframe ( )
2019-01-30 02:39:56 +00:00
lj3 . DrawPL ( laser )
2019-02-10 15:53:51 +00:00
lj3 . OSCframe ( )
time . sleep ( 0.01 )
except KeyboardInterrupt :
pass
# Gently stop on CTRL C
finally :
2019-02-26 10:10:57 +00:00
WebStatus ( " Planet Exit " )
print ( " Stopping OSC... " )
2019-02-10 15:53:51 +00:00
lj3 . OSCstop ( )
print ( " Fin du planetarium. " )
2019-01-30 02:39:56 +00:00