Skip to content

Instantly share code, notes, and snippets.

@miklb
Created July 1, 2015 07:12
Show Gist options
  • Save miklb/ed145757971096565723 to your computer and use it in GitHub Desktop.
Save miklb/ed145757971096565723 to your computer and use it in GitHub Desktop.
Calculate Lunar Phase
#!/usr/bin/env python
"""
moonphase.py - Calculate Lunar Phase
Author: Sean B. Palmer, inamidst.com
Cf. http://en.wikipedia.org/wiki/Lunar_phase#Lunar_phase_calculation
"""
import math, decimal, datetime
dec = decimal.Decimal
def position(now=None):
if now is None:
now = datetime.datetime.now()
diff = now - datetime.datetime(2001, 1, 1)
days = dec(diff.days) + (dec(diff.seconds) / dec(86400))
lunations = dec("0.20439731") + (days * dec("0.03386319269"))
return lunations % dec(1)
def phase(pos):
index = (pos * dec(8)) + dec("0.5")
index = math.floor(index)
return {
0: "New Moon",
1: "Waxing Crescent",
2: "First Quarter",
3: "Waxing Gibbous",
4: "Full Moon",
5: "Waning Gibbous",
6: "Last Quarter",
7: "Waning Crescent"
}[int(index) & 7]
def main():
pos = position()
phasename = phase(pos)
roundedpos = round(float(pos), 3)
print "%s (%s)" % (phasename, roundedpos)
if __name__=="__main__":
main()
@sbp
Copy link

sbp commented Jun 17, 2024

Hi, original author here. The equation that I used was originally posted to Wikipedia by an author named "Monsieur le docteur Ralph" in March 2005. The magic values that I used were from that equation. Later, on the talk page for that article where they discuss removing the equation, they also discussed some potentially more accurate alternatives.

I posted the above code to my own website as moonphase.py, which has a Last-Modified date of 30 November 2005. I've been hosting it for nearly two decades on that site! I'm glad that people are finding the script useful. I and my friends use it in an IRC bot called saxo which I wrote about a decade ago to replace another one which I'd written a decade previously, roughly contemporaneous with moonphase.py.

If anybody comes up with an improved version of this script, with greater accuracy or ported to another language such a Go or Rust, please post the code or link to the code on this thread, and please send me a message. You can contact me on GitHub at @sbp, leave a message on my Wikipedia user talk page, or use whatever email address du jour I've got listed on my homepage.

@miklb
Copy link
Author

miklb commented Jun 18, 2024

@sbp howdy! I did leave credit in the script and I honestly don't remember where I came across it or why I originally shared it. I posted this gist 9 years ago! Thanks for pointing folks to the original source and offering support.

@Trotter73
Copy link

Trotter73 commented Apr 11, 2025

@sbp & @miklb thanks for this gents, just used it in a little toy I've been playing with, https://github.com/Trotter73/weather-display.git , I was using ephem but was struggling to get the results I wanted, this was perfect and was a drop in replacement, woop woop !

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment