Source code for out3Plot.outCom1DFA

import numpy as np
import pathlib
import matplotlib.pyplot as plt
import logging
from matplotlib.animation import FuncAnimation, PillowWriter

# Local imports
from avaframe.in3Utils import cfgUtils
import avaframe.com1DFA.DFAtools as DFAtls
import avaframe.in3Utils.geoTrans as geoTrans
import avaframe.out3Plot.plotUtils as pU
import avaframe.out3Plot.outQuickPlot as oQ
import avaframe.out3Plot.outAIMEC as oA
import avaframe.in3Utils.fileHandlerUtils as fU

cfgMain = cfgUtils.getGeneralConfig()
cfgFlags = cfgMain['FLAGS']
# create local logger
log = logging.getLogger(__name__)


[docs]def plotTrackParticle(outDirData, particlesList, trackedPartProp, cfg, dem, cuSimName): """ Plot time series of tracked particles Parameters ---------- outDirData: str path to output directory particlesList: list list or particles dictionaries trackedPartProp: dict dictionary with time series of the wanted properties for tracked particles cfg : dict configuration read from ini file dem: dict dem dictionary with normal information cuSimName: str name of current simulation """ cfgTrackPart = cfg['TRACKPARTICLES'] radius = cfgTrackPart.getfloat('radius') centerList = cfgTrackPart['centerTrackPartPoint'] centerList = centerList.split('|') center = {'x': np.array([float(centerList[0])]), 'y': np.array([float(centerList[1])])} center, _ = geoTrans.projectOnRaster(dem, center, interp='bilinear') time = trackedPartProp['t'] # do some ploting fig = plt.figure(figsize=(pU.figW*3, pU.figH*2)) fig.suptitle('Tracked particles') ax1 = plt.subplot(221) ax1 = addDem2Plot(ax1, dem, what='slope') circle1 = plt.Circle((center['x'], center['y']), radius, color='r') ax1.plot(trackedPartProp['x'], trackedPartProp['y']) ax1.add_patch(circle1) ax1.set_xlabel('x [m]') ax1.set_ylabel('y [m]') ax1.set_title('Trajectory') ax2 = plt.subplot(222) ax2.plot(time, trackedPartProp['m']) ax2.set_xlabel('t [s]') ax2.set_ylabel('m [kg]') ax2.set_title('Mass') ax3 = plt.subplot(223) velocity = DFAtls.norm(trackedPartProp['ux'], trackedPartProp['uy'], trackedPartProp['uz']) ax3.plot(time, velocity) ax3.set_xlabel('t [s]') ax3.set_ylabel('v [m/s]') ax3.set_title('Velocity') ax4 = plt.subplot(224) ax4.plot(time, trackedPartProp['h']) ax4.set_xlabel('t [s]') ax4.set_ylabel('h [m]') ax4.set_title('Flow thickness') pathDict = {} pathDict['pathResult'] = outDirData outFileName = 'trackedParticles_%s' % cuSimName pU.saveAndOrPlot(pathDict, outFileName, fig) if cfgFlags.getboolean('showPlot'): fig2 = plt.figure() ax1 = plt.subplot(111) for count in range(len(particlesList)): particles = particlesList[count] ax1 = updateTrackPart(particles, ax1, dem) ax1 = addDem2Plot(ax1, dem, what='slope') plt.pause(0.1) plt.show()
# ani = FuncAnimation(fig2, update, round(len(Particles)), # fargs=(Particles, xllc, yllc, ax1, XX, YY, dem)) # # plt.show() # # writer = PillowWriter(fps=4) # # ani.save("MalSecRel.gif", writer=writer) # ani.save("testTrackAlr1.gif", writer=writer)
[docs]def plotTrackParticleAcceleration(outDirData, trackedPartProp, cfg, cuSimName): """ Plot time series of tracked particles Parameters ---------- outDirData: str path to output directory trackedPartProp: dict dictionary with time series of the wanted properties for tracked particles cfg : dict configuration read from ini file cuSimName: str name of simulation """ # do some ploting fig = plt.figure(figsize=(pU.figW, pU.figH)) fig.suptitle('Tracked particles acceleration') ax1 = plt.subplot(111) ax1.plot(trackedPartProp['t'], trackedPartProp['uAcc']) ax1.set_xlabel('time step [s]') ax1.set_ylabel('acceleration [ms-2]') pathDict = {} pathDict['pathResult'] = outDirData outFileName = 'trackedParticles_acceleration_ %s' % cuSimName pU.saveAndOrPlot(pathDict, outFileName, fig)
[docs]def plotAllPartAcc(outDirData, particlesList, cfg, Tsave, cuSimName): """ Plot time series of tracked particles Parameters ---------- outDirData: str path to output directory particlesList: list list with dictionary of all particles time steps particles cfg : dict configuration read from ini file Tsave: list list of saving time step info cuSimName: str name of current sim """ # initialize fig fig = plt.figure(figsize=(pU.figW, pU.figH)) fig.suptitle('Tracked particles acceleration') ax1 = plt.subplot(111) uAcc = np.zeros((len(particlesList), particlesList[0]['nPart'])) timeStep = np.asarray([p['t'] for p in particlesList]) for idx in particlesList[0]['ID']: uAcc[:, idx] = np.asarray([p['uAcc'][idx] for p in particlesList]) ax1.plot(Tsave, uAcc[:, idx]) ax1.set_xlabel('time step [s]') ax1.set_ylabel('acceleration [ms-2]') pathDict = {} pathDict['pathResult'] = outDirData outFileName = 'allparticles_acceleration_%s' % cuSimName pU.saveAndOrPlot(pathDict, outFileName, fig)
[docs]def updateTrackPart(particles, ax, dem): """Update axes with particles (tracked particles are highlighted in red) """ header = dem['header'] xllc = header['xllcenter'] yllc = header['yllcenter'] X = particles['x'] + xllc Y = particles['y'] + yllc ax.clear() ax.set_title('t=%.2f s' % particles['t']) variable = particles['trackedParticles'] # set range and steps of colormap cc = np.where(variable == 1, True, False) ax.scatter(X, Y, c='b', cmap=None, marker='.') ax.scatter(X[cc], Y[cc], c='r', cmap=None, marker='.', s=5) return ax
[docs]def addParticles2Plot(particles, ax, dem, whatS='m', whatC='h', colBarResType=''): """Update axes with particles Parameters ---------- particles: dict particles dictionary ax: matplotlib ax object dem: dict dem dictionary with normal information whatS: str which particle property should be used for the markersize whatC: str which particle property should be used for the marker color """ header = dem['header'] xllc = header['xllcenter'] yllc = header['yllcenter'] X = particles['x'] + xllc Y = particles['y'] + yllc cmap = pU.cmapT if colBarResType != '': unit = pU.cfgPlotUtils['unit%s' % colBarResType] else: unit = '' variableC = particles[whatC] variableS = particles[whatS] minMax = np.nanmax(variableS)-np.nanmin(variableS) if minMax > 0: variableS = ((variableS-np.nanmin(variableS))/(np.nanmax(variableS)-np.nanmin(variableS)) + 1)*pU.ms else: variableS = pU.ms cmap, _, ticks, norm = pU.makeColorMap(cmap, np.amin(variableC), np.amax(variableC), continuous=pU.contCmap) # set range and steps of colormap sc = ax.scatter(X, Y, c=variableC, s=variableS, cmap=cmap, marker='.', zorder=15) cb = pU.addColorBar(sc, ax, ticks, unit) return ax, cb
[docs]def addDem2Plot(ax, dem, what='slope', extent='', origHeader=False): """ Add dem to the background of a plot Parameters ---------- ax: matplotlib ax object dem: dict dem dictionary with normal information what: str what information about the dem will be plotted? slope: use the dem slope (computed from the normals) to color the plot z : use the elevation to color the plot origHeader: bool if True use originalHeader and not header """ if origHeader: header = dem['originalHeader'] else: header = dem['header'] ncols = header['ncols'] nrows = header['nrows'] xllc = header['xllcenter'] yllc = header['yllcenter'] csz = header['cellsize'] xArray = np.linspace(xllc, xllc+(ncols-1)*csz, ncols) yArray = np.linspace(yllc, yllc+(nrows-1)*csz, nrows) cmap = pU.cmapGreys cmap.set_bad(color='white') if what == 'slope': value = dem['Nz'] / DFAtls.norm(dem['Nx'], dem['Ny'], dem['Nz']) elif what == 'z': value = dem['rasterData'] elif what == 'hillshade': ls = pU.LightSource(azdeg=pU.azimuthDegree, altdeg=pU.elevationDegree) value = dem['rasterData'] value = ls.hillshade(value, vert_exag=pU.vertExag, dx=value.shape[1], dy=value.shape[0]) else: value = dem['rasterData'] if extent == '': extent = [xArray.min(), xArray.max(), yArray.min(), yArray.max()] ref0, im = pU.NonUnifIm(ax, xArray, yArray, value, 'x [m]', 'y [m]', # extent=[2400, 2700, YY.min(), YY.max()], extent=extent, cmap=cmap, norm=None, zorder=0) CS = ax.contour(xArray, yArray, dem['rasterData'], levels=pU.hillshadeContLevs, colors='k', linewidths=0.5, zorder=3) # add labels ax.clabel(CS, CS.levels, inline=True, fontsize=8, zorder=3) # add info box with indication of label meaning pU.putInfoBox(ax, '- elevation [m]', location='upperLeft', color='gray', hAlignment='left', alphaF=1.0) return ax
[docs]def plotParticles(particlesList, cfg, dem): """ Plot particles on dem Parameters ---------- particlesList: list list or particles dictionaries cfg : dict configuration read from ini file dem: dict dem dictionary with normal information """ if cfgFlags.getboolean('showPlot'): for count in range(len(particlesList)): fig2 = plt.figure() ax1 = plt.subplot(111) ax1.clear() particles = particlesList[count] ax1.set_title('t=%.2f s' % particles['t']) ax1 = addParticles2Plot(particles, ax1, dem, whatS='h', whatC='m') ax1 = addDem2Plot(ax1, dem, what='slope') plt.show()
[docs]def addResult2Plot(ax, header, rasterData, resType, colorbar=True, contour=False): """ Add raster data to a plot Parameters ---------- ax: matplotlib ax object header: dict raster header dictionary rasterData: 2D numpy array data to plot resType: str what kinf of result is it? ppr, pft... colorbar: bool If true add the colorbar """ xllc = header['xllcenter'] yllc = header['yllcenter'] csz = header['cellsize'] rowsMin, rowsMax, colsMin, colsMax, rasterData = pU.constrainPlotsToData(rasterData, csz, extentOption=False, constrainedData=True) xArray = np.linspace(xllc+colsMin*csz, xllc+colsMax*csz, colsMax-colsMin+1) yArray = np.linspace(yllc+rowsMin*csz, yllc+rowsMax*csz, rowsMax-rowsMin+1) extent = [xArray.min(), xArray.max(), yArray.min(), yArray.max()] unit = pU.cfgPlotUtils['unit%s' % resType] contourLevels = pU.cfgPlotUtils['contourLevels%s' % resType] contourLevels = fU.splitIniValueToArraySteps(contourLevels) cmap, _, ticks, norm = pU.makeColorMap(pU.colorMaps[resType], np.amin(rasterData), np.amax(rasterData), continuous=pU.contCmap) cmap.set_bad(alpha=0) rasterData = np.ma.masked_where(rasterData == 0, rasterData) ref0, im = pU.NonUnifIm(ax, xArray, yArray, rasterData, 'x [m]', 'y [m]', extent=extent, cmap=cmap, norm=norm, zorder=9) if colorbar: cb = pU.addColorBar(im, ax, ticks, unit) else: cb = None if contour: CS = ax.contour(xArray, yArray, rasterData, levels=contourLevels, colors='k') ax.clabel(CS, inline=1, fontsize=8, zorder=10) else: CS = None return ax, extent, cb, CS
[docs]def createContourPlot(reportDictList, avalancheDir, simDF): """ create a contour line plot of all simulations of current run Parameters ----------- reportDictList: list list of com1DFA dictionary with info on contour dicts for each sim avalancheDir: str or pathlib path path to avalanche directory simDF: pandas DataFrame dataframe with one row per simulation performed and its parameter settings Returns ------- reportDictList: list updated reportDictList - deleted contours dict """ modName = 'com1DFA' contourD = {} # fetch coordinates of contour line for each sim in reportDict and create contourD for cont in reportDictList: contourD[list(cont['contours'].keys())[0]] = cont['contours'][list(cont['contours'].keys())[0]] del cont['contours'] # create contours directory in Ouputs to save plot contourPlotDir = pathlib.Path(avalancheDir, 'Outputs', modName, 'contours') fU.makeADir(contourPlotDir) # create pathDict and fetch simName of first sim found pathDict = {'pathResult': contourPlotDir, 'plotScenario': pathlib.Path(avalancheDir).stem, 'avaDir': avalancheDir} simName1 = simDF['simName'].iloc[0] # check if consistent settings throughout all sims if len(np.unique(simDF['contourResType'])) != 1 or len(np.unique(simDF['thresholdValue'])) != 1: log.warning('Contour result type or thresholdValue are not identical for all sims performed - so cannot create contour plot') return reportDictList, False # generate plot oQ.plotContours(contourD, contourD[simName1]['contourResType'], contourD[simName1]['thresholdValue'], pathDict) log.info('Saved contour plot of %d sims to %s' % (len(simDF), contourPlotDir)) log.info('Sim names are: %s' % simDF['simName'].to_list()) return reportDictList, True
[docs]def fetchContCoors(demHeader, flowF, cfgVisu, simName): """ fetch coordinates of contour line Parameters ------------ demHeader: dict dictionary of dem nrows, ncols, cellsize flowF: np.ndarray field data used to compute contour line cfgVisu: configparser object configuration settings for visualisation, here used: contourResType, thresholdValue simName: str simName Rertuns -------- contDictXY: dict dictionary with simName and subDict with x, y coordinates of contour line contourResType and thresholdValue """ # create coordinate grid first xGrid, yGrid, _, _ = geoTrans.makeCoordGridFromHeader(demHeader) # fetch contour line contourDictXYLines = pU.fetchContourCoords(xGrid, yGrid, flowF, cfgVisu.getfloat('thresholdValue')) # setup dict contDictXY = {simName: contourDictXYLines} contDictXY[simName]['contourResType'] = cfgVisu['contourResType'] contDictXY[simName]['thresholdValue'] = cfgVisu.getfloat('thresholdValue') return contDictXY
[docs]def plotReleaseScenarioView(avaDir, releaseLine, dem, titleFig, cuSimName): """ plot release polygon, area with thickness on dem hillshade saved to avaDir/Outputs/com1DFA/reports Parameters ------------ avaDir: str path to ava directory dem: dict dict with dem header and data releaseLine: dict dict with raster of release line and x,y coors titleFig: str title of figure cuSimName: str name of simulation """ ny = releaseLine['rasterData'].shape[0] nx = releaseLine['rasterData'].shape[1] Ly = ny * dem['originalHeader']['cellsize'] Lx = nx * dem['originalHeader']['cellsize'] xL = dem['originalHeader']['xllcenter'] yL = dem['originalHeader']['yllcenter'] originCells = dem['header']['cellsize'] * 0.5 rField = np.ma.masked_where(releaseLine['rasterData'] == 0.0, releaseLine['rasterData']) # choose colormap cmap1, col, ticks, norm = pU.makeColorMap( pU.colorMaps['pft'], np.amin(releaseLine['rasterData']), np.amax(releaseLine['rasterData']), continuous=pU.contCmap) cmap1.set_bad(alpha=0.) extentCells = [xL - originCells, xL + Lx - originCells, yL + Ly - originCells, yL - originCells] extentDem = [xL, xL + Lx, yL + Ly, yL] # create figure fig, ax = plt.subplots() addDem2Plot(ax, dem, what='hillshade', extent=extentDem, origHeader=True) im1 = ax.imshow(rField, extent=extentCells, cmap=cmap1) ax.plot(releaseLine['x'], releaseLine['y'], 'b-', label='release polygon') ax.set_aspect('equal') cax = ax.inset_axes([1.04, 0.0, 0.05, 1.]) pU.addColorBar(im1, ax, ticks, 'm', cax=cax) plt.legend(fontsize=8) plt.title(titleFig) pU.putAvaNameOnPlot(ax, avaDir) # save and or plot plotName = 'releaseScenario_%s' % cuSimName outDir = pathlib.Path(avaDir, 'Outputs', 'com1DFA', 'reports') fU.makeADir(outDir) pU.saveAndOrPlot({"pathResult": outDir}, plotName, fig)