/* * Copyright (C) 2010 Brockmann Consult GmbH (info@brockmann-consult.de) * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the Free * Software Foundation; either version 3 of the License, or (at your option) * any later version. * This program is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for * more details. * * You should have received a copy of the GNU General Public License along * with this program; if not, see http://www.gnu.org/licenses/ */ package com.bc.ceres.binio.smos; import com.bc.ceres.binio.*; import org.junit.*; import javax.imageio.stream.*; import java.io.*; import java.nio.*; import static com.bc.ceres.binio.TypeBuilder.*; public class SmosProduct { public static final int[] BT_DATA_COUNTERS = new int[]{2, 4, 3, 6}; public static final CompoundType SNAPSHOT_INFO_TYPE = COMPOUND("Snapshot_Information", MEMBER("Snapshot_Time", SEQUENCE(UINT, 3)), MEMBER("Snapshot_ID", UINT), MEMBER("Snapshot_OBET", SEQUENCE(UBYTE, 8)), MEMBER("Position", SEQUENCE(DOUBLE, 3)), MEMBER("Velocity", SEQUENCE(DOUBLE, 3)), MEMBER("Vector_Source", UBYTE), MEMBER("Q0", DOUBLE), MEMBER("Q1", DOUBLE), MEMBER("Q2", DOUBLE), MEMBER("Q3", DOUBLE), MEMBER("TEC", DOUBLE), MEMBER("Geomag_F", DOUBLE), MEMBER("Geomag_D", DOUBLE), MEMBER("Geomag_I", DOUBLE), MEMBER("Sun_RA", FLOAT), MEMBER("Sun_DEC", FLOAT), MEMBER("Sun_BT", FLOAT), MEMBER("Accuracy", FLOAT), MEMBER("Radiometric_Accuracy", SEQUENCE(FLOAT, 2))); public static final CompoundType F1C_BT_DATA_TYPE = COMPOUND("Bt_Data", MEMBER("Flags", USHORT), MEMBER("BT_Value_Real", FLOAT), MEMBER("BT_Value_Imag", FLOAT), MEMBER("Radiometric_Accuracy_of_Pixel", USHORT), MEMBER("Incidence_Angle", USHORT), MEMBER("Azimuth_Angle", USHORT), MEMBER("Faraday_Rotation_Angle", USHORT), MEMBER("Geometric_Rotation_Angle", USHORT), MEMBER("Snapshot_ID_of_Pixel", UINT), MEMBER("Footprint_Axis1", USHORT), MEMBER("Footprint_Axis2", USHORT)); public static final CompoundType F1C_GRID_POINT_DATA_TYPE = COMPOUND("Grid_Point_Data", MEMBER("Grid_Point_ID", UINT), /*4*/ MEMBER("Grid_Point_Latitude", FLOAT), /*8*/ MEMBER("Grid_Point_Longitude", FLOAT),/*12*/ MEMBER("Grid_Point_Altitude", FLOAT), /*16*/ MEMBER("Grid_Point_Mask", UBYTE), /*17*/ MEMBER("BT_Data_Counter", UBYTE), /*18*/ MEMBER("Bt_Data_List", VAR_SEQUENCE(F1C_BT_DATA_TYPE, "BT_Data_Counter"))); public static final CompoundType MIR_SCLF1C_TYPE = COMPOUND("MIR_SCLF1C", MEMBER("Snapshot_Counter", UINT), MEMBER("Snapshot_List", VAR_SEQUENCE(SNAPSHOT_INFO_TYPE, "Snapshot_Counter")), MEMBER("Grid_Point_Counter", UINT), MEMBER("Grid_Point_List", VAR_SEQUENCE(F1C_GRID_POINT_DATA_TYPE, "Grid_Point_Counter"))); public static final DataFormat MIR_SCLF1C_FORMAT; static { MIR_SCLF1C_FORMAT = new DataFormat(SmosProduct.MIR_SCLF1C_TYPE, ByteOrder.LITTLE_ENDIAN); } public static byte[] createTestProductData(ByteOrder byteOrder) throws IOException { ByteArrayOutputStream baos = new ByteArrayOutputStream(); ImageOutputStream ios = new MemoryCacheImageOutputStream(baos); int size = 4; // uint Snapshot_Counter size += 3 * SNAPSHOT_INFO_TYPE.getSize(); // Snapshot_Info[3] Snapshot_List size += 4; // uint Grid_Point_Counter for (int btDataCount : BT_DATA_COUNTERS) { // Grid_Point_Data[4] Grid_Point_List size += 18; size += btDataCount * F1C_BT_DATA_TYPE.getSize(); // Bt_Data[btDataCount] Bt_Data_List } ios.setByteOrder(byteOrder); ios.writeInt(3); // uint Snapshot_Counter for (int i = 0; i < 3; i++) { int[] snapshotTime = getSnapshotTime(i); ios.writeInt(snapshotTime[0]); // uint Snapshot_Info[i].Snapshot_Time[0] ios.writeInt(snapshotTime[1]); // uint Snapshot_Info[i].Snapshot_Time[1] ios.writeInt(snapshotTime[2]); // uint Snapshot_Info[i].Snapshot_Time[2] ios.writeInt(getSnapshotId(i)); // uint Snapshot_Info[i].Snapshot_ID ios.skipBytes(SNAPSHOT_INFO_TYPE.getSize() - (3 * 4 + 4)); } ios.writeInt(BT_DATA_COUNTERS.length); // uint Grid_Point_Counter for (int i = 0; i < BT_DATA_COUNTERS.length; i++) { int btDataCounter = BT_DATA_COUNTERS[i]; ios.writeInt(getGridPointId(i)); // uint Grid_Point_Data[i].Grid_Point_ID ios.writeFloat(getGridPointLatitude(i)); // float Grid_Point_Data[i].Grid_Point_Latitude ios.writeFloat(getGridPointLongitude(i)); // float Grid_Point_Data[i].Grid_Point_Longitude ios.skipBytes(18 - (4 + 2 * 4 + 1)); ios.writeByte(btDataCounter); // ubyte Grid_Point_Data[i].BT_Data_Counter for (int j = 0; j < btDataCounter; j++) { ios.writeShort(getBtDataFlags(j)); // ushort Bt_Data[j].Flags ios.writeFloat(getBtValueReal(j)); // float Bt_Data[j].BT_Value_Real ios.writeFloat(getBtValueImag(j)); // float Bt_Data[j].BT_Value_Imag ios.skipBytes(F1C_BT_DATA_TYPE.getSize() - (2 + 2 * 4 + 2)); ios.writeShort(getFootprintAxis2(j)); // ushort Bt_Data[j].Footprint_Axis2 } } ios.close(); final byte[] bytes = baos.toByteArray(); Assert.assertEquals(size, bytes.length); return bytes; } public static int[] getSnapshotTime(int i) { return new int[]{2540, i, 10000 + i}; } public static int getSnapshotId(int i) { return 40000 + i; } public static int getGridPointId(int i) { return 968000 + i; } public static float getGridPointLatitude(int i) { return 36.0F + i * 0.1F; } public static float getGridPointLongitude(int i) { return 13.0F + i * 0.1F; } public static int getBtDataFlags(int j) { return 1 + j * 2; } public static float getBtValueReal(int j) { return 0.5F * (j % 2); } public static float getBtValueImag(int j) { return 0.5F * ((1 - j) % 2); } public static int getFootprintAxis2(int j) { return j % 3; } }