def parse(self): """ Parse the leader file to create a header object """ try: fp = open(self.file, 'rb') except IOError as errs: errno, strerr = errs print("IOError: %s" % strerr) return # Leader record self.leaderFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix, 'risat/leader_file.xml'), dataFile=fp) self.leaderFDR.parse() fp.seek(self.leaderFDR.getEndOfRecordPosition()) # pprint.pprint(self.leaderFDR.metadata) # Scene Header self.sceneHeaderRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'risat/scene_record.xml'), dataFile=fp) self.sceneHeaderRecord.parse() fp.seek(self.sceneHeaderRecord.getEndOfRecordPosition()) pprint.pprint(self.sceneHeaderRecord.metadata) # Platform Position self.platformPositionRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'risat/platform_position_record.xml'), dataFile=fp) self.platformPositionRecord.parse() fp.seek(self.platformPositionRecord.getEndOfRecordPosition()) fp.close()
def parse(self): """ Parse the leader file to create a header object """ try: fp = open(self.file,'rb') except IOError as errs: errno,strerr = errs print("IOError: %s" % strerr) return # Leader record self.leaderFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'alos_slc/leader_file.xml'),dataFile=fp) self.leaderFDR.parse() fp.seek(self.leaderFDR.getEndOfRecordPosition()) # Scene Header self.sceneHeaderRecord = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'alos_slc/scene_record.xml'),dataFile=fp) self.sceneHeaderRecord.parse() fp.seek(self.sceneHeaderRecord.getEndOfRecordPosition()) # Platform Position self.platformPositionRecord = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'alos_slc/platform_position_record.xml'),dataFile=fp) self.platformPositionRecord.parse() fp.seek(self.platformPositionRecord.getEndOfRecordPosition()) # Spacecraft Attitude # if (self.leaderFDR.metadata['Number of attitude data records'] == 1): # self.platformAttitudeRecord = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'alos2_slc/attitude_record.xml'),dataFile=fp) # self.platformAttitudeRecord.parse() # fp.seek(self.platformAttitudeRecord.getEndOfRecordPosition()) # Radiometric Record fp.seek(8192, 1) self.radiometricRecord = CEOS.CEOSDB(xml=os.path.join(xmlPrefix, 'alos_slc/radiometric_record.xml'), dataFile=fp) self.radiometricRecord.parse() fp.seek(self.radiometricRecord.getEndOfRecordPosition()) # Data Quality Summary Record self.dataQualitySummaryRecord = CEOS.CEOSDB(xml=os.path.join(xmlPrefix, 'alos_slc/data_quality_summary_record.xml'), dataFile=fp) self.dataQualitySummaryRecord.parse() fp.seek(self.dataQualitySummaryRecord.getEndOfRecordPosition()) # 1 File descriptor 720 # 2 Data set summary 4096 # 3 Map projection data 1620 # 4 Platform position data 4680 # 5 Attitude data 8192 # 6 Radiometric data 9860 # 7 Data quality summary 1620 # 8 Calibration data 13212 # 9 Facility related Variable fp.close()
def readLeader(self): ''' read meta data from leader ''' try: fp = open(self.leaderFile, 'rb') except IOError as errs: errno, strerr = errs print("IOError: %s" % strerr) return # Leader record leaderFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix, 'alos2_slc/leader_file.xml'), dataFile=fp) leaderFDR.parse() fp.seek(leaderFDR.getEndOfRecordPosition()) # Scene Header sceneHeaderRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'alos2_slc/scene_record.xml'), dataFile=fp) sceneHeaderRecord.parse() fp.seek(sceneHeaderRecord.getEndOfRecordPosition()) # Platform Position platformPositionRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'alos2_slc/platform_position_record.xml'), dataFile=fp) platformPositionRecord.parse() fp.seek(platformPositionRecord.getEndOfRecordPosition()) #####Skip attitude information fp.seek(16384, 1) #####Skip radiometric information fp.seek(9860, 1) ####Skip the data quality information fp.seek(1620, 1) ####Skip facility 1-4 fp.seek(325000 + 511000 + 3072 + 728000, 1) ####Read facility 5 facilityRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'alos2_slc/facility_record.xml'), dataFile=fp) facilityRecord.parse() ###close file fp.close() return (leaderFDR, sceneHeaderRecord, platformPositionRecord, facilityRecord)
def read_param_for_checking_overlap(leader_file, image_file): import os import isce from isceobj.Sensor import xmlPrefix import isceobj.Sensor.CEOS as CEOS #read from leader file fsampConst = { 104: 1.047915957140240E+08, 52: 5.239579785701190E+07, 34: 3.493053190467460E+07, 17: 1.746526595233730E+07 } fp = open(leader_file, 'rb') leaderFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix, 'alos2_slc/leader_file.xml'), dataFile=fp) leaderFDR.parse() fp.seek(leaderFDR.getEndOfRecordPosition()) sceneHeaderRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'alos2_slc/scene_record.xml'), dataFile=fp) sceneHeaderRecord.parse() fp.seek(sceneHeaderRecord.getEndOfRecordPosition()) fsamplookup = int(sceneHeaderRecord.metadata['Range sampling rate in MHz']) rangeSamplingRate = fsampConst[fsamplookup] fp.close() #print('{}'.format(rangeSamplingRate)) #read from image file fp = open(image_file, 'rb') imageFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix, 'alos2_slc/image_file.xml'), dataFile=fp) imageFDR.parse() fp.seek(imageFDR.getEndOfRecordPosition()) imageData = CEOS.CEOSDB(xml=os.path.join(xmlPrefix, 'alos2_slc/image_record.xml'), dataFile=fp) imageData.parseFast() width = imageFDR.metadata['Number of pixels per line per SAR channel'] near_range = imageData.metadata['Slant range to 1st data sample'] fp.close() #print('{}'.format(width)) #print('{}'.format(near_range)) return [rangeSamplingRate, width, near_range]
def parse(self): """ Parse the leader file to create a header object """ try: fp = open(self.file, 'rb') except IOError as errs: errno, strerr = errs print("IOError: %s" % strerr) return # Leader record self.leaderFDR = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'alos2_slc/leader_file.xml'), dataFile=fp) self.leaderFDR.parse() fp.seek(self.leaderFDR.getEndOfRecordPosition()) # Scene Header self.sceneHeaderRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'alos2_slc/scene_record.xml'), dataFile=fp) self.sceneHeaderRecord.parse() fp.seek(self.sceneHeaderRecord.getEndOfRecordPosition()) # Platform Position self.platformPositionRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'alos2_slc/platform_position_record.xml'), dataFile=fp) self.platformPositionRecord.parse() fp.seek(self.platformPositionRecord.getEndOfRecordPosition()) #####Skip attitude information fp.seek(16384, 1) #####Skip radiometric information fp.seek(9860, 1) ####Skip the data quality information fp.seek(1620, 1) ####Skip facility 1-4 fp.seek(325000 + 511000 + 3072 + 728000, 1) ####Read facility 5 self.facilityRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'alos2_slc/facility_record.xml'), dataFile=fp) self.facilityRecord.parse() fp.close()
def extractImage(self, output=None): """ Extract I and Q channels from the image file """ if self.imageFDR is None: self.parse() try: fp = open(self.file, 'rb') except IOError as strerr: self.logger.error(" IOError: %s" % strerr) return fp.seek(self.imageFDR.getEndOfRecordPosition(), os.SEEK_SET) # Extract the I and Q channels imageData = CEOS.CEOSDB(xml=self.image_record, dataFile=fp) dataLen = self.imageFDR.metadata['Number of pixels per line per SAR channel'] prf = self.parent.leaderFile.sceneHeaderRecord.metadata['Pulse Repetition Frequency in mHz']*1.0e-3 for line in range(self.length): if ((line % 1000) == 0): self.logger.debug("Extracting line %s" % line) a = fp.tell() imageData.parseFast() msecs = imageData.metadata['Sensor acquisition milliseconds of day'] if line==0: yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata['Sensor acquisition milliseconds of day'] self.sensingStart = datetime.datetime(yr,1,1) + datetime.timedelta(days=(dys-1)) + datetime.timedelta(seconds = msecs*1e-3) self.nearRange = imageData.metadata['Slant range to 1st data sample'] if line == (self.length-1): yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata['Sensor acquisition milliseconds of day'] IQLine = np.fromfile(fp, dtype='>f', count=2*dataLen) self.writeRawData(output, IQLine) self.width = dataLen self.prf = prf self.sensingStop = self.sensingStart + datetime.timedelta(seconds=(self.length-1)/self.prf) transmitted_polarization_bool = imageData.metadata['Transmitted polarization'] received_polarization_bool = imageData.metadata['Received polarization'] transmitted_polarization = 'V' if transmitted_polarization_bool else 'H' received_polarization = 'V' if received_polarization_bool else 'H' self.current_polarization = transmitted_polarization + received_polarization
def parse(self): try: fp = open(self.file,'r') except IOError as errs: errno,strerr = errs print("IOError: %s" % strerr) return self.imageFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'jers/image_file.xml'), dataFile=fp) self.imageFDR.parse() fp.seek(self.imageFDR.getEndOfRecordPosition()) fp.close()
def parse(self): try: fp = open(self.file,'rb') except IOError as errs: errno,strerr = errs print("IOError: %s" % strerr) return volumeFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'alos_slc/volume_descriptor.xml'),dataFile=fp) volumeFDR.parse() fp.seek(volumeFDR.getEndOfRecordPosition()) fp.close()
def parse(self): """ Parse the leader file to create a header object """ try: fp = open(self.file, 'rb') except IOError as errs: errno, strerr = errs print("IOError: %s" % strerr) return # Leader record self.leaderFDR = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'risat_slc/leader_file.xml'), dataFile=fp) self.leaderFDR.parse() fp.seek(self.leaderFDR.getEndOfRecordPosition()) # Scene Header self.sceneHeaderRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'risat_slc/scene_record.xml'), dataFile=fp) self.sceneHeaderRecord.parse() fp.seek(self.sceneHeaderRecord.getEndOfRecordPosition()) #Data quality summary qualityRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'risat_slc/data_quality_summary_record.xml'), dataFile=fp) qualityRecord.parse() fp.seek(qualityRecord.getEndOfRecordPosition()) #Data histogram records for ind in range( self.leaderFDR.metadata['Number of data histograms records']): histRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'risat_slc/data_histogram_record.xml'), dataFile=fp) histRecord.parse() fp.seek(histRecord.getEndOfRecordPosition()) self.processingRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'risat_slc/detailed_processing_record.xml'), dataFile=fp) self.processingRecord.parse() fp.seek(self.processingRecord.getEndOfRecordPosition()) # Platform Position self.platformPositionRecord = CEOS.CEOSDB(xml=os.path.join( xmlPrefix, 'risat_slc/platform_position_record.xml'), dataFile=fp) self.platformPositionRecord.parse() fp.seek(self.platformPositionRecord.getEndOfRecordPosition()) fp.close()
def parse(self): try: fp = open(self.file,'r') except IOError as errs: errno,strerr = errs print("IOError: %s" % strerr) return volumeFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'jers/volume_descriptor.xml'),dataFile=fp) volumeFDR.parse() fp.seek(volumeFDR.getEndOfRecordPosition()) fp.close() import pprint pp = pprint.PrettyPrinter() pp.pprint(volumeFDR.metadata)
def extractImage(self, output=None, dtype='short'): """ Extract I and Q channels from the image file """ if self.imageFDR is None: self.parse() try: fp = open(self.file, 'rb') except IOError as strerr: self.logger.error(" IOError: %s" % strerr) return fp.seek(self.imageFDR.getEndOfRecordPosition(), os.SEEK_SET) prf = self.parent.leaderFile.sceneHeaderRecord.metadata[ 'Pulse Repetition Frequency'] # Extract the I and Q channels imageData = CEOS.CEOSDB(xml=self.image_record, dataFile=fp) dataLen = self.imageFDR.metadata[ 'Number of pixels per line per SAR channel'] for line in range(self.length): if ((line % 1000) == 0): self.logger.debug("Extracting line %s" % line) imageData.parseFast() if line == 0: yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata[ 'Sensor acquisition milliseconds of day'] + imageData.metadata[ 'Acquisition time bias in ms'] self.sensingStart = datetime.datetime( yr, 1, 1) + datetime.timedelta(days=( dys - 1)) + datetime.timedelta(seconds=msecs * 1e-3) self.nearRange = imageData.metadata['Slant range to 1st pixel'] self.farRange = imageData.metadata['Slant range to last pixel'] self.dopplerCoeff = [ imageData.metadata['First pixel Doppler centroid'], imageData.metadata['Mid-pixel Doppler centroid'], imageData.metadata['Last pixel Doppler centroid'] ] self.prf = imageData.metadata['PRF'] self.polarization = ( imageData.metadata['Transmitted polarization'], imageData.metadata['Received polarization']) if line == (self.length - 1): yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata[ 'Sensor acquisition milliseconds of day'] + imageData.metadata[ 'Acquisition time bias in ms'] self.sensingStop = datetime.datetime( yr, 1, 1) + datetime.timedelta(days=( dys - 1)) + datetime.timedelta(seconds=msecs * 1e-3) if dtype == 'short': IQLine = np.fromfile(fp, dtype='>i2', count=2 * dataLen) else: IQLine = np.fromfile(fp, dtype='>i4', count=2 * dataLen) self.writeRawData(output, IQLine) self.width = dataLen
def extractImage(self, output=None): """ Extract I and Q channels from the image file """ if self.imageFDR is None: self.parse() try: fp = open(self.file, 'rb') except IOError as strerr: self.logger.error(" IOError: %s" % strerr) return fp.seek(self.imageFDR.getEndOfRecordPosition(), os.SEEK_SET) # Extract the I and Q channels imageData = CEOS.CEOSDB(xml=self.image_record, dataFile=fp) dataLen = self.imageFDR.metadata[ 'Number of pixels per line per SAR channel'] delta = 0.0 prf = self.parent.leaderFile.sceneHeaderRecord.metadata[ 'Pulse Repetition Frequency in mHz'] * 1.0e-3 # print('LEADERFILE PRF: ', prf) for line in range(self.length): if ((line % 1000) == 0): self.logger.debug("Extracting line %s" % line) # pprint.pprint(imageData.metadata) imageData.parseFast() usecs = imageData.metadata[ 'Sensor acquisition micro-seconds of day'] if line == 0: yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata[ 'Sensor acquisition milliseconds of day'] self.sensingStart = datetime.datetime( yr, 1, 1) + datetime.timedelta(days=( dys - 1)) + datetime.timedelta(seconds=usecs * 1e-6) self.nearRange = imageData.metadata[ 'Slant range to 1st data sample'] prf1 = imageData.metadata['PRF'] * 1.0e-3 if line == (self.length - 1): yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata[ 'Sensor acquisition milliseconds of day'] # self.sensingStop = datetime.datetime(yr,1,1) + datetime.timedelta(days=(dys-1)) + datetime.timedelta(seconds=usecs*1e-6) if line > 0: delta += (usecs - prevline) prevline = usecs IQLine = np.fromfile(fp, dtype='>f', count=2 * dataLen) self.writeRawData(output, IQLine) self.width = dataLen prf2 = (self.length - 1) / (delta * 1.0e-6) # print('TIME TAG PRF: ', prf2) # print('LINE TAG PRF: ', prf1) # print('Using Leaderfile PRF') # self.prf = prf #choose PRF according to operation mode. Cunren Liang, 2015 operationMode = "{}".format( self.parent.leaderFile.sceneHeaderRecord. metadata['Sensor ID and mode of operation for this channel']) operationMode = operationMode[10:12] if operationMode == '08' or operationMode == '09': # Operation mode # '00': Spotlight mode # '01': Ultra-fine # '02': High-sensitive # '03': Fine # '08': ScanSAR nominal mode # '09': ScanSAR wide mode # '18': Full (Quad.) pol./High-sensitive # '19': Full (Quad.) pol./Fine print('ScanSAR nominal mode, using PRF from the line header') self.prf = prf1 else: self.prf = prf if operationMode == '08': #adding burst information here. Cunren, 14-DEC-2015 sceneCenterIncidenceAngle = self.parent.leaderFile.sceneHeaderRecord.metadata[ 'Incidence angle at scene centre'] sarChannelId = imageData.metadata['SAR channel indicator'] scanId = imageData.metadata['Scan ID'] #Scan ID starts with 1 #if (sceneCenterIncidenceAngle > 39.032 - 5.0 and sceneCenterIncidenceAngle < 39.032 + 5.0) and (sarChannelId == 2): if 1: #burst parameters, currently only for the second, dual polarization, ScanSAR nominal mode #that is the second WBD mode. #p.25 and p.115 of ALOS-2/PALSAR-2 Level 1.1/1.5/2.1/3.1 CEOS SAR Product Format Description #for the definations of wide swath mode nbraw = [358, 470, 358, 355, 487] ncraw = [2086.26, 2597.80, 1886.18, 1779.60, 2211.17] self.parent.frame.nbraw = nbraw[scanId - 1] self.parent.frame.ncraw = ncraw[scanId - 1] #this is the prf fraction (total azimuth bandwith) used in extracting burst. #here the total bandwith is 0.93 * prfs[3] for all subswaths, which is the following values: #[0.7933, 0.6371, 0.8774, 0.9300, 0.7485] prfs = [2661.847, 3314.512, 2406.568, 2270.575, 2821.225] self.parent.frame.prffrac = 0.93 * prfs[3] / prfs[scanId - 1] self.sensingStop = self.sensingStart + datetime.timedelta( seconds=(self.length - 1) / self.prf)
def extractImage(self, output=None): """ Extract I and Q channels from the image file """ if self.imageFDR is None: self.parse() try: fp = open(self.file, 'rb') except IOError as strerr: self.logger.error(" IOError: %s" % strerr) return fp.seek(self.imageFDR.getEndOfRecordPosition(), os.SEEK_SET) # pprint.pprint(self.imageFDR.metadata) prf = self.parent.leaderFile.sceneHeaderRecord.metadata[ 'Pulse Repetition Frequency'] # Extract the I and Q channels imageData = CEOS.CEOSDB(xml=self.image_record, dataFile=fp) self.length = self.length - 1 for line in range(self.length): if ((line % 1000) == 0): self.logger.debug("Extracting line %s" % line) imageData.parseFast() if line == 0: # pprint.pprint(imageData.metadata) dataLen = imageData.metadata['Actual count of data pixels'] yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata[ 'Sensor acquisition milliseconds of day'] + imageData.metadata[ 'Acquisition time bias in ms'] self.sensingStart = datetime.datetime( yr, 1, 1) + datetime.timedelta(days=( dys - 1)) + datetime.timedelta(seconds=msecs * 1e-3) self.nearRange = imageData.metadata['Slant range to 1st pixel'] self.prf = imageData.metadata['PRF'] self.roll = imageData.metadata[ 'Platform roll in micro degs'] * 1.0e-6 if line == (self.length - 1): yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata[ 'Sensor acquisition milliseconds of day'] + imageData.metadata[ 'Acquisition time bias in ms'] self.sensingStop = datetime.datetime( yr, 1, 1) + datetime.timedelta(days=( dys - 1)) + datetime.timedelta(seconds=msecs * 1e-3) IQLine = np.fromfile(fp, dtype='>i1', count=2 * dataLen) trailer = np.fromfile(fp, dtype='>i1', count=2) self.writeRawData(output, IQLine) ###Read the replica and write it to file imageData.parseFast() chirpLength = imageData.metadata['Actual count of data pixels'] ###Rewind to skip missing aux fp.seek(-192, os.SEEK_CUR) IQLine = np.fromfile(fp, dtype='>i1', count=2 * chirpLength) IQLine.astype(np.float32).tofile('replica.bin') # pprint.pprint(imageData.metadata) self.chirpLength = imageData.metadata['Pulse length in ns'] * 1.0e-9 self.width = dataLen
def extractImage(self, output=None): """ Extract I and Q channels from the image file """ if self.imageFDR is None: self.parse() try: fp = open(self.file, 'rb') except IOError as strerr: self.logger.error(" IOError: %s" % strerr) return fp.seek(self.imageFDR.getEndOfRecordPosition(), os.SEEK_SET) auxLength = self.parent.auxLength prf = self.parent.leaderFile.sceneHeaderRecord.metadata[ 'Pulse Repetition Frequency'] # Extract the I and Q channels imageData = CEOS.CEOSDB(xml=self.image_record, dataFile=fp) firstRecTime = None nominalPRF = None nominalPulseLength = None nominalRangeSamplingRate = None nominalChirpSlope = None nominalStartingRange = None startUTC = None lineCount = 0 lineWidth = 0 for line in range(self.length): if ((line % 1000) == 0): self.logger.debug("Extracting line %s" % line) imageData.parseFast() auxData = self.extractAUXinformation(fp) # pprint.pprint(imageData.metadata) #####Check length of current record #######12 CEOS + 180 prefix + 50 dataLen = imageData.recordLength - self.imageFDR.metadata[ 'Number of bytes of prefix data per record'] - auxLength - 12 recTime = auxData['Record Time'] if firstRecTime is None: firstRecTime = recTime nominalPRF = auxData['PRF'] nominalPulseLength = auxData['Pulse length'] nominalChirpSlope = auxData['Chirp slope'] nominalRangeSamplingRate = auxData['fsamp'] nominalStartingRange = auxData['Starting Range'] replicaLength = auxData['Replica length'] startUTC = datetime.datetime( imageData.metadata['Sensor acquisition year'], 1, 1) + datetime.timedelta( imageData.metadata['Sensor acquisition day of year'] - 1) + datetime.timedelta(seconds=auxData['Record Time']) prevRecTime = recTime # pprint.pprint(imageData.metadata) if (auxData['hasReplica']): lineWidth = dataLen - replicaLength else: lineWidth = dataLen # pprint.pprint(auxData) IQLine = np.fromfile(fp, dtype='B', count=dataLen) if (recTime > (prevRecTime + 0.001)): self.logger.debug('Time gap of %f sec at RecNum %d' % (recTime - prevRecTime, imageData.metadata['Record Number'])) if (auxData['hasReplica']): # self.logger.debug("Removing replica from Line %s" % line) IQLine[0:dataLen - replicaLength] = IQLine[replicaLength:dataLen] IQLine[dataLen - replicaLength:] = 16 dataLen = dataLen - replicaLength # print('Line: ', line, dataLen, lineWidth, auxData['Replica length']) if dataLen >= lineWidth: IQout = IQLine else: IQout = 16 * np.ones(lineWidth, dtype='b') IQout[:dataLen] = IQLine lineGap = int(0.5 + (recTime - prevRecTime) * nominalPRF) if ((lineGap == 1) or (line == 0)): self.writeRawData(output, IQout[:lineWidth]) lineCount += 1 prevRecTime = recTime elif ((lineGap > 1) and (lineGap < self.maxLineGap)): for kk in range(lineGap): self.writeRawData(output, IQout[:lineWidth]) lineCount += 1 prevRecTime = recTime + (lineGap - 1) * 8.0e-4 elif (lineGap >= self.maxLineGap): raise Exception('Line Gap too big to be filled') self.prf = nominalPRF self.chirpSlope = nominalChirpSlope self.rangeSamplingRate = nominalRangeSamplingRate self.pulseLength = nominalPulseLength self.startingRange = nominalStartingRange self.sensingStart = startUTC self.length = lineCount self.width = lineWidth
def readImage(self): ''' read image and get parameters ''' try: fp = open(self.imageFile,'rb') except IOError as errs: errno,strerr = errs print("IOError: %s" % strerr) return #read meta data imageFDR = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'alos2_slc/image_file.xml'), dataFile=fp) imageFDR.parse() fp.seek(imageFDR.getEndOfRecordPosition()) #record length: header (544 bytes) + SAR data (width*8 bytes) recordlength = imageFDR.metadata['SAR DATA record length'] width = imageFDR.metadata['Number of pixels per line per SAR channel'] length = imageFDR.metadata['Number of SAR DATA records'] #line header imageData = CEOS.CEOSDB(xml=os.path.join(xmlPrefix,'alos2_slc/image_record.xml'), dataFile=fp) imageData.parseFast() #creat vrt and xml files for sar data image = isceobj.createSlcImage() image.setFilename(self.outputFile) image.setWidth(width) image.setLength(length) image.renderHdr() #sar data fileHeaderBytes = 720 lineHeaderBytes = 544 if self.useVirtualFile: #this overwrites the previous vrt with open(self.outputFile+'.vrt', 'w') as fid: fid.write('''<VRTDataset rasterXSize="{0}" rasterYSize="{1}"> <VRTRasterBand band="1" dataType="CFloat32" subClass="VRTRawRasterBand"> <SourceFilename relativeToVRT="0">{2}</SourceFilename> <ByteOrder>MSB</ByteOrder> <ImageOffset>{3}</ImageOffset> <PixelOffset>8</PixelOffset> <LineOffset>{4}</LineOffset> </VRTRasterBand> </VRTDataset>'''.format(width, length, self.imageFile, fileHeaderBytes + lineHeaderBytes, width*8 + lineHeaderBytes)) else: #read sar data line by line try: fp2 = open(self.outputFile,'wb') except IOError as errs: errno,strerr = errs print("IOError: %s" % strerr) return fp.seek(-lineHeaderBytes, 1) for line in range(length): if (((line+1)%1000) == 0): print("extracting line %6d of %6d" % (line+1, length), end='\r', flush=True) fp.seek(lineHeaderBytes, 1) IQLine = np.fromfile(fp, dtype='>f', count=2*width) self.writeRawData(fp2, IQLine) #IQLine.tofile(fp2) print("extracting line %6d of %6d" % (length, length)) fp2.close() #close input image file fp.close() return (imageFDR, imageData)
def extractImage(self, output=None, virtual=False): """ Extract I and Q channels from the image file """ if virtual: output = output + '.vrt' else: try: output = open(output, 'wb') except IOError as strerr: raise Exceptin("IOError: {0}".format(strerr)) if self.imageFDR is None: self.parse() ###Open the image file for reading try: fp = open(self.file, 'rb') except IOError as strerr: self.logger.error(" IOError: %s" % strerr) return fp.seek(self.imageFDR.getEndOfRecordPosition(), os.SEEK_SET) offsetAfterImageFDR = fp.tell() dataLen = self.imageFDR.metadata[ 'Number of pixels per line per SAR channel'] self.width = dataLen ##Leaderfile PRF prf = self.parent.leaderFile.sceneHeaderRecord.metadata[ 'Pulse Repetition Frequency in mHz'] * 1.0e-3 #choose PRF according to operation mode. Cunren Liang, 2015 operationMode = "{}".format( self.parent.leaderFile.sceneHeaderRecord. metadata['Sensor ID and mode of operation for this channel']) operationMode = operationMode[10:12] if operationMode not in ['08', '09']: # Operation mode # '00': Spotlight mode # '01': Ultra-fine # '02': High-sensitive # '03': Fine # '08': ScanSAR nominal mode # '09': ScanSAR wide mode # '18': Full (Quad.) pol./High-sensitive # '19': Full (Quad.) pol./Fine print( 'This reader only supports ScanSAR full aperture data parsing.' ) raise Exception('Use stripmap reader for other modes') if operationMode != '08': raise Exception('Only ScanSAR nominal mode is currently supported') # Extract the I and Q channels imageData = CEOS.CEOSDB(xml=self.image_record, dataFile=fp) ###If only a VRT needs to be written for line in range(self.length): if ((line % 1000) == 0): self.logger.debug("Extracting line %s" % line) imageData.parseFast() ###Always read the first line virtual / not if line == 0: offsetAfterFirstImageRecord = fp.tell() yr = imageData.metadata['Sensor acquisition year'] dys = imageData.metadata['Sensor acquisition day of year'] msecs = imageData.metadata[ 'Sensor acquisition milliseconds of day'] usecs = imageData.metadata[ 'Sensor acquisition micro-seconds of day'] self.sensingStart = datetime.datetime( yr, 1, 1) + datetime.timedelta( days=(dys - 1)) + datetime.timedelta( seconds=usecs * 1e-6) self.nearRange = imageData.metadata[ 'Slant range to 1st data sample'] self.prf = imageData.metadata['PRF'] * 1.0e-3 sceneCenterIncidenceAngle = self.parent.leaderFile.sceneHeaderRecord.metadata[ 'Incidence angle at scene centre'] sarChannelId = imageData.metadata['SAR channel indicator'] scanId = imageData.metadata[ 'Scan ID'] #Scan ID starts with 1 ###Exit loop after first line if virtual if virtual: break ###Write line to file if not virtual IQLine = np.fromfile(fp, dtype='>f', count=2 * dataLen) self.writeRawData(output, IQLine) fp.close() ####If virtual file was requested, create VRT here if virtual: ##Close input file with open(output, 'w') as fid: fid.write('''<VRTDataset rasterXSize="{0}" rasterYSize="{1}"> <VRTRasterBand dataType="CFloat32" band="1" subClass="VRTRawRasterBand"> <SourceFilename relativeToVRT="0">{2}</SourceFilename> <ByteOrder>MSB</ByteOrder> <ImageOffset>{3}</ImageOffset> <PixelOffset>8</PixelOffset> <LineOffset>{4}</LineOffset> </VRTRasterBand> </VRTDataset>'''.format( self.width, self.length, os.path.abspath(self.file), offsetAfterFirstImageRecord, dataLen * 8 + offsetAfterFirstImageRecord - offsetAfterImageFDR)) else: ##Close actual file on disk output.close() #burst parameters, currently only for the second, dual polarization, ScanSAR nominal mode #that is the second WBD mode. #p.25 and p.115 of ALOS-2/PALSAR-2 Level 1.1/1.5/2.1/3.1 CEOS SAR Product Format Description #for the definations of wide swath mode nbraw = [358, 470, 358, 355, 487] ncraw = [2086.26, 2597.80, 1886.18, 1779.60, 2211.17] self.parent.frame.nbraw = nbraw[scanId - 1] self.parent.frame.ncraw = ncraw[scanId - 1] #this is the prf fraction (total azimuth bandwith) used in extracting burst. #here the total bandwith is 0.93 * prfs[3] for all subswaths, which is the following values: #[0.7933, 0.6371, 0.8774, 0.9300, 0.7485] prfs = [2661.847, 3314.512, 2406.568, 2270.575, 2821.225] #Only needed for burst extraction. Skipping for now .... #self.parent.frame.prffrac = 0.93 * prfs[3]/prfs[scanId-1] self.sensingStop = self.sensingStart + datetime.timedelta( seconds=(self.length - 1) / self.prf)