def getGeocentricPlanetDirectRetrogradeInfo(planetName):
    """
    Returns a list of tuples, each tuple containing:
    (planetName,
    julianDay,
    datetime,
    "R" or "D",
    geoTropLongitudeOfPlanet,
    geoSidLongitudeOfPlanet)
    """

    # Return value.
    rv = []

    prevDt = None
    currDt = copy.deepcopy(startDt)

    prevTropLongitudeSpeed = None
    currTropLongitudeSpeed = None

    currTropLongitude = None
    currSidLongitude = None
    
    while currDt <= endDt:
        dt = currDt

        pi = Ephemeris.getPlanetaryInfo(planetName, dt)
        
        log.debug("Just obtained planetaryInfo for planet '{}', timestamp: {}".\
                  format(planetName, Ephemeris.datetimeToStr(dt)))

        # Get the geocentric longitude and geocentric longitude speed.
        tropLongitudeSpeed = pi.geocentric['tropical']['longitude_speed']
        tropLongitude = pi.geocentric['tropical']['longitude']
        sidLongitude = pi.geocentric['sidereal']['longitude']

        # Store new current planet values.
        currTropLongitudeSpeed = tropLongitudeSpeed
        currTropLongitude = tropLongitude
        currSidLongitude = sidLongitude

        log.debug("prevTropLongitudeSpeed={}, currTropLongitudeSpeed={}".\
                  format(prevTropLongitudeSpeed, currTropLongitudeSpeed))
        
        # We need two data points to proceed.
        if prevTropLongitudeSpeed != None and \
               currTropLongitudeSpeed != None and \
               prevDt != None:
            
            # Check to see if we passed over 0 degrees.
            
            if prevTropLongitudeSpeed < 0.0 and currTropLongitudeSpeed >= 0.0:
                # Crossed over from negative to positive!
                log.debug("Crossed over from negative to positive!")

                # This is the upper-bound of the error timedelta.
                t1 = prevDt
                t2 = currDt
                currErrorTd = t2 - t1
                
                # Refine the timestamp until it is less than the
                # desired threshold.
                while currErrorTd > maxErrorTd:
                    log.debug("Refining between {} and {}".\
                              format(Ephemeris.datetimeToStr(t1),
                                     Ephemeris.datetimeToStr(t2)))
                    
                    # Check the timestamp between.
                    diffTd = t2 - t1
                    halfDiffTd = \
                        datetime.\
                        timedelta(days=(diffTd.days / 2.0),
                                  seconds=(diffTd.seconds / 2.0),
                                  microseconds=(diffTd.microseconds / 2.0))
                    testDt = t1 + halfDiffTd
                    
                    pi = Ephemeris.getPlanetaryInfo(planetName, testDt)
                    
                    testTropLongitudeSpeed = \
                        pi.geocentric['tropical']['longitude_speed']
                    testTropLongitude = pi.geocentric['tropical']['longitude']
                    testSidLongitude = pi.geocentric['sidereal']['longitude']

                    if testTropLongitudeSpeed >= 0.0:
                        t2 = testDt
                        
                        # Update the curr values as the later boundary.
                        currDt = t2
                        currTropLongitudeSpeed = testTropLongitudeSpeed
                        currTropLongitude = testTropLongitude
                        currSidLongitude = testSidLongitude
                    else:
                        t1 = testDt

                    currErrorTd = t2 - t1
                        
                # Broke out of while loop, meaning we have a timestamp
                # within our threshold.
                # Create a tuple to add to our list.
                tup = (planetName,
                       Ephemeris.datetimeToJulianDay(currDt),
                       currDt,
                       directStr,
                       currTropLongitude,
                       currSidLongitude)

                # Append to the list.
                rv.append(tup)
                
            elif prevTropLongitudeSpeed > 0.0 and currTropLongitudeSpeed <= 0.0:
                # Crossed over from positive to negative!
                log.debug("Crossed over from positive to negative!")
                
                # This is the upper-bound of the error timedelta.
                t1 = prevDt
                t2 = currDt
                currErrorTd = t2 - t1
                
                # Refine the timestamp until it is less than the
                # desired threshold.
                while currErrorTd > maxErrorTd:
                    log.debug("Refining between {} and {}".\
                              format(Ephemeris.datetimeToStr(t1),
                                     Ephemeris.datetimeToStr(t2)))
                    
                    # Check the timestamp between.
                    diffTd = t2 - t1
                    halfDiffTd = \
                        datetime.\
                        timedelta(days=(diffTd.days / 2.0),
                                  seconds=(diffTd.seconds / 2.0),
                                  microseconds=(diffTd.microseconds / 2.0))
                    testDt = t1 + halfDiffTd
                    
                    pi = Ephemeris.getPlanetaryInfo(planetName, testDt)
                    
                    testTropLongitudeSpeed = \
                        pi.geocentric['tropical']['longitude_speed']
                    testTropLongitude = pi.geocentric['tropical']['longitude']
                    testSidLongitude = pi.geocentric['sidereal']['longitude']

                    if testTropLongitudeSpeed <= 0.0:
                        t2 = testDt
                        
                        # Update the curr values as the later boundary.
                        currDt = t2
                        currTropLongitudeSpeed = testTropLongitudeSpeed
                        currTropLongitude = testTropLongitude
                        currSidLongitude = testSidLongitude
                    else:
                        t1 = testDt

                    currErrorTd = t2 - t1
                    
                # Broke out of while loop, meaning we have a timestamp
                # within our threshold.
                # Create a tuple to add to our list.
                tup = (planetName,
                       Ephemeris.datetimeToJulianDay(currDt),
                       currDt,
                       retrogradeStr,
                       currTropLongitude,
                       currSidLongitude)

                # Append to the list.
                rv.append(tup)
                
            
        # Increment currDt timestamp.
        prevDt = currDt
        currDt = currDt + stepSizeTd
        
        # Move the previous currTropLongitudeSpeed to prevTropLongitudeSpeed.
        prevTropLongitudeSpeed = currTropLongitudeSpeed
        currTropLongitudeSpeed = None
        currTropLongitude = None
        currSidLongitude = None

        log.debug("prevTropLongitudeSpeed={}, currTropLongitudeSpeed={}".\
                  format(prevTropLongitudeSpeed, currTropLongitudeSpeed))
        
    return rv
def convertSwingFileDataToCsvStr(swingFileData):
    """Takes a SwingFileData and generates a CSV str containing most
    of the swing file data.
    """

    geocentricPlanetNameList = [\
        "Jupiter",
        "Saturn",
        "Uranus",
        "Neptune",
        "Pluto",
        "Chiron",
        "TrueNorthNode",
        #"Isis",
        ]

    endl = "\n"

    rv = ""

    rv += "Trading Entity Description: {}".\
          format(swingFileData.tradingEntityDescription) + endl
    #rv += "Swing File Description: {}".\
    #      format(swingFileData.swingFileDescription) + endl
    #rv += "User notes: {}".\
    #      format(swingFileData.userNotes) + endl
    rv += "Source Swing File: {}".\
          format(swingFile) + endl
    #rv += "Source PCD filename: {}".\
    #      format(swingFileData.sourcePcdFilename) + endl
    #rv += "Source PriceBar data filename: {}".\
    #      format(swingFileData.sourcePriceBarDataFilename) + endl

    # Column headers.
    rv += "jd,day,date,time,timezone,tags,open,high,low,close,volume,oi"

    # Add the columns headers for the Geocentric planets' longitude.
    # Here we do it twice because the first set is the 15-degree axis
    # reduction, and the second set is the actual planet positions.
    for planetName in geocentricPlanetNameList:
        rv += ",G." + planetName
    for planetName in geocentricPlanetNameList:
        rv += ",G." + planetName

    rv += endl

    for pb in swingFileData.priceBars:
        # Field: jd
        rv += "{}".format(Ephemeris.datetimeToJulianDay(pb.timestamp))
        rv += ","

        # Timezone name string, extracted from datetime.tzname().
        # This accounts for the fact that datetime.tzname() can return None.
        datetimeObj = pb.timestamp
        tznameStr = datetimeObj.tzname()
        if tznameStr == None:
            tznameStr = ""
        dayOfWeekStr = datetimeObj.ctime()[0:3]
        offsetStr = \
            Ephemeris.getTimezoneOffsetFromDatetime(datetimeObj)

        # Field: day
        rv += dayOfWeekStr
        rv += ","

        # Field: date
        rv += "{:04}-{:02}-{:02}".\
              format(datetimeObj.year,
                     datetimeObj.month,
                     datetimeObj.day)
        #rv += "{:02}/{:02}/{:04}".\
        #      format(datetimeObj.month,
        #             datetimeObj.day,
        #             datetimeObj.year)
        rv += ","

        # Field: time
        rv += "{:02}:{:02}:{:02}".\
              format(datetimeObj.hour,
                     datetimeObj.minute,
                     datetimeObj.second)
        rv += ","

        # Field: timezone.
        rv += "{}{}".format(tznameStr, offsetStr)
        rv += ","

        # Field: tags
        for tag in pb.tags:
            rv += tag + " "
        rv += ","

        # Field: open
        rv += "{}".format(pb.open)
        rv += ","

        # Field: high
        rv += "{}".format(pb.high)
        rv += ","

        # Field: low
        rv += "{}".format(pb.low)
        rv += ","

        # Field: close
        rv += "{}".format(pb.close)
        rv += ","

        # Field: volume
        rv += "{}".format(pb.vol)
        rv += ","

        # Field: oi
        rv += "{}".format(pb.oi)
        rv += ","

        # Get PlanetaryInfos for this timestamp.
        planetaryInfos = \
            getPlanetaryInfosForDatetime(pb.timestamp,
                                         swingFileData.birthInfo)

        # Fields of the geocentric planets' longitude 15-degree axis points.
        for planetName in geocentricPlanetNameList:
            for pi in planetaryInfos:
                if pi.name == planetName:
                    lon = pi.geocentric['tropical']['longitude']
                    rv += "{:6.3f},".format(lon % 15.0)
                    break

        # Fields of the geocentric planets' longitude.
        for planetName in geocentricPlanetNameList:
            for pi in planetaryInfos:
                if pi.name == planetName:
                    lon = pi.geocentric['tropical']['longitude']
                    valueStr = AstrologyUtils.\
                               convertLongitudeToStrWithRasiAbbrev(lon)
                    rv += "{},".format(valueStr)
                    break

        # Chop off the last trailing comma.
        rv = rv[:-1]
        rv += endl

    return rv
Пример #3
0
def processPCDD(pcdd, tag):
    """
    Module for printing information about the BirthInfo in a
    PriceChartDocumentData object.  BirthInfo printed includes:
 
     - Birth location name.
     - Birth country name.
     - Birth location coordinates.
     - Birth timestamp as a UTC datetime.datetime
     - Birth timestamp as a julian day.

    Arguments:
    pcdd - PriceChartDocumentData object that will be modified.
    tag  - str containing the tag.  The value of this field
           may be "" if a tag is not specified by the user.
           This implementation doesn't use this field.
           
    Returns:
    0 if the changes are to be saved to file.
    1 if the changes are NOT to be saved to file.
    This implementation always returns 1.
    """

    # Return value.
    rv = 1

    birthInfo = pcdd.birthInfo

    # Convert longitude from a float value to degrees,
    # minutes, seconds and East/West polarity.
    (lonDegrees, lonMinutes, lonSeconds, lonPolarity) = \
        GeoInfo.longitudeToDegMinSec(birthInfo.longitudeDegrees)

    # Convert latitude from a float value to degrees, minutes,
    # seconds and North/South polarity.
    (latDegrees, latMinutes, latSeconds, latPolarity) = \
        GeoInfo.latitudeToDegMinSec(birthInfo.latitudeDegrees)

    log.info("")
    log.info("Birth location name: {}".format(birthInfo.locationName))
    log.info("Birth location country: {}".format(birthInfo.countryName))
    log.info("Birth location longitude: {} {} {}' {} ({})".\
             format(lonDegrees,
                    lonPolarity,
                    lonMinutes,
                    lonSeconds,
                    birthInfo.longitudeDegrees))
    log.info("Birth location latitude:  {} {} {}' {} ({})".\
             format(latDegrees,
                    latPolarity,
                    latMinutes,
                    latSeconds,
                    birthInfo.latitudeDegrees))

    birthLocalizedDatetime = birthInfo.getBirthLocalizedDatetime()
    birthUtcDatetime = birthInfo.getBirthUtcDatetime()
    birthJd = Ephemeris.datetimeToJulianDay(birthUtcDatetime)
    log.info("Birth timestamp (localized):  {}".\
             format(Ephemeris.datetimeToStr(birthLocalizedDatetime)))
    log.info("Birth timestamp (UTC):        {}".\
             format(Ephemeris.datetimeToStr(birthUtcDatetime)))
    log.info("Birth timestamp (julian day): {}".\
             format(birthJd))
    log.info("")

    rv = 1
    return rv
def processPCDD(pcdd, tag):
    """Module for printing generic information about the PriceBars in a
    PriceChartDocumentData object.  The generic information that is
    printed includes:
 
     - Earliest pricebar timestamp as a datetime.datetime and a julian day.
     - Latest   pricebar timestamp as a datetime.datetime and a julian day.
     - highest  pricebar high price.
     - lowest   pricebar low price.

    Arguments:
    pcdd - PriceChartDocumentData object that will be modified.
    tag  - str containing the tag.  The value of this field
           may be "" if a tag is not specified by the user.
           This implementation doesn't use this field.
           
    Returns:
    0 if the changes are to be saved to file.
    1 if the changes are NOT to be saved to file.
    This implementation always returns 1.
    """

    # Return value.
    rv = 1

    # Get the number of PriceBars.
    numPriceBars = len(pcdd.priceBars)
    
    # Get the earliest and latest PriceBar.
    earliestPriceBar = None
    latestPriceBar = None
    lowestPrice = None
    highestPrice = None
    lowestClosePrice = None
    highestClosePrice = None

    for pb in pcdd.priceBars:
        if earliestPriceBar == None:
            earliestPriceBar = pb
        elif pb.timestamp < earliestPriceBar.timestamp:
            earliestPriceBar = pb

        if latestPriceBar == None:
            latestPriceBar = pb
        elif pb.timestamp > latestPriceBar.timestamp:
            latestPriceBar = pb

        if lowestPrice == None:
            lowestPrice = pb.low
        elif pb.low < lowestPrice:
            lowestPrice = pb.low

        if highestPrice == None:
            highestPrice = pb.high
        elif pb.high > highestPrice:
            highestPrice = pb.high
            
        if lowestClosePrice == None:
            lowestClosePrice = pb.close
        elif pb.close < lowestClosePrice:
            lowestClosePrice = pb.close

        if highestClosePrice == None:
            highestClosePrice = pb.close
        elif pb.close > highestClosePrice:
            highestClosePrice = pb.close
            
    log.info("")
    log.info("Number of PriceBars: {}".format(numPriceBars))

    if numPriceBars > 0:

        # Make sure we got values for everything.
        if earliestPriceBar == None or \
               latestPriceBar == None or \
               lowestPrice == None or \
               highestPrice == None or \
               lowestClosePrice == None or \
               highestClosePrice == None:
            
            log.error("PriceBars existed, but we are missing some set values.")
            rv = 1
            return rv
        
        # Convert the datetimes to julian day.
        earliestPriceBarJd = \
            Ephemeris.datetimeToJulianDay(earliestPriceBar.timestamp)
        latestPriceBarJd = \
            Ephemeris.datetimeToJulianDay(latestPriceBar.timestamp)

        # Print the information to log.
        log.info("EarliestPriceBar datetime   == {}".\
                 format(Ephemeris.datetimeToStr(earliestPriceBar.timestamp)))
        log.info("LatestPriceBar   datetime   == {}".\
                 format(Ephemeris.datetimeToStr(latestPriceBar.timestamp)))
        log.info("EarliestPriceBar julian day == {}".format(earliestPriceBarJd))
        log.info("LatestPriceBar   julian day == {}".format(latestPriceBarJd))
        log.info("Lowest  PriceBar LOW   price == {}".format(highestPrice))
        log.info("Highest PriceBar HIGH  price == {}".format(highestPrice))
        log.info("Lowest  PriceBar CLOSE price == {}".format(highestPrice))
        log.info("Highest PriceBar CLOSE price == {}".format(highestPrice))
        
    log.info("")

    rv = 1
    return rv
def getTimestampInfoDataLine(dt):
    """Takes the timestamp described by the given datetime.datetime,
    and returns a str in CSV format, describing this timestamp.

    Arguments:
    
    dt - datetime.datetime object holding the timestamp of which to
         get information on.

    Returns:
    str in CSV format, holding the information regarding this timestamp.
    The data in this string is:
    
        jd,day,date,time,timezone
        
    """

    # Return value.
    rv = ""
    
    # Field: jd
    rv += "{}".format(Ephemeris.datetimeToJulianDay(dt))
    rv += ","
    
    # Timezone name string, extracted from datetime.tzname().
    # This accounts for the fact that datetime.tzname() can return None.
    datetimeObj = dt
    tznameStr = datetimeObj.tzname()
    if tznameStr == None:
        tznameStr = ""
    dayOfWeekStr = datetimeObj.ctime()[0:3]
    offsetStr = \
        Ephemeris.getTimezoneOffsetFromDatetime(datetimeObj)
    
    # Field: day
    rv += dayOfWeekStr
    rv += ","
    
    # Field: date
    rv += "{:04}-{:02}-{:02}".\
          format(datetimeObj.year,
                 datetimeObj.month,
                 datetimeObj.day)
    #rv += "{:02}/{:02}/{:04}".\
    #      format(datetimeObj.month,
    #             datetimeObj.day,
    #             datetimeObj.year)
    rv += ","
    
    # Field: time
    rv += "{:02}:{:02}:{:02}".\
          format(datetimeObj.hour,
                 datetimeObj.minute,
                 datetimeObj.second)
    rv += ","
    
    # Field: timezone.
    rv += "{}{}".format(tznameStr, offsetStr)
    rv += ","

    # Remove trailing comma.
    rv = rv[:-1]

    return rv
def processPCDD(pcdd, tag):
    """Module for drawing two veritcal lines (line segments) at 1/3
    and 2/3 of the way through the price chart.  The lines will have a
    tag str matching the given tag parameter.

    Arguments:
    pcdd - PriceChartDocumentData object that will be modified.
    tag  - str containing the tag.  

    Returns:
    0 if the changes are to be saved to file.
    1 if the changes are NOT to be saved to file.
    """

    # Return value.
    rv = 0

    # Check input.
    if tag == None or tag == "":
        log.error("Must specify a non-empty tag str value.")
        rv = 1
        return rv


    # Get the earliest and latest PriceBar.
    earliestPriceBar = None
    latestPriceBar = None
    lowestPrice = None
    highestPrice = None
    
    for pb in pcdd.priceBars:
        if earliestPriceBar == None:
            earliestPriceBar = pb
        elif pb.timestamp < earliestPriceBar.timestamp:
            earliestPriceBar = pb

        if latestPriceBar == None:
            latestPriceBar = pb
        elif pb.timestamp > latestPriceBar.timestamp:
            latestPriceBar = pb

        if lowestPrice == None:
            lowestPrice = pb.low
        elif pb.low < lowestPrice:
            lowestPrice = pb.low

        if highestPrice == None:
            highestPrice = pb.high
        elif pb.high > highestPrice:
            highestPrice = pb.high
            
    if earliestPriceBar == None or \
           latestPriceBar == None or \
           lowestPrice == None or \
           highestPrice == None:
        
        log.info("No pricebars were found in the document.  " + \
                 "Not doing anything.")
        rv = 1
        return rv

    # Convert the datetimes to julian day.
    earliestPriceBarJd = \
        Ephemeris.datetimeToJulianDay(earliestPriceBar.timestamp)
    latestPriceBarJd = \
        Ephemeris.datetimeToJulianDay(latestPriceBar.timestamp)

    log.debug("earliestPriceBar.timestamp == {}".\
              format(Ephemeris.datetimeToStr(earliestPriceBar.timestamp)))
    log.debug("latestPriceBar.timestamp == {}".\
              format(Ephemeris.datetimeToStr(latestPriceBar.timestamp)))

    log.debug("earliestPriceBarJd == {}".format(earliestPriceBarJd))
    log.debug("latestPriceBarJd == {}".format(latestPriceBarJd))

    diff = latestPriceBarJd - earliestPriceBarJd

    jdLine1 = earliestPriceBarJd + (diff / 3)
    jdLine2 = earliestPriceBarJd + ((diff / 3) * 2)

    dtLine1 = Ephemeris.julianDayToDatetime(jdLine1)
    dtLine2 = Ephemeris.julianDayToDatetime(jdLine2)

    log.debug("Creating scene...")

    # Scene for conversion functions.
    scene = PriceBarChartGraphicsScene()

    log.debug("Converting dt to x...")

    line1X = scene.datetimeToSceneXPos(dtLine1)
    line2X = scene.datetimeToSceneXPos(dtLine2)
    
    log.debug("Converting price to y...")

    lowY = scene.priceToSceneYPos(lowestPrice)
    highY = scene.priceToSceneYPos(highestPrice)
    
    log.debug("Creating line1 artifact ...")
    line1Artifact = PriceBarChartLineSegmentArtifact()
    line1Artifact.addTag(tag)
    line1Artifact.setTiltedTextFlag(False)
    line1Artifact.setAngleTextFlag(False)
    line1Artifact.setColor(QColor(Qt.red))
    line1Artifact.setStartPointF(QPointF(line1X, lowY))
    line1Artifact.setEndPointF(QPointF(line1X, highY))
    
    log.debug("Creating line2 artifact ...")
    line2Artifact = PriceBarChartLineSegmentArtifact()
    line2Artifact.addTag(tag)
    line2Artifact.setTiltedTextFlag(False)
    line2Artifact.setAngleTextFlag(False)
    line2Artifact.setColor(QColor(Qt.blue))
    line2Artifact.setStartPointF(QPointF(line2X, lowY))
    line2Artifact.setEndPointF(QPointF(line2X, highY))

    log.debug("Appending two lines...")

    pcdd.priceBarChartArtifacts.append(line1Artifact)
    pcdd.priceBarChartArtifacts.append(line2Artifact)

    log.debug("Done appending two lines.")

    rv = 0
    return rv
                # - planetName1SiderealLongitude_Degrees
                # - planetName2SiderealLongitude_Degrees
                # - planetName1SiderealLongitude_ZodiacSignFormat
                # - planetName2SiderealLongitude_ZodiacSignFormat
                # - planetName1SiderealLongitudeLongitudeSpeed
                # - planetName2SiderealLongitudeLongitudeSpeed
                resultList = []

                # Create a tuple for each timestamp that was found
                # that was a conjunction.
                for dt in conjunctionTimestamps:
                    pi1 = Ephemeris.getPlanetaryInfo(planetName1, dt)
                    pi2 = Ephemeris.getPlanetaryInfo(planetName2, dt)
                    
                    tup = (comboPlanetName,
                           Ephemeris.datetimeToJulianDay(dt),
                           dt,
                           desiredAspectDegree,
                           pi1.heliocentric["tropical"]["longitude"],
                           pi2.heliocentric["tropical"]["longitude"],
                           pi1.heliocentric["tropical"]["longitude_speed"],
                           pi2.heliocentric["tropical"]["longitude_speed"],
                           pi1.heliocentric["sidereal"]["longitude"],
                           pi2.heliocentric["sidereal"]["longitude"],
                           pi1.heliocentric["sidereal"]["longitude_speed"],
                           pi2.heliocentric["sidereal"]["longitude_speed"])

                    resultList.append(tup)
                    
                results[comboPlanetName] = resultList
                
def processPCDD(pcdd, tag):
    """Module for printing generic information about the PriceBars in a
    PriceChartDocumentData object.  The generic information that is
    printed includes:
 
     - Earliest pricebar timestamp as a datetime.datetime and a julian day.
     - Latest   pricebar timestamp as a datetime.datetime and a julian day.
     - highest  pricebar high price.
     - lowest   pricebar low price.

    Arguments:
    pcdd - PriceChartDocumentData object that will be modified.
    tag  - str containing the tag.  The value of this field
           may be "" if a tag is not specified by the user.
           This implementation doesn't use this field.
           
    Returns:
    0 if the changes are to be saved to file.
    1 if the changes are NOT to be saved to file.
    This implementation always returns 1.
    """

    # Return value.
    rv = 1

    # Get the number of PriceBars.
    numPriceBars = len(pcdd.priceBars)

    # Get the earliest and latest PriceBar.
    earliestPriceBar = None
    latestPriceBar = None
    lowestPrice = None
    highestPrice = None
    lowestClosePrice = None
    highestClosePrice = None

    for pb in pcdd.priceBars:
        if earliestPriceBar == None:
            earliestPriceBar = pb
        elif pb.timestamp < earliestPriceBar.timestamp:
            earliestPriceBar = pb

        if latestPriceBar == None:
            latestPriceBar = pb
        elif pb.timestamp > latestPriceBar.timestamp:
            latestPriceBar = pb

        if lowestPrice == None:
            lowestPrice = pb.low
        elif pb.low < lowestPrice:
            lowestPrice = pb.low

        if highestPrice == None:
            highestPrice = pb.high
        elif pb.high > highestPrice:
            highestPrice = pb.high

        if lowestClosePrice == None:
            lowestClosePrice = pb.close
        elif pb.close < lowestClosePrice:
            lowestClosePrice = pb.close

        if highestClosePrice == None:
            highestClosePrice = pb.close
        elif pb.close > highestClosePrice:
            highestClosePrice = pb.close

    log.info("")
    log.info("Number of PriceBars: {}".format(numPriceBars))

    if numPriceBars > 0:

        # Make sure we got values for everything.
        if earliestPriceBar == None or \
               latestPriceBar == None or \
               lowestPrice == None or \
               highestPrice == None or \
               lowestClosePrice == None or \
               highestClosePrice == None:

            log.error("PriceBars existed, but we are missing some set values.")
            rv = 1
            return rv

        # Convert the datetimes to julian day.
        earliestPriceBarJd = \
            Ephemeris.datetimeToJulianDay(earliestPriceBar.timestamp)
        latestPriceBarJd = \
            Ephemeris.datetimeToJulianDay(latestPriceBar.timestamp)

        # Print the information to log.
        log.info("EarliestPriceBar datetime   == {}".\
                 format(Ephemeris.datetimeToStr(earliestPriceBar.timestamp)))
        log.info("LatestPriceBar   datetime   == {}".\
                 format(Ephemeris.datetimeToStr(latestPriceBar.timestamp)))
        log.info(
            "EarliestPriceBar julian day == {}".format(earliestPriceBarJd))
        log.info("LatestPriceBar   julian day == {}".format(latestPriceBarJd))
        log.info("Lowest  PriceBar LOW   price == {}".format(highestPrice))
        log.info("Highest PriceBar HIGH  price == {}".format(highestPrice))
        log.info("Lowest  PriceBar CLOSE price == {}".format(highestPrice))
        log.info("Highest PriceBar CLOSE price == {}".format(highestPrice))

    log.info("")

    rv = 1
    return rv
def convertSwingFileDataToCsvStr(swingFileData):
    """Takes a SwingFileData and generates a CSV str containing most
    of the swing file data.
    """

    endl = "\n"

    rv = ""

    rv += "Trading Entity Description: {}".\
          format(swingFileData.tradingEntityDescription) + endl
    #rv += "Swing File Description: {}".\
    #      format(swingFileData.swingFileDescription) + endl
    #rv += "User notes: {}".\
    #      format(swingFileData.userNotes) + endl
    rv += "Source Swing File: {}".\
          format(swingFile) + endl
    #rv += "Source PCD filename: {}".\
    #      format(swingFileData.sourcePcdFilename) + endl
    #rv += "Source PriceBar data filename: {}".\
    #      format(swingFileData.sourcePriceBarDataFilename) + endl

    rv += "jd,day,date,time,timezone,tags,open,high,low,close,volume,oi" + endl

    for pb in swingFileData.priceBars:
        # Field: jd
        rv += "{}".format(Ephemeris.datetimeToJulianDay(pb.timestamp))
        rv += ","

        # Timezone name string, extracted from datetime.tzname().
        # This accounts for the fact that datetime.tzname() can return None.
        datetimeObj = pb.timestamp
        tznameStr = datetimeObj.tzname()
        if tznameStr == None:
            tznameStr = ""
        dayOfWeekStr = datetimeObj.ctime()[0:3]
        offsetStr = \
            Ephemeris.getTimezoneOffsetFromDatetime(datetimeObj)

        # Field: day
        rv += dayOfWeekStr
        rv += ","

        # Field: date
        rv += "{:04}-{:02}-{:02}".\
              format(datetimeObj.year,
                     datetimeObj.month,
                     datetimeObj.day)
        #rv += "{:02}/{:02}/{:04}".\
        #      format(datetimeObj.month,
        #             datetimeObj.day,
        #             datetimeObj.year)
        rv += ","

        # Field: time
        rv += "{:02}:{:02}:{:02}".\
              format(datetimeObj.hour,
                     datetimeObj.minute,
                     datetimeObj.second)
        rv += ","

        # Field: timezone.
        rv += "{}{}".format(tznameStr, offsetStr)
        rv += ","

        # Field: tags
        for tag in pb.tags:
            rv += tag + " "
        rv += ","

        # Field: open
        rv += "{}".format(pb.open)
        rv += ","

        # Field: high
        rv += "{}".format(pb.high)
        rv += ","

        # Field: low
        rv += "{}".format(pb.low)
        rv += ","

        # Field: close
        rv += "{}".format(pb.close)
        rv += ","

        # Field: volume
        rv += "{}".format(pb.vol)
        rv += ","

        # Field: oi
        rv += "{}".format(pb.oi)
        rv += ","

        rv = rv[:-1]
        rv += endl

    return rv
Пример #10
0
def getTimestampInfoDataLine(dt):
    """Takes the timestamp described by the given datetime.datetime,
    and returns a str in CSV format, describing this timestamp.

    Arguments:
    
    dt - datetime.datetime object holding the timestamp of which to
         get information on.

    Returns:
    str in CSV format, holding the information regarding this timestamp.
    The data in this string is:
    
        jd,day,date,time,timezone
        
    """

    # Return value.
    rv = ""

    # Field: jd
    rv += "{}".format(Ephemeris.datetimeToJulianDay(dt))
    rv += ","

    # Timezone name string, extracted from datetime.tzname().
    # This accounts for the fact that datetime.tzname() can return None.
    datetimeObj = dt
    tznameStr = datetimeObj.tzname()
    if tznameStr == None:
        tznameStr = ""
    dayOfWeekStr = datetimeObj.ctime()[0:3]
    offsetStr = \
        Ephemeris.getTimezoneOffsetFromDatetime(datetimeObj)

    # Field: day
    rv += dayOfWeekStr
    rv += ","

    # Field: date
    rv += "{:04}-{:02}-{:02}".\
          format(datetimeObj.year,
                 datetimeObj.month,
                 datetimeObj.day)
    #rv += "{:02}/{:02}/{:04}".\
    #      format(datetimeObj.month,
    #             datetimeObj.day,
    #             datetimeObj.year)
    rv += ","

    # Field: time
    rv += "{:02}:{:02}:{:02}".\
          format(datetimeObj.hour,
                 datetimeObj.minute,
                 datetimeObj.second)
    rv += ","

    # Field: timezone.
    rv += "{}{}".format(tznameStr, offsetStr)
    rv += ","

    # Remove trailing comma.
    rv = rv[:-1]

    return rv
Пример #11
0
def generateOutputFileCsvStr(priceBars, descriptionStr):
    """Takes a list of PriceBar objects and generates a CSV str
    containing the same data and planet location information.

    Arguments:
    priceBars - list of PriceBar objects.  Each of the PriceBar
                objects in this list have timestamp and timezone
                information set.
                
    descriptionStr - str containing text that describes the trading entity
                and other descriptive text for the data.  This str
                will be part of the outputted CSV str.

    Returns:
    str value for the output CSV text.
    """

    geocentricPlanetNameList = [\
        "Sun",
        "Mercury",
        "Venus",
        "Mars",
        "Jupiter",
        "Saturn",
        "Uranus",
        "Neptune",
        "Pluto",
        "Chiron",
        "TrueNorthNode",
        #"Isis",
        ]

    endl = "\n"

    # Return value.
    rv = ""

    rv += "Description: {}".\
          format(descriptionStr) + endl

    # Column headers.
    rv += "jd,day,date,time,timezone,tags,open,high,low,close,volume,oi"

    # Add the columns headers for the Geocentric planets' longitude.
    # Here we do it twice because the first set is the 15-degree axis
    # reduction, and the second set is the actual planet positions.
    for planetName in geocentricPlanetNameList:
        rv += ",G." + planetName
    for planetName in geocentricPlanetNameList:
        rv += ",G." + planetName

    rv += endl

    for pb in priceBars:
        # Field: jd
        rv += "{}".format(Ephemeris.datetimeToJulianDay(pb.timestamp))
        rv += ","

        # Timezone name string, extracted from datetime.tzname().
        # This accounts for the fact that datetime.tzname() can return None.
        datetimeObj = pb.timestamp
        tznameStr = datetimeObj.tzname()
        if tznameStr == None:
            tznameStr = ""
        dayOfWeekStr = datetimeObj.ctime()[0:3]
        offsetStr = \
            Ephemeris.getTimezoneOffsetFromDatetime(datetimeObj)

        # Field: day
        rv += dayOfWeekStr
        rv += ","

        # Field: date
        rv += "{:04}-{:02}-{:02}".\
              format(datetimeObj.year,
                     datetimeObj.month,
                     datetimeObj.day)
        #rv += "{:02}/{:02}/{:04}".\
        #      format(datetimeObj.month,
        #             datetimeObj.day,
        #             datetimeObj.year)
        rv += ","

        # Field: time
        rv += "{:02}:{:02}:{:02}".\
              format(datetimeObj.hour,
                     datetimeObj.minute,
                     datetimeObj.second)
        rv += ","

        # Field: timezone.
        rv += "{}{}".format(tznameStr, offsetStr)
        rv += ","

        # Field: tags
        for tag in pb.tags:
            rv += tag + " "
        rv += ","

        # Field: open
        rv += "{}".format(pb.open)
        rv += ","

        # Field: high
        rv += "{}".format(pb.high)
        rv += ","

        # Field: low
        rv += "{}".format(pb.low)
        rv += ","

        # Field: close
        rv += "{}".format(pb.close)
        rv += ","

        # Field: volume
        rv += "{}".format(pb.vol)
        rv += ","

        # Field: oi
        rv += "{}".format(pb.oi)
        rv += ","

        # Get PlanetaryInfos for this timestamp.
        planetaryInfos = \
            getPlanetaryInfosForDatetime(pb.timestamp)

        # Fields of the geocentric planets' longitude 15-degree axis points.
        for planetName in geocentricPlanetNameList:
            for pi in planetaryInfos:
                if pi.name == planetName:
                    lon = pi.geocentric['tropical']['longitude']
                    rv += "{:6.3f},".format(lon % 15.0)
                    break

        # Fields of the geocentric planets' longitude.
        for planetName in geocentricPlanetNameList:
            for pi in planetaryInfos:
                if pi.name == planetName:
                    lon = pi.geocentric['tropical']['longitude']
                    valueStr = AstrologyUtils.\
                               convertLongitudeToStrWithRasiAbbrev(lon)
                    rv += "{},".format(valueStr)
                    break

        # Chop off the last trailing comma.
        rv = rv[:-1]
        rv += endl

    return rv
Пример #12
0
def processPCDD(pcdd, tag):
    """Module for drawing two veritcal lines (line segments) at 1/3
    and 2/3 of the way through the price chart.  The lines will have a
    tag str matching the given tag parameter.

    Arguments:
    pcdd - PriceChartDocumentData object that will be modified.
    tag  - str containing the tag.  

    Returns:
    0 if the changes are to be saved to file.
    1 if the changes are NOT to be saved to file.
    """

    # Return value.
    rv = 0

    # Check input.
    if tag == None or tag == "":
        log.error("Must specify a non-empty tag str value.")
        rv = 1
        return rv

    # Get the earliest and latest PriceBar.
    earliestPriceBar = None
    latestPriceBar = None
    lowestPrice = None
    highestPrice = None

    for pb in pcdd.priceBars:
        if earliestPriceBar == None:
            earliestPriceBar = pb
        elif pb.timestamp < earliestPriceBar.timestamp:
            earliestPriceBar = pb

        if latestPriceBar == None:
            latestPriceBar = pb
        elif pb.timestamp > latestPriceBar.timestamp:
            latestPriceBar = pb

        if lowestPrice == None:
            lowestPrice = pb.low
        elif pb.low < lowestPrice:
            lowestPrice = pb.low

        if highestPrice == None:
            highestPrice = pb.high
        elif pb.high > highestPrice:
            highestPrice = pb.high

    if earliestPriceBar == None or \
           latestPriceBar == None or \
           lowestPrice == None or \
           highestPrice == None:

        log.info("No pricebars were found in the document.  " + \
                 "Not doing anything.")
        rv = 1
        return rv

    # Convert the datetimes to julian day.
    earliestPriceBarJd = \
        Ephemeris.datetimeToJulianDay(earliestPriceBar.timestamp)
    latestPriceBarJd = \
        Ephemeris.datetimeToJulianDay(latestPriceBar.timestamp)

    log.debug("earliestPriceBar.timestamp == {}".\
              format(Ephemeris.datetimeToStr(earliestPriceBar.timestamp)))
    log.debug("latestPriceBar.timestamp == {}".\
              format(Ephemeris.datetimeToStr(latestPriceBar.timestamp)))

    log.debug("earliestPriceBarJd == {}".format(earliestPriceBarJd))
    log.debug("latestPriceBarJd == {}".format(latestPriceBarJd))

    diff = latestPriceBarJd - earliestPriceBarJd

    jdLine1 = earliestPriceBarJd + (diff / 3)
    jdLine2 = earliestPriceBarJd + ((diff / 3) * 2)

    dtLine1 = Ephemeris.julianDayToDatetime(jdLine1)
    dtLine2 = Ephemeris.julianDayToDatetime(jdLine2)

    log.debug("Creating scene...")

    # Scene for conversion functions.
    scene = PriceBarChartGraphicsScene()

    log.debug("Converting dt to x...")

    line1X = scene.datetimeToSceneXPos(dtLine1)
    line2X = scene.datetimeToSceneXPos(dtLine2)

    log.debug("Converting price to y...")

    lowY = scene.priceToSceneYPos(lowestPrice)
    highY = scene.priceToSceneYPos(highestPrice)

    log.debug("Creating line1 artifact ...")
    line1Artifact = PriceBarChartLineSegmentArtifact()
    line1Artifact.addTag(tag)
    line1Artifact.setTiltedTextFlag(False)
    line1Artifact.setAngleTextFlag(False)
    line1Artifact.setColor(QColor(Qt.red))
    line1Artifact.setStartPointF(QPointF(line1X, lowY))
    line1Artifact.setEndPointF(QPointF(line1X, highY))

    log.debug("Creating line2 artifact ...")
    line2Artifact = PriceBarChartLineSegmentArtifact()
    line2Artifact.addTag(tag)
    line2Artifact.setTiltedTextFlag(False)
    line2Artifact.setAngleTextFlag(False)
    line2Artifact.setColor(QColor(Qt.blue))
    line2Artifact.setStartPointF(QPointF(line2X, lowY))
    line2Artifact.setEndPointF(QPointF(line2X, highY))

    log.debug("Appending two lines...")

    pcdd.priceBarChartArtifacts.append(line1Artifact)
    pcdd.priceBarChartArtifacts.append(line2Artifact)

    log.debug("Done appending two lines.")

    rv = 0
    return rv
Пример #13
0
def getGeocentricPlanetDirectRetrogradeInfo(planetName):
    """
    Returns a list of tuples, each tuple containing:
    (planetName,
    julianDay,
    datetime,
    "R" or "D",
    geoTropLongitudeOfPlanet,
    geoSidLongitudeOfPlanet)
    """

    # Return value.
    rv = []

    prevDt = None
    currDt = copy.deepcopy(startDt)

    prevTropLongitudeSpeed = None
    currTropLongitudeSpeed = None

    currTropLongitude = None
    currSidLongitude = None

    while currDt <= endDt:
        dt = currDt

        pi = Ephemeris.getPlanetaryInfo(planetName, dt)

        log.debug("Just obtained planetaryInfo for planet '{}', timestamp: {}".\
                  format(planetName, Ephemeris.datetimeToStr(dt)))

        # Get the geocentric longitude and geocentric longitude speed.
        tropLongitudeSpeed = pi.geocentric['tropical']['longitude_speed']
        tropLongitude = pi.geocentric['tropical']['longitude']
        sidLongitude = pi.geocentric['sidereal']['longitude']

        # Store new current planet values.
        currTropLongitudeSpeed = tropLongitudeSpeed
        currTropLongitude = tropLongitude
        currSidLongitude = sidLongitude

        log.debug("prevTropLongitudeSpeed={}, currTropLongitudeSpeed={}".\
                  format(prevTropLongitudeSpeed, currTropLongitudeSpeed))

        # We need two data points to proceed.
        if prevTropLongitudeSpeed != None and \
               currTropLongitudeSpeed != None and \
               prevDt != None:

            # Check to see if we passed over 0 degrees.

            if prevTropLongitudeSpeed < 0.0 and currTropLongitudeSpeed >= 0.0:
                # Crossed over from negative to positive!
                log.debug("Crossed over from negative to positive!")

                # This is the upper-bound of the error timedelta.
                t1 = prevDt
                t2 = currDt
                currErrorTd = t2 - t1

                # Refine the timestamp until it is less than the
                # desired threshold.
                while currErrorTd > maxErrorTd:
                    log.debug("Refining between {} and {}".\
                              format(Ephemeris.datetimeToStr(t1),
                                     Ephemeris.datetimeToStr(t2)))

                    # Check the timestamp between.
                    diffTd = t2 - t1
                    halfDiffTd = \
                        datetime.\
                        timedelta(days=(diffTd.days / 2.0),
                                  seconds=(diffTd.seconds / 2.0),
                                  microseconds=(diffTd.microseconds / 2.0))
                    testDt = t1 + halfDiffTd

                    pi = Ephemeris.getPlanetaryInfo(planetName, testDt)

                    testTropLongitudeSpeed = \
                        pi.geocentric['tropical']['longitude_speed']
                    testTropLongitude = pi.geocentric['tropical']['longitude']
                    testSidLongitude = pi.geocentric['sidereal']['longitude']

                    if testTropLongitudeSpeed >= 0.0:
                        t2 = testDt

                        # Update the curr values as the later boundary.
                        currDt = t2
                        currTropLongitudeSpeed = testTropLongitudeSpeed
                        currTropLongitude = testTropLongitude
                        currSidLongitude = testSidLongitude
                    else:
                        t1 = testDt

                    currErrorTd = t2 - t1

                # Broke out of while loop, meaning we have a timestamp
                # within our threshold.
                # Create a tuple to add to our list.
                tup = (planetName, Ephemeris.datetimeToJulianDay(currDt),
                       currDt, directStr, currTropLongitude, currSidLongitude)

                # Append to the list.
                rv.append(tup)

            elif prevTropLongitudeSpeed > 0.0 and currTropLongitudeSpeed <= 0.0:
                # Crossed over from positive to negative!
                log.debug("Crossed over from positive to negative!")

                # This is the upper-bound of the error timedelta.
                t1 = prevDt
                t2 = currDt
                currErrorTd = t2 - t1

                # Refine the timestamp until it is less than the
                # desired threshold.
                while currErrorTd > maxErrorTd:
                    log.debug("Refining between {} and {}".\
                              format(Ephemeris.datetimeToStr(t1),
                                     Ephemeris.datetimeToStr(t2)))

                    # Check the timestamp between.
                    diffTd = t2 - t1
                    halfDiffTd = \
                        datetime.\
                        timedelta(days=(diffTd.days / 2.0),
                                  seconds=(diffTd.seconds / 2.0),
                                  microseconds=(diffTd.microseconds / 2.0))
                    testDt = t1 + halfDiffTd

                    pi = Ephemeris.getPlanetaryInfo(planetName, testDt)

                    testTropLongitudeSpeed = \
                        pi.geocentric['tropical']['longitude_speed']
                    testTropLongitude = pi.geocentric['tropical']['longitude']
                    testSidLongitude = pi.geocentric['sidereal']['longitude']

                    if testTropLongitudeSpeed <= 0.0:
                        t2 = testDt

                        # Update the curr values as the later boundary.
                        currDt = t2
                        currTropLongitudeSpeed = testTropLongitudeSpeed
                        currTropLongitude = testTropLongitude
                        currSidLongitude = testSidLongitude
                    else:
                        t1 = testDt

                    currErrorTd = t2 - t1

                # Broke out of while loop, meaning we have a timestamp
                # within our threshold.
                # Create a tuple to add to our list.
                tup = (planetName, Ephemeris.datetimeToJulianDay(currDt),
                       currDt, retrogradeStr, currTropLongitude,
                       currSidLongitude)

                # Append to the list.
                rv.append(tup)

        # Increment currDt timestamp.
        prevDt = currDt
        currDt = currDt + stepSizeTd

        # Move the previous currTropLongitudeSpeed to prevTropLongitudeSpeed.
        prevTropLongitudeSpeed = currTropLongitudeSpeed
        currTropLongitudeSpeed = None
        currTropLongitude = None
        currSidLongitude = None

        log.debug("prevTropLongitudeSpeed={}, currTropLongitudeSpeed={}".\
                  format(prevTropLongitudeSpeed, currTropLongitudeSpeed))

    return rv
Пример #14
0
def processPCDD(pcdd, tag):
    """
    Module for printing information about the BirthInfo in a
    PriceChartDocumentData object.  BirthInfo printed includes:
 
     - Birth location name.
     - Birth country name.
     - Birth location coordinates.
     - Birth timestamp as a UTC datetime.datetime
     - Birth timestamp as a julian day.

    Arguments:
    pcdd - PriceChartDocumentData object that will be modified.
    tag  - str containing the tag.  The value of this field
           may be "" if a tag is not specified by the user.
           This implementation doesn't use this field.
           
    Returns:
    0 if the changes are to be saved to file.
    1 if the changes are NOT to be saved to file.
    This implementation always returns 1.
    """

    # Return value.
    rv = 1

    birthInfo = pcdd.birthInfo

    # Convert longitude from a float value to degrees,
    # minutes, seconds and East/West polarity.
    (lonDegrees, lonMinutes, lonSeconds, lonPolarity) = \
        GeoInfo.longitudeToDegMinSec(birthInfo.longitudeDegrees)
    
    # Convert latitude from a float value to degrees, minutes,
    # seconds and North/South polarity.
    (latDegrees, latMinutes, latSeconds, latPolarity) = \
        GeoInfo.latitudeToDegMinSec(birthInfo.latitudeDegrees)
    
    log.info("")
    log.info("Birth location name: {}".format(birthInfo.locationName))
    log.info("Birth location country: {}".format(birthInfo.countryName))
    log.info("Birth location longitude: {} {} {}' {} ({})".\
             format(lonDegrees,
                    lonPolarity,
                    lonMinutes,
                    lonSeconds,
                    birthInfo.longitudeDegrees))
    log.info("Birth location latitude:  {} {} {}' {} ({})".\
             format(latDegrees,
                    latPolarity,
                    latMinutes,
                    latSeconds,
                    birthInfo.latitudeDegrees))

    birthLocalizedDatetime = birthInfo.getBirthLocalizedDatetime()
    birthUtcDatetime = birthInfo.getBirthUtcDatetime()
    birthJd = Ephemeris.datetimeToJulianDay(birthUtcDatetime)
    log.info("Birth timestamp (localized):  {}".\
             format(Ephemeris.datetimeToStr(birthLocalizedDatetime)))
    log.info("Birth timestamp (UTC):        {}".\
             format(Ephemeris.datetimeToStr(birthUtcDatetime)))
    log.info("Birth timestamp (julian day): {}".\
             format(birthJd))
    log.info("")

    rv = 1
    return rv