Skip to content

Commit

Permalink
Relinted uilib and motorlib
Browse files Browse the repository at this point in the history
  • Loading branch information
reilleya committed Jul 2, 2019
1 parent b957ea7 commit ca6691e
Show file tree
Hide file tree
Showing 9 changed files with 23 additions and 33 deletions.
2 changes: 1 addition & 1 deletion motorlib/grain.py
Expand Up @@ -185,7 +185,7 @@ def getFaceImage(self, mapDim):
"""Returns an image of the grain's cross section, with resolution (mapDim, mapDim)."""

@abstractmethod
def getRegressionData(self, mapDim, numContours=15):
def getRegressionData(self, mapDim, numContours=15, coreBlack=True):
"""Returns a tuple that includes a grain face image as described in 'getFaceImage', a regression map
where color maps to regression depth, a list of contours (lists of (x,y) points in image space) of
equal regression depth, and a list of corresponding contour lengths. The contours are equally spaced
Expand Down
9 changes: 3 additions & 6 deletions motorlib/motor.py
@@ -1,7 +1,5 @@
"""Conains the motor class and a supporting configuration property collection."""

import numpy as np

from .grains import grainTypes
from .nozzle import Nozzle
from .propellant import Propellant
Expand Down Expand Up @@ -120,7 +118,7 @@ def calcIdealThrustCoeff(self, chamberPres):
def calcForce(self, chamberPres):
"""Calculates the force of the motor at a given regression depth per grain. Calculates pressure by default,
but can also use a value passed in. This method uses a combination of the techniques described in these
resources to adjust the thrust coefficient: https://apps.dtic.mil/dtic/tr/fulltext/u2/a099791.pdf and
resources to adjust the thrust coefficient: https://apps.dtic.mil/dtic/tr/fulltext/u2/a099791.pdf and
http://rasaero.com/dloads/Departures%20from%20Ideal%20Performance.pdf."""
thrustCoeffIdeal = self.calcIdealThrustCoeff(chamberPres)
divLoss = self.nozzle.getDivergenceLosses()
Expand All @@ -138,7 +136,6 @@ def runSimulation(self, callback=None):
using the pressure to determine how the motor will regress in the given timestep at the current pressure.
This process is repeated and regression tracked until all grains have burned out, when the results and any
warnings are returned."""
ambientPressure = self.config.getProperty('ambPressure')
burnoutWebThres = self.config.getProperty('burnoutWebThres')
burnoutThrustThres = self.config.getProperty('burnoutThrustThres')
dTime = self.config.getProperty('timestep')
Expand Down Expand Up @@ -199,8 +196,8 @@ def runSimulation(self, callback=None):
desc = 'Initial port/throat ratio of ' + str(round(ratio, 3)) + ' was less than ' + str(minAllowed)
simRes.addAlert(SimAlert(SimAlertLevel.WARNING, SimAlertType.CONSTRAINT, desc, 'N/A'))

# Perform timesteps, 0.01 converts the threshold to a %
while len(simRes.channels['time'].getData()) == 1 or simRes.channels['force'].getLast() > burnoutThrustThres * 0.01 * simRes.channels['force'].getMax():
# Perform timesteps
while simRes.shouldContinueSim(burnoutThrustThres):
# Calculate regression
massFlow = 0
perGrainMass = [0 for grain in self.grains]
Expand Down
8 changes: 8 additions & 0 deletions motorlib/simResult.py
Expand Up @@ -204,6 +204,14 @@ def getAlertsByLevel(self, level):
out.append(alert)
return out

def shouldContinueSim(self, thrustThres):
"""Returns if the simulation should continue based on the thrust from the last timestep."""
# With only one data point, there is nothing to compare
if len(self.channels['time'].getData()) == 1:
return True
# Otherwise perform the comparison. 0.01 converts the threshold to a %
return self.channels['force'].getLast() > thrustThres * 0.01 * self.channels['force'].getMax()

def getCSV(self, pref=None, exclude=[]):
"""Returns a string that contains a CSV of the simulated data. Preferences can be passed in to set units that
the values will be converted to. All log channels are included unless their names are in the include
Expand Down
2 changes: 1 addition & 1 deletion motorlib/units.py
Expand Up @@ -74,7 +74,7 @@ def convertAll(quantities, originUnit, destUnit):
convRate = getConversion(originUnit, destUnit)
return [q * convRate for q in quantities]

def format(quantity, originUnit, destUnit, places=3):
def convFormat(quantity, originUnit, destUnit, places=3):
"""Takes in a quantity in originUnit, converts it to destUnit and outputs a rounded and formatted string that
includes the unit appended to the end."""
num = round(convert(quantity, originUnit, destUnit), places)
Expand Down
9 changes: 1 addition & 8 deletions uilib/widgets/grainImageWidget.py
@@ -1,20 +1,13 @@
from PyQt5.QtWidgets import QMainWindow, QLabel, QSizePolicy, QApplication
from PyQt5.QtWidgets import QLabel
from PyQt5.QtGui import QPixmap, QImage
from PyQt5.QtCore import Qt
import numpy as np

import motorlib

class GrainImageWidget(QLabel):
def __init__(self):
super().__init__()

def showImage(self, image):
np.ma.set_fill_value(image, 0)
image = np.logical_not(image.filled())
image = image.astype(np.uint8) * 255
height, width = image.shape
bytesPerLine = width
qImg = QImage(image.data, width, height, QImage.Format_Grayscale8)
pixmap = QPixmap(qImg)
self.setPixmap(pixmap)
6 changes: 2 additions & 4 deletions uilib/widgets/grainSelector.py
@@ -1,8 +1,6 @@
from PyQt5.QtWidgets import QGroupBox, QCheckBox, QRadioButton, QVBoxLayout
from PyQt5.QtCore import pyqtSignal

import motorlib

class GrainSelector(QGroupBox):

checksChanged = pyqtSignal()
Expand All @@ -15,13 +13,13 @@ def __init__(self, parent):
self.setTitle("Grains")

def resetChecks(self):
for check in range(0, len(self.checks)):
for _ in range(0, len(self.checks)):
self.layout().removeWidget(self.checks[-1])
self.checks[-1].deleteLater()
del self.checks[-1]

def setupChecks(self, simRes, multiselect):
for gid, grain in enumerate(simRes.motor.grains):
for gid, _ in enumerate(simRes.motor.grains):
checkTitle = "Grain " + str(gid + 1)
if multiselect:
check = QCheckBox(checkTitle)
Expand Down
2 changes: 1 addition & 1 deletion uilib/widgets/graphWidget.py
Expand Up @@ -63,4 +63,4 @@ def resetPlot(self):
self.draw()

def saveImage(self, filename):
self.figure.savefig(filename)
self.figure.savefig(filename)
5 changes: 2 additions & 3 deletions uilib/widgets/motorEditor.py
@@ -1,4 +1,4 @@
from PyQt5.QtWidgets import QLabel, QListWidget, QSizePolicy
from PyQt5.QtWidgets import QLabel

import motorlib.grain
import motorlib.nozzle
Expand All @@ -24,8 +24,7 @@ def __init__(self, parent):
self.nozzlePreview.hide()
self.stats.addWidget(self.nozzlePreview)

self.nozzle = True
self.grainClass = None
self.objType = None

def propertyUpdate(self):
if issubclass(self.objType, motorlib.nozzle.Nozzle):
Expand Down
13 changes: 4 additions & 9 deletions uilib/widgets/resultsWidget.py
@@ -1,9 +1,4 @@
from threading import Thread

from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
from matplotlib.figure import Figure
from PyQt5.QtWidgets import QWidget, QHeaderView, QLabel
from PyQt5.QtCore import pyqtSignal

import motorlib

Expand Down Expand Up @@ -96,14 +91,14 @@ def updateGrainTab(self):
currentImpulse = self.simResult.getImpulse(index)
remainingImpulse = self.simResult.getImpulse() - currentImpulse
impUnit = self.preferences.getUnit('Ns')
self.ui.labelImpulseProgress.setText(motorlib.units.format(currentImpulse, 'Ns', impUnit))
self.ui.labelImpulseRemaining.setText(motorlib.units.format(remainingImpulse, 'Ns', impUnit))
self.ui.labelImpulseProgress.setText(motorlib.units.convFormat(currentImpulse, 'Ns', impUnit))
self.ui.labelImpulseRemaining.setText(motorlib.units.convFormat(remainingImpulse, 'Ns', impUnit))

currentMass = self.simResult.getPropellantMass(index)
remainingMass = self.simResult.getPropellantMass() - currentMass
massUnit = self.preferences.getUnit('kg')
self.ui.labelMassProgress.setText(motorlib.units.format(remainingMass, 'kg', massUnit))
self.ui.labelMassRemaining.setText(motorlib.units.format(currentMass, 'kg', massUnit))
self.ui.labelMassProgress.setText(motorlib.units.convFormat(remainingMass, 'kg', massUnit))
self.ui.labelMassRemaining.setText(motorlib.units.convFormat(currentMass, 'kg', massUnit))

currentISP = self.simResult.getISP(index)
self.ui.labelISPProgress.setText(str(round(currentISP, 3)) + ' s')
Expand Down

0 comments on commit ca6691e

Please sign in to comment.