Search in sources :

Example 16 with IFDList

use of loci.formats.tiff.IFDList in project bioformats by openmicroscopy.

the class CellSensReader method initFile.

// -- Internal FormatReader API methods --
/* @see loci.formats.FormatReader#initFile(String) */
@Override
protected void initFile(String id) throws FormatException, IOException {
    super.initFile(id);
    if (!checkSuffix(id, "vsi")) {
        Location current = new Location(id).getAbsoluteFile();
        Location parent = current.getParentFile();
        parent = parent.getParentFile();
        Location grandparent = parent.getParentFile();
        String vsi = parent.getName();
        vsi = vsi.substring(1, vsi.length() - 1) + ".vsi";
        Location vsiFile = new Location(grandparent, vsi);
        if (!vsiFile.exists()) {
            throw new FormatException("Could not find .vsi file.");
        } else {
            id = vsiFile.getAbsolutePath();
        }
    }
    parser = new TiffParser(id);
    ifds = parser.getIFDs();
    RandomAccessInputStream vsi = new RandomAccessInputStream(id);
    vsi.order(parser.getStream().isLittleEndian());
    vsi.seek(8);
    readTags(vsi, false, "");
    vsi.close();
    ArrayList<String> files = new ArrayList<String>();
    Location file = new Location(id).getAbsoluteFile();
    Location dir = file.getParentFile();
    String name = file.getName();
    name = name.substring(0, name.lastIndexOf("."));
    Location pixelsDir = new Location(dir, "_" + name + "_");
    String[] stackDirs = pixelsDir.list(true);
    if (stackDirs != null) {
        Arrays.sort(stackDirs);
        for (String f : stackDirs) {
            Location stackDir = new Location(pixelsDir, f);
            String[] pixelsFiles = stackDir.list(true);
            if (pixelsFiles != null) {
                Arrays.sort(pixelsFiles);
                for (String pixelsFile : pixelsFiles) {
                    if (checkSuffix(pixelsFile, "ets")) {
                        files.add(new Location(stackDir, pixelsFile).getAbsolutePath());
                    }
                }
            }
        }
    }
    files.add(file.getAbsolutePath());
    usedFiles = files.toArray(new String[files.size()]);
    if (expectETS && files.size() == 1) {
        String message = "Missing expected .ets files in " + pixelsDir.getAbsolutePath();
        if (failOnMissingETS()) {
            throw new FormatException(message);
        } else {
            LOGGER.warn(message);
        }
    } else if (!expectETS && files.size() > 1) {
        LOGGER.warn(".ets files present but not expected");
    }
    int seriesCount = files.size();
    core.clear();
    IFDList exifs = parser.getExifIFDs();
    int index = 0;
    for (int s = 0; s < seriesCount; s++) {
        CoreMetadata ms = new CoreMetadata();
        core.add(ms);
        if (s < files.size() - 1) {
            setCoreIndex(index);
            parseETSFile(files.get(s), s);
            ms.littleEndian = compressionType.get(index) == RAW;
            ms.interleaved = ms.rgb;
            for (int q = 1; q < ms.resolutionCount; q++) {
                int res = core.size() - ms.resolutionCount + q;
                core.get(res).littleEndian = ms.littleEndian;
                core.get(res).interleaved = ms.interleaved;
            }
            if (s == 0 && exifs.size() > 0) {
                IFD exif = exifs.get(0);
                int newX = exif.getIFDIntValue(IFD.PIXEL_X_DIMENSION);
                int newY = exif.getIFDIntValue(IFD.PIXEL_Y_DIMENSION);
                if (getSizeX() > newX || getSizeY() > newY) {
                    ms.sizeX = newX;
                    ms.sizeY = newY;
                }
            }
            index += ms.resolutionCount;
            if (s < pyramids.size()) {
                ms.seriesMetadata = pyramids.get(s).originalMetadata;
            }
            setCoreIndex(0);
        } else {
            IFD ifd = ifds.get(s - files.size() + 1);
            PhotoInterp p = ifd.getPhotometricInterpretation();
            int samples = ifd.getSamplesPerPixel();
            ms.rgb = samples > 1 || p == PhotoInterp.RGB;
            ms.sizeX = (int) ifd.getImageWidth();
            ms.sizeY = (int) ifd.getImageLength();
            ms.sizeZ = 1;
            ms.sizeT = 1;
            ms.sizeC = ms.rgb ? samples : 1;
            ms.littleEndian = ifd.isLittleEndian();
            ms.indexed = p == PhotoInterp.RGB_PALETTE && (get8BitLookupTable() != null || get16BitLookupTable() != null);
            ms.imageCount = 1;
            ms.pixelType = ifd.getPixelType();
            ms.interleaved = false;
            ms.falseColor = false;
            ms.thumbnail = s != 0;
            index++;
        }
        ms.metadataComplete = true;
        ms.dimensionOrder = "XYCZT";
    }
    MetadataStore store = makeFilterMetadata();
    MetadataTools.populatePixels(store, this, true);
    String instrument = MetadataTools.createLSID("Instrument", 0);
    store.setInstrumentID(instrument, 0);
    for (int i = 0; i < pyramids.size(); i++) {
        Pyramid pyramid = pyramids.get(i);
        store.setObjectiveID(MetadataTools.createLSID("Objective", 0, i), 0, i);
        store.setObjectiveNominalMagnification(pyramid.magnification, 0, i);
        store.setObjectiveWorkingDistance(FormatTools.createLength(pyramid.workingDistance, UNITS.MICROMETER), 0, i);
        for (int q = 0; q < pyramid.objectiveTypes.size(); q++) {
            if (pyramid.objectiveTypes.get(q) == 1) {
                store.setObjectiveModel(pyramid.objectiveNames.get(q), 0, i);
                break;
            }
        }
        store.setObjectiveLensNA(pyramid.numericalAperture, 0, i);
        store.setDetectorID(MetadataTools.createLSID("Detector", 0, i), 0, i);
        store.setDetectorOffset(pyramid.offset, 0, i);
        store.setDetectorGain(pyramid.gain, 0, i);
        for (int q = 0; q < pyramid.deviceTypes.size(); q++) {
            if (pyramid.deviceTypes.get(q).equals("Camera")) {
                if (q < pyramid.deviceNames.size()) {
                    store.setDetectorModel(pyramid.deviceNames.get(q), 0, i);
                }
                if (q < pyramid.deviceIDs.size()) {
                    store.setDetectorSerialNumber(pyramid.deviceIDs.get(q), 0, i);
                }
                if (q < pyramid.deviceManufacturers.size()) {
                    store.setDetectorManufacturer(pyramid.deviceManufacturers.get(q), 0, i);
                }
                store.setDetectorType(getDetectorType("CCD"), 0, i);
                break;
            }
        }
    }
    int nextPyramid = 0;
    for (int i = 0; i < core.size(); ) {
        setCoreIndex(i);
        Pyramid pyramid = null;
        if (nextPyramid < pyramids.size()) {
            pyramid = pyramids.get(nextPyramid++);
        }
        int ii = coreIndexToSeries(i);
        if (pyramid != null) {
            int nextPlane = 0;
            int effectiveSizeC = core.get(i).rgb ? 1 : core.get(i).sizeC;
            for (int c = 0; c < effectiveSizeC; c++) {
                store.setDetectorSettingsID(MetadataTools.createLSID("Detector", 0, nextPyramid - 1), ii, c);
                store.setDetectorSettingsBinning(getBinning(pyramid.binningX + "x" + pyramid.binningY), ii, c);
                if (c == 0) {
                    store.setDetectorSettingsGain(pyramid.redGain, ii, c);
                    store.setDetectorSettingsOffset(pyramid.redOffset, ii, c);
                } else if (c == 1) {
                    store.setDetectorSettingsGain(pyramid.greenGain, ii, c);
                    store.setDetectorSettingsOffset(pyramid.greenOffset, ii, c);
                } else if (c == 2) {
                    store.setDetectorSettingsGain(pyramid.blueGain, ii, c);
                    store.setDetectorSettingsOffset(pyramid.blueOffset, ii, c);
                }
                if (c < pyramid.channelNames.size()) {
                    store.setChannelName(pyramid.channelNames.get(c), ii, c);
                }
                if (c < pyramid.channelWavelengths.size()) {
                    int wave = pyramid.channelWavelengths.get(c).intValue();
                    if (wave > 0) {
                        store.setChannelEmissionWavelength(FormatTools.getEmissionWavelength((double) wave), ii, c);
                    }
                }
                for (int z = 0; z < core.get(i).sizeZ; z++) {
                    for (int t = 0; t < core.get(i).sizeT; t++) {
                        nextPlane = getIndex(z, c, t);
                        Long exp = pyramid.defaultExposureTime;
                        if (c < pyramid.exposureTimes.size()) {
                            exp = pyramid.exposureTimes.get(c);
                        }
                        if (exp != null) {
                            store.setPlaneExposureTime(FormatTools.createTime(exp / 1000000.0, UNITS.SECOND), ii, nextPlane);
                        }
                        store.setPlanePositionX(FormatTools.createLength(pyramid.originX, UNITS.MICROMETER), ii, nextPlane);
                        store.setPlanePositionY(FormatTools.createLength(pyramid.originY, UNITS.MICROMETER), ii, nextPlane);
                    }
                }
            }
        }
        store.setImageInstrumentRef(instrument, ii);
        if (pyramid != null) {
            String imageName = pyramid.name;
            boolean duplicate = false;
            for (int q = 0; q < pyramids.size(); q++) {
                if (q != (nextPyramid - 1) && imageName.equals(pyramids.get(q).name)) {
                    duplicate = true;
                    break;
                }
            }
            if (!imageName.equals("Overview") && !imageName.equals("Label") && duplicate) {
                imageName += " #" + ii;
            }
            if (imageName.equals("Overview") || imageName.equals("Label")) {
                imageName = imageName.toLowerCase();
            }
            store.setImageName(imageName, ii);
            store.setObjectiveSettingsID(MetadataTools.createLSID("Objective", 0, nextPyramid - 1), ii);
            store.setObjectiveSettingsRefractiveIndex(pyramid.refractiveIndex, ii);
            if (pyramid.physicalSizeX > 0) {
                store.setPixelsPhysicalSizeX(FormatTools.getPhysicalSizeX(pyramid.physicalSizeX), ii);
            }
            if (pyramid.physicalSizeY > 0) {
                store.setPixelsPhysicalSizeY(FormatTools.getPhysicalSizeY(pyramid.physicalSizeY), ii);
            }
            if (pyramid.acquisitionTime != null) {
                // acquisition time is stored in seconds
                store.setImageAcquisitionDate(new Timestamp(DateTools.convertDate(pyramid.acquisitionTime * 1000, DateTools.UNIX)), ii);
            }
        } else {
            store.setImageName("macro image", ii);
        }
        i += core.get(i).resolutionCount;
    }
    setCoreIndex(0);
}
Also used : IFD(loci.formats.tiff.IFD) ArrayList(java.util.ArrayList) PhotoInterp(loci.formats.tiff.PhotoInterp) CoreMetadata(loci.formats.CoreMetadata) Timestamp(ome.xml.model.primitives.Timestamp) FormatException(loci.formats.FormatException) MetadataStore(loci.formats.meta.MetadataStore) IFDList(loci.formats.tiff.IFDList) TiffParser(loci.formats.tiff.TiffParser) RandomAccessInputStream(loci.common.RandomAccessInputStream) Location(loci.common.Location)

Example 17 with IFDList

use of loci.formats.tiff.IFDList in project bioformats by openmicroscopy.

the class ZeissLSMReader method initMetadata.

protected void initMetadata(int series) throws FormatException, IOException {
    setSeries(series);
    IFDList ifds = ifdsList.get(series);
    IFD ifd = ifds.get(0);
    in.close();
    in = new RandomAccessInputStream(getLSMFileFromSeries(series), 16);
    in.order(isLittleEndian());
    tiffParser = new TiffParser(in);
    PhotoInterp photo = ifd.getPhotometricInterpretation();
    int samples = ifd.getSamplesPerPixel();
    CoreMetadata ms = core.get(series);
    ms.sizeX = (int) ifd.getImageWidth();
    ms.sizeY = (int) ifd.getImageLength();
    ms.rgb = samples > 1 || photo == PhotoInterp.RGB;
    ms.interleaved = false;
    ms.sizeC = isRGB() ? samples : 1;
    ms.pixelType = ifd.getPixelType();
    ms.imageCount = ifds.size();
    ms.sizeZ = getImageCount();
    ms.sizeT = 1;
    LOGGER.info("Reading LSM metadata for series #{}", series);
    MetadataStore store = makeFilterMetadata();
    int instrument = getEffectiveSeries(series);
    String imageName = getLSMFileFromSeries(series);
    if (imageName.indexOf('.') != -1) {
        imageName = imageName.substring(0, imageName.lastIndexOf("."));
    }
    if (imageName.indexOf(File.separator) != -1) {
        imageName = imageName.substring(imageName.lastIndexOf(File.separator) + 1);
    }
    if (lsmFilenames.length != getSeriesCount()) {
        imageName += " #" + (getPosition(series) + 1);
    }
    // link Instrument and Image
    store.setImageID(MetadataTools.createLSID("Image", series), series);
    String instrumentID = MetadataTools.createLSID("Instrument", instrument);
    store.setInstrumentID(instrumentID, instrument);
    store.setImageInstrumentRef(instrumentID, series);
    RandomAccessInputStream ras = getCZTag(ifd);
    if (ras == null) {
        imageNames.add(imageName);
        return;
    }
    ras.seek(16);
    ms.sizeZ = ras.readInt();
    ras.skipBytes(4);
    ms.sizeT = ras.readInt();
    int dataType = ras.readInt();
    switch(dataType) {
        case 2:
            addSeriesMeta("DataType", "12 bit unsigned integer");
            break;
        case 5:
            addSeriesMeta("DataType", "32 bit float");
            break;
        case 0:
            addSeriesMeta("DataType", "varying data types");
            break;
        default:
            addSeriesMeta("DataType", "8 bit unsigned integer");
    }
    if (getMetadataOptions().getMetadataLevel() != MetadataLevel.MINIMUM) {
        ras.seek(0);
        addSeriesMeta("MagicNumber ", ras.readInt());
        addSeriesMeta("StructureSize", ras.readInt());
        addSeriesMeta("DimensionX", ras.readInt());
        addSeriesMeta("DimensionY", ras.readInt());
        ras.seek(32);
        addSeriesMeta("ThumbnailX", ras.readInt());
        addSeriesMeta("ThumbnailY", ras.readInt());
        // pixel sizes are stored in meters, we need them in microns
        pixelSizeX = ras.readDouble() * 1000000;
        pixelSizeY = ras.readDouble() * 1000000;
        pixelSizeZ = ras.readDouble() * 1000000;
        addSeriesMeta("VoxelSizeX", pixelSizeX);
        addSeriesMeta("VoxelSizeY", pixelSizeY);
        addSeriesMeta("VoxelSizeZ", pixelSizeZ);
        originX = ras.readDouble() * 1000000;
        originY = ras.readDouble() * 1000000;
        originZ = ras.readDouble() * 1000000;
        addSeriesMeta("OriginX", originX);
        addSeriesMeta("OriginY", originY);
        addSeriesMeta("OriginZ", originZ);
    } else
        ras.seek(88);
    int scanType = ras.readShort();
    switch(scanType) {
        case 0:
            addSeriesMeta("ScanType", "x-y-z scan");
            ms.dimensionOrder = "XYZCT";
            break;
        case 1:
            addSeriesMeta("ScanType", "z scan (x-z plane)");
            ms.dimensionOrder = "XYZCT";
            break;
        case 2:
            addSeriesMeta("ScanType", "line scan");
            ms.dimensionOrder = "XYZCT";
            break;
        case 3:
            addSeriesMeta("ScanType", "time series x-y");
            ms.dimensionOrder = "XYTCZ";
            break;
        case 4:
            addSeriesMeta("ScanType", "time series x-z");
            ms.dimensionOrder = "XYZTC";
            break;
        case 5:
            addSeriesMeta("ScanType", "time series 'Mean of ROIs'");
            ms.dimensionOrder = "XYTCZ";
            break;
        case 6:
            addSeriesMeta("ScanType", "time series x-y-z");
            ms.dimensionOrder = "XYZTC";
            break;
        case 7:
            addSeriesMeta("ScanType", "spline scan");
            ms.dimensionOrder = "XYCTZ";
            break;
        case 8:
            addSeriesMeta("ScanType", "spline scan x-z");
            ms.dimensionOrder = "XYCZT";
            break;
        case 9:
            addSeriesMeta("ScanType", "time series spline plane x-z");
            ms.dimensionOrder = "XYTCZ";
            break;
        case 10:
            addSeriesMeta("ScanType", "point mode");
            ms.dimensionOrder = "XYZCT";
            break;
        default:
            addSeriesMeta("ScanType", "x-y-z scan");
            ms.dimensionOrder = "XYZCT";
    }
    ms.indexed = lut != null && lut[series] != null;
    if (isIndexed()) {
        ms.rgb = false;
    }
    if (getSizeC() == 0)
        ms.sizeC = 1;
    if (isRGB()) {
        // shuffle C to front of order string
        ms.dimensionOrder = getDimensionOrder().replaceAll("C", "");
        ms.dimensionOrder = getDimensionOrder().replaceAll("XY", "XYC");
    }
    if (getEffectiveSizeC() == 0) {
        ms.imageCount = getSizeZ() * getSizeT();
    } else {
        ms.imageCount = getSizeZ() * getSizeT() * getEffectiveSizeC();
    }
    if (getImageCount() != ifds.size()) {
        int diff = getImageCount() - ifds.size();
        ms.imageCount = ifds.size();
        if (diff % getSizeZ() == 0) {
            ms.sizeT -= (diff / getSizeZ());
        } else if (diff % getSizeT() == 0) {
            ms.sizeZ -= (diff / getSizeT());
        } else if (getSizeZ() > 1) {
            ms.sizeZ = ifds.size();
            ms.sizeT = 1;
        } else if (getSizeT() > 1) {
            ms.sizeT = ifds.size();
            ms.sizeZ = 1;
        }
    }
    if (getSizeZ() == 0)
        ms.sizeZ = getImageCount();
    if (getSizeT() == 0)
        ms.sizeT = getImageCount() / getSizeZ();
    long channelColorsOffset = 0;
    long timeStampOffset = 0;
    long eventListOffset = 0;
    long scanInformationOffset = 0;
    long channelWavelengthOffset = 0;
    long applicationTagOffset = 0;
    channelColor = new Color[getSizeC()];
    if (getMetadataOptions().getMetadataLevel() != MetadataLevel.MINIMUM) {
        int spectralScan = ras.readShort();
        if (spectralScan != 1) {
            addSeriesMeta("SpectralScan", "no spectral scan");
        } else
            addSeriesMeta("SpectralScan", "acquired with spectral scan");
        int type = ras.readInt();
        switch(type) {
            case 1:
                addSeriesMeta("DataType2", "calculated data");
                break;
            case 2:
                addSeriesMeta("DataType2", "animation");
                break;
            default:
                addSeriesMeta("DataType2", "original scan data");
        }
        long[] overlayOffsets = new long[9];
        String[] overlayKeys = new String[] { "VectorOverlay", "InputLut", "OutputLut", "ROI", "BleachROI", "MeanOfRoisOverlay", "TopoIsolineOverlay", "TopoProfileOverlay", "LinescanOverlay" };
        overlayOffsets[0] = ras.readInt();
        overlayOffsets[1] = ras.readInt();
        overlayOffsets[2] = ras.readInt();
        channelColorsOffset = ras.readInt();
        addSeriesMeta("TimeInterval", ras.readDouble());
        ras.skipBytes(4);
        scanInformationOffset = ras.readInt();
        applicationTagOffset = ras.readInt();
        timeStampOffset = ras.readInt();
        eventListOffset = ras.readInt();
        overlayOffsets[3] = ras.readInt();
        overlayOffsets[4] = ras.readInt();
        ras.skipBytes(4);
        addSeriesMeta("DisplayAspectX", ras.readDouble());
        addSeriesMeta("DisplayAspectY", ras.readDouble());
        addSeriesMeta("DisplayAspectZ", ras.readDouble());
        addSeriesMeta("DisplayAspectTime", ras.readDouble());
        overlayOffsets[5] = ras.readInt();
        overlayOffsets[6] = ras.readInt();
        overlayOffsets[7] = ras.readInt();
        overlayOffsets[8] = ras.readInt();
        if (getMetadataOptions().getMetadataLevel() != MetadataLevel.NO_OVERLAYS) {
            for (int i = 0; i < overlayOffsets.length; i++) {
                parseOverlays(series, overlayOffsets[i], overlayKeys[i], store);
            }
        }
        addSeriesMeta("ToolbarFlags", ras.readInt());
        channelWavelengthOffset = ras.readInt();
        ras.skipBytes(64);
    } else
        ras.skipBytes(182);
    if (getSizeC() > 1) {
        if (!splitPlanes)
            splitPlanes = isRGB();
        ms.rgb = false;
        if (splitPlanes)
            ms.imageCount *= getSizeC();
    }
    // NB: the Zeiss LSM 5.5 specification indicates that there should be
    // 15 32-bit integers here; however, there are actually 16 32-bit
    // integers before the tile position offset.
    // We have confirmed with Zeiss that this is correct, and the 6.0
    // specification was updated to contain the correct information.
    // rotations and phases may be reversed
    // we only have examples where both values are equal
    rotations = ras.readInt();
    phases = ras.readInt();
    illuminations = ras.readInt();
    if (rotations > 1) {
        ms.moduloZ.step = ms.sizeZ;
        ms.moduloZ.end = ms.sizeZ * (rotations - 1);
        ms.moduloZ.type = FormatTools.ROTATION;
        ms.sizeZ *= rotations;
    }
    if (illuminations > 1) {
        ms.moduloC.step = ms.sizeC;
        ms.moduloC.end = ms.sizeC * (illuminations - 1);
        ms.moduloC.type = FormatTools.ILLUMINATION;
        ms.moduloC.parentType = FormatTools.CHANNEL;
        ms.sizeC *= illuminations;
    }
    if (phases > 1) {
        ms.moduloT.step = ms.sizeT;
        ms.moduloT.end = ms.sizeT * (phases - 1);
        ms.moduloT.type = FormatTools.PHASE;
        ms.sizeT *= phases;
    }
    for (int c = 0; c < getEffectiveSizeC(); c++) {
        String lsid = MetadataTools.createLSID("Channel", series, c);
        store.setChannelID(lsid, series, c);
    }
    if (getMetadataOptions().getMetadataLevel() != MetadataLevel.MINIMUM) {
        ras.skipBytes(52);
        int tilePositionOffset = ras.readInt();
        ras.skipBytes(36);
        int positionOffset = ras.readInt();
        // read referenced structures
        addSeriesMeta("DimensionZ", getSizeZ());
        addSeriesMeta("DimensionChannels", getSizeC());
        addSeriesMeta("DimensionM", dimensionM);
        addSeriesMeta("DimensionP", dimensionP);
        if (lsmFilenames.length == 1) {
            xCoordinates.clear();
            yCoordinates.clear();
            zCoordinates.clear();
        }
        if (positionOffset != 0) {
            in.seek(positionOffset);
            int nPositions = in.readInt();
            for (int i = 0; i < nPositions; i++) {
                double xPos = originX + in.readDouble() * 1000000;
                double yPos = originY + in.readDouble() * 1000000;
                double zPos = originZ + in.readDouble() * 1000000;
                xCoordinates.add(xPos);
                yCoordinates.add(yPos);
                zCoordinates.add(zPos);
                addGlobalMetaList("X position for position", xPos);
                addGlobalMetaList("Y position for position", yPos);
                addGlobalMetaList("Z position for position", zPos);
            }
        }
        if (tilePositionOffset != 0) {
            in.seek(tilePositionOffset);
            int nTiles = in.readInt();
            for (int i = 0; i < nTiles; i++) {
                double xPos = originX + in.readDouble() * 1000000;
                double yPos = originY + in.readDouble() * 1000000;
                double zPos = originZ + in.readDouble() * 1000000;
                if (xCoordinates.size() > i) {
                    xPos += xCoordinates.get(i);
                    xCoordinates.set(i, xPos);
                } else if (xCoordinates.size() == i) {
                    xCoordinates.add(xPos);
                }
                if (yCoordinates.size() > i) {
                    yPos += yCoordinates.get(i);
                    yCoordinates.set(i, yPos);
                } else if (yCoordinates.size() == i) {
                    yCoordinates.add(yPos);
                }
                if (zCoordinates.size() > i) {
                    zPos += zCoordinates.get(i);
                    zCoordinates.set(i, zPos);
                } else if (zCoordinates.size() == i) {
                    zCoordinates.add(zPos);
                }
                addGlobalMetaList("X position for position", xPos);
                addGlobalMetaList("Y position for position", yPos);
                addGlobalMetaList("Z position for position", zPos);
            }
        }
        if (channelColorsOffset != 0) {
            in.seek(channelColorsOffset + 12);
            int colorsOffset = in.readInt();
            int namesOffset = in.readInt();
            if (colorsOffset > 0) {
                in.seek(channelColorsOffset + colorsOffset);
                lut[getSeries()] = new byte[getSizeC() * 3][256];
                core.get(getSeries()).indexed = true;
                for (int i = 0; i < getSizeC(); i++) {
                    if (i >= channelColor.length) {
                        continue;
                    }
                    int color = in.readInt();
                    int red = color & 0xff;
                    int green = (color & 0xff00) >> 8;
                    int blue = (color & 0xff0000) >> 16;
                    // otherwise set the color to white, as this will display better
                    if (red == 0 && green == 0 & blue == 0) {
                        if (i > 0) {
                            red = channelColor[i - 1].getRed();
                            green = channelColor[i - 1].getGreen();
                            blue = channelColor[i - 1].getBlue();
                        } else {
                            red = 255;
                            green = 255;
                            blue = 255;
                        }
                    }
                    channelColor[i] = new Color(red, green, blue, 255);
                    for (int j = 0; j < 256; j++) {
                        lut[getSeries()][i * 3][j] = (byte) ((red / 255.0) * j);
                        lut[getSeries()][i * 3 + 1][j] = (byte) ((green / 255.0) * j);
                        lut[getSeries()][i * 3 + 2][j] = (byte) ((blue / 255.0) * j);
                    }
                }
            }
            if (namesOffset > 0) {
                in.seek(channelColorsOffset + namesOffset);
                channelNames[series] = new String[getSizeC()];
                for (int i = 0; i < getSizeC(); i++) {
                    if (in.getFilePointer() >= in.length() - 1)
                        break;
                    // we want to read until we find a null char
                    int length = in.readInt();
                    String name = in.readString(length);
                    while ((name.length() > 0) && (name.codePointAt(name.length() - 1) == 0)) {
                        name = name.substring(0, name.length() - 1);
                    }
                    if (name.length() <= 128) {
                        addSeriesMetaList("ChannelName", name);
                    }
                    channelNames[series][i] = name;
                }
            }
        }
        if (timeStampOffset != 0) {
            in.seek(timeStampOffset + 4);
            int nStamps = in.readInt();
            for (int i = 0; i < nStamps; i++) {
                double stamp = in.readDouble();
                addSeriesMetaList("TimeStamp", stamp);
                timestamps.add(stamp);
            }
        }
        if (eventListOffset != 0) {
            in.seek(eventListOffset + 4);
            int numEvents = in.readInt();
            in.seek(in.getFilePointer() - 4);
            in.order(!in.isLittleEndian());
            int tmpEvents = in.readInt();
            if (numEvents < 0)
                numEvents = tmpEvents;
            else
                numEvents = (int) Math.min(numEvents, tmpEvents);
            in.order(!in.isLittleEndian());
            if (numEvents > 65535)
                numEvents = 0;
            for (int i = 0; i < numEvents; i++) {
                if (in.getFilePointer() + 16 <= in.length()) {
                    int size = in.readInt();
                    double eventTime = in.readDouble();
                    int eventType = in.readInt();
                    addSeriesMetaList("Event Time", eventTime);
                    addSeriesMetaList("Event Type", eventType);
                    long fp = in.getFilePointer();
                    int len = size - 16;
                    if (len > 65536)
                        len = 65536;
                    if (len < 0)
                        len = 0;
                    addSeriesMetaList("Event Description", in.readString(len));
                    in.seek(fp + size - 16);
                    if (in.getFilePointer() < 0)
                        break;
                }
            }
        }
        if (scanInformationOffset != 0) {
            in.seek(scanInformationOffset);
            nextLaser = nextDetector = 0;
            nextFilter = nextDichroicChannel = nextDichroic = 0;
            nextDetectChannel = nextIllumChannel = 0;
            final List<SubBlock> blocks = new ArrayList<SubBlock>();
            while (in.getFilePointer() < in.length() - 12) {
                if (in.getFilePointer() < 0)
                    break;
                int entry = in.readInt();
                int blockType = in.readInt();
                int dataSize = in.readInt();
                if (blockType == TYPE_SUBBLOCK) {
                    SubBlock block = null;
                    switch(entry) {
                        case SUBBLOCK_RECORDING:
                            block = new Recording();
                            break;
                        case SUBBLOCK_LASER:
                            block = new Laser();
                            break;
                        case SUBBLOCK_TRACK:
                            block = new Track();
                            break;
                        case SUBBLOCK_DETECTION_CHANNEL:
                            block = new DetectionChannel();
                            break;
                        case SUBBLOCK_ILLUMINATION_CHANNEL:
                            block = new IlluminationChannel();
                            break;
                        case SUBBLOCK_BEAM_SPLITTER:
                            block = new BeamSplitter();
                            break;
                        case SUBBLOCK_DATA_CHANNEL:
                            block = new DataChannel();
                            break;
                        case SUBBLOCK_TIMER:
                            block = new Timer();
                            break;
                        case SUBBLOCK_MARKER:
                            block = new Marker();
                            break;
                    }
                    if (block != null) {
                        blocks.add(block);
                    }
                } else if (dataSize + in.getFilePointer() <= in.length() && dataSize > 0) {
                    in.skipBytes(dataSize);
                } else
                    break;
            }
            final List<SubBlock> nonAcquiredBlocks = new ArrayList<SubBlock>();
            SubBlock[] metadataBlocks = blocks.toArray(new SubBlock[0]);
            for (SubBlock block : metadataBlocks) {
                block.addToHashtable();
                if (!block.acquire) {
                    nonAcquiredBlocks.add(block);
                    blocks.remove(block);
                }
            }
            for (int i = 0; i < blocks.size(); i++) {
                SubBlock block = blocks.get(i);
                // a valid DataChannel or IlluminationChannel
                if ((block instanceof IlluminationChannel) && i < blocks.size() - 1) {
                    SubBlock nextBlock = blocks.get(i + 1);
                    if (!(nextBlock instanceof DataChannel) && !(nextBlock instanceof IlluminationChannel)) {
                        ((IlluminationChannel) block).wavelength = null;
                    }
                } else // a valid Track or DetectionChannel
                if ((block instanceof DetectionChannel) && i > 0) {
                    SubBlock prevBlock = blocks.get(i - 1);
                    if (!(prevBlock instanceof Track) && !(prevBlock instanceof DetectionChannel)) {
                        block.acquire = false;
                        nonAcquiredBlocks.add(block);
                    }
                }
                if (block.acquire)
                    populateMetadataStore(block, store, series);
            }
            for (SubBlock block : nonAcquiredBlocks) {
                populateMetadataStore(block, store, series);
            }
        }
        if (applicationTagOffset != 0) {
            in.seek(applicationTagOffset);
            parseApplicationTags();
        }
    }
    imageNames.add(imageName);
    if (getMetadataOptions().getMetadataLevel() != MetadataLevel.MINIMUM) {
        if (userName != null) {
            String experimenterID = MetadataTools.createLSID("Experimenter", 0);
            store.setExperimenterID(experimenterID, 0);
            store.setExperimenterUserName(userName, 0);
        }
        Length pixX = FormatTools.getPhysicalSizeX(pixelSizeX);
        Length pixY = FormatTools.getPhysicalSizeY(pixelSizeY);
        Length pixZ = FormatTools.getPhysicalSizeZ(pixelSizeZ);
        if (pixX != null) {
            store.setPixelsPhysicalSizeX(pixX, series);
        }
        if (pixY != null) {
            store.setPixelsPhysicalSizeY(pixY, series);
        }
        if (pixZ != null) {
            store.setPixelsPhysicalSizeZ(pixZ, series);
        }
        for (int i = 0; i < getSizeC(); i++) {
            store.setChannelColor(channelColor[i], series, i);
            if (channelNames[series] != null) {
                store.setChannelName(channelNames[series][i], series, i);
            }
        }
        int stampIndex = 0;
        for (int i = 0; i < series; i++) {
            stampIndex += core.get(i).sizeT;
        }
        double firstStamp = 0;
        if (timestamps.size() > 0 && stampIndex < timestamps.size()) {
            firstStamp = timestamps.get(stampIndex).doubleValue();
        }
        for (int i = 0; i < getImageCount(); i++) {
            int[] zct = FormatTools.getZCTCoords(this, i);
            if (getSizeT() > 1 && zct[2] < timestamps.size() - stampIndex) {
                double thisStamp = timestamps.get(stampIndex + zct[2]).doubleValue();
                store.setPlaneDeltaT(new Time(thisStamp - firstStamp, UNITS.SECOND), series, i);
            }
            if (xCoordinates.size() > series) {
                final Double xCoord = xCoordinates.get(series);
                final Double yCoord = yCoordinates.get(series);
                final Double zCoord = zCoordinates.get(series);
                if (xCoord == null) {
                    store.setPlanePositionX(null, series, i);
                } else {
                    final Length x = new Length(xCoord, UNITS.REFERENCEFRAME);
                    store.setPlanePositionX(x, series, i);
                }
                if (yCoord == null) {
                    store.setPlanePositionY(null, series, i);
                } else {
                    final Length y = new Length(yCoord, UNITS.REFERENCEFRAME);
                    store.setPlanePositionY(y, series, i);
                }
                if (zCoord == null) {
                    store.setPlanePositionZ(null, series, i);
                } else {
                    final Length z = new Length(zCoord, UNITS.REFERENCEFRAME);
                    store.setPlanePositionZ(z, series, i);
                }
            }
        }
    }
    ras.close();
}
Also used : IFD(loci.formats.tiff.IFD) ArrayList(java.util.ArrayList) Time(ome.units.quantity.Time) Color(ome.xml.model.primitives.Color) PhotoInterp(loci.formats.tiff.PhotoInterp) CoreMetadata(loci.formats.CoreMetadata) MetadataStore(loci.formats.meta.MetadataStore) Length(ome.units.quantity.Length) IFDList(loci.formats.tiff.IFDList) TiffParser(loci.formats.tiff.TiffParser) RandomAccessInputStream(loci.common.RandomAccessInputStream)

Example 18 with IFDList

use of loci.formats.tiff.IFDList in project bioformats by openmicroscopy.

the class ZeissLSMReader method initFile.

// -- Internal FormatReader API methods --
/* @see loci.formats.FormatReader#initFile(String) */
@Override
protected void initFile(String id) throws FormatException, IOException {
    super.initFile(id);
    if (checkSuffix(id, MDB_SUFFIX)) {
        lsmFilenames = parseMDB(id);
    } else
        lsmFilenames = new String[] { id };
    if (lsmFilenames == null || lsmFilenames.length == 0) {
        throw new FormatException("LSM files were not found.");
    }
    totalROIs = 0;
    timestamps = new ArrayList<Double>();
    imageNames = new ArrayList<String>();
    xCoordinates = new ArrayList<Double>();
    yCoordinates = new ArrayList<Double>();
    zCoordinates = new ArrayList<Double>();
    seriesCounts = new HashMap<String, Integer>();
    int seriesCount = 0;
    final List<String> validFiles = new ArrayList<String>();
    for (String filename : lsmFilenames) {
        try {
            int extraSeries = getExtraSeries(filename);
            seriesCounts.put(filename, extraSeries);
            seriesCount += extraSeries;
            validFiles.add(filename);
        } catch (IOException e) {
            LOGGER.debug("Failed to parse " + filename, e);
        }
    }
    lsmFilenames = validFiles.toArray(new String[validFiles.size()]);
    core.clear();
    for (int c = 0; c < seriesCount; c++) {
        CoreMetadata ms = new CoreMetadata();
        core.add(ms);
    }
    channelNames = new String[seriesCount][];
    ifdsList = new ArrayList<IFDList>();
    for (int series = 0; series < seriesCount; series++) {
        ifdsList.add(null);
    }
    int realSeries = 0;
    for (int i = 0; i < lsmFilenames.length; i++) {
        RandomAccessInputStream stream = null;
        try {
            stream = new RandomAccessInputStream(lsmFilenames[i], 16);
            int count = seriesCounts.get(lsmFilenames[i]);
            TiffParser tp = new TiffParser(stream);
            Boolean littleEndian = tp.checkHeader();
            long[] ifdOffsets = tp.getIFDOffsets();
            int ifdsPerSeries = (ifdOffsets.length / 2) / count;
            int offset = 0;
            Object zeissTag = null;
            for (int s = 0; s < count; s++, realSeries++) {
                CoreMetadata ms = core.get(realSeries);
                ms.littleEndian = littleEndian;
                IFDList ifds = new IFDList();
                while (ifds.size() < ifdsPerSeries) {
                    tp.setDoCaching(offset == 0);
                    IFD ifd = tp.getIFD(ifdOffsets[offset]);
                    if (offset == 0)
                        zeissTag = ifd.get(ZEISS_ID);
                    if (offset > 0 && ifds.isEmpty()) {
                        ifd.putIFDValue(ZEISS_ID, zeissTag);
                    }
                    ifds.add(ifd);
                    if (zeissTag != null)
                        offset += 2;
                    else
                        offset++;
                }
                for (IFD ifd : ifds) {
                    tp.fillInIFD(ifd);
                }
                ifdsList.set(realSeries, ifds);
            }
        } catch (IOException e) {
            throw e;
        } finally {
            if (stream != null)
                stream.close();
        }
    }
    MetadataStore store = makeFilterMetadata();
    lut = new byte[ifdsList.size()][][];
    long[] previousStripOffsets = null;
    for (int series = 0; series < ifdsList.size(); series++) {
        // the previous series
        if (series > 0 && getSizeT() > 1) {
            previousStripOffsets = null;
        }
        IFDList ifds = ifdsList.get(series);
        for (IFD ifd : ifds) {
            // than LZW compression is used
            if (ifd.getCompression() != TiffCompression.LZW) {
                ifd.putIFDValue(IFD.PREDICTOR, 1);
            }
        }
        // fix the offsets for > 4 GB files
        RandomAccessInputStream s = null;
        try {
            s = new RandomAccessInputStream(getLSMFileFromSeries(series));
            for (int i = 0; i < ifds.size(); i++) {
                long[] stripOffsets = ifds.get(i).getStripOffsets();
                if (stripOffsets == null || (i != 0 && previousStripOffsets == null)) {
                    throw new FormatException("Strip offsets are missing; this is an invalid file.");
                } else if (i == 0 && previousStripOffsets == null) {
                    previousStripOffsets = stripOffsets;
                    continue;
                }
                boolean neededAdjustment = false;
                for (int j = 0; j < stripOffsets.length; j++) {
                    if (j >= previousStripOffsets.length)
                        break;
                    if (stripOffsets[j] < previousStripOffsets[j]) {
                        stripOffsets[j] = (previousStripOffsets[j] & ~0xffffffffL) | (stripOffsets[j] & 0xffffffffL);
                        if (stripOffsets[j] < previousStripOffsets[j]) {
                            long newOffset = stripOffsets[j] + 0x100000000L;
                            if (newOffset < s.length()) {
                                stripOffsets[j] = newOffset;
                            }
                        }
                        neededAdjustment = true;
                    }
                    if (neededAdjustment) {
                        ifds.get(i).putIFDValue(IFD.STRIP_OFFSETS, stripOffsets);
                    }
                }
                previousStripOffsets = stripOffsets;
            }
            initMetadata(series);
        } catch (IOException e) {
            throw e;
        } finally {
            if (s != null)
                s.close();
        }
    }
    for (int i = 0; i < getSeriesCount(); i++) {
        CoreMetadata ms = core.get(i);
        ms.imageCount = ms.sizeZ * ms.sizeC * ms.sizeT;
    }
    MetadataTools.populatePixels(store, this, true);
    for (int series = 0; series < ifdsList.size(); series++) {
        setSeries(series);
        if (series < imageNames.size()) {
            store.setImageName(imageNames.get(series), series);
        }
        if (acquiredDate.containsKey(series)) {
            store.setImageAcquisitionDate(new Timestamp(acquiredDate.get(series)), series);
        }
    }
    setSeries(0);
}
Also used : IFD(loci.formats.tiff.IFD) ArrayList(java.util.ArrayList) IOException(java.io.IOException) CoreMetadata(loci.formats.CoreMetadata) Timestamp(ome.xml.model.primitives.Timestamp) FormatException(loci.formats.FormatException) MetadataStore(loci.formats.meta.MetadataStore) IFDList(loci.formats.tiff.IFDList) TiffParser(loci.formats.tiff.TiffParser) RandomAccessInputStream(loci.common.RandomAccessInputStream)

Example 19 with IFDList

use of loci.formats.tiff.IFDList in project bioformats by openmicroscopy.

the class TCSReader method initFile.

// -- Internal FormatReader API methods --
/* @see loci.formats.FormatReader#initFile(String) */
@Override
protected void initFile(String id) throws FormatException, IOException {
    Location l = new Location(id).getAbsoluteFile();
    Location parent = l.getParentFile();
    String[] list = parent.list();
    Arrays.sort(list);
    boolean isXML = checkSuffix(id, XML_SUFFIX);
    if (list != null) {
        for (String file : list) {
            if (checkSuffix(file, XML_SUFFIX) && !isXML && isGroupFiles()) {
                xmlFile = new Location(parent, file).getAbsolutePath();
                break;
            } else if (checkSuffix(file, TiffReader.TIFF_SUFFIXES) && isXML) {
                initFile(new Location(parent, file).getAbsolutePath());
                return;
            }
        }
    }
    if (isXML)
        xmlFile = l.getAbsolutePath();
    super.initFile(id);
    MetadataStore store = makeFilterMetadata();
    in = new RandomAccessInputStream(id, 16);
    tiffParser = new TiffParser(in);
    tiffs = new ArrayList<String>();
    IFDList ifds = tiffParser.getIFDs();
    String date = ifds.get(0).getIFDStringValue(IFD.DATE_TIME);
    if (date != null) {
        datestamp = DateTools.getTime(date, "yyyy:MM:dd HH:mm:ss");
    }
    groupFiles();
    addGlobalMeta("Number of image files", tiffs.size());
    tiffReaders = new TiffReader[tiffs.size()];
    for (int i = 0; i < tiffReaders.length; i++) {
        tiffReaders[i] = new TiffReader();
    }
    tiffReaders[0].setId(tiffs.get(0));
    int[] ch = new int[ifds.size()];
    int[] idx = new int[ifds.size()];
    long[] stamp = new long[ifds.size()];
    int channelCount = 0;
    CoreMetadata ms0 = core.get(0);
    ms0.sizeZ = 1;
    ms0.sizeC = tiffReaders[0].getSizeC();
    ms0.dimensionOrder = isRGB() ? "XYC" : "XY";
    if (isGroupFiles()) {
        try {
            FilePattern fp = new FilePattern(new Location(currentId).getAbsoluteFile());
            AxisGuesser guesser = new AxisGuesser(fp, "XYTZC", 1, ifds.size(), 1, true);
            int[] axisTypes = guesser.getAxisTypes();
            int[] count = fp.getCount();
            for (int i = axisTypes.length - 1; i >= 0; i--) {
                if (axisTypes[i] == AxisGuesser.Z_AXIS) {
                    if (getDimensionOrder().indexOf('Z') == -1) {
                        ms0.dimensionOrder += 'Z';
                    }
                    ms0.sizeZ *= count[i];
                } else if (axisTypes[i] == AxisGuesser.C_AXIS) {
                    if (getDimensionOrder().indexOf('C') == -1) {
                        ms0.dimensionOrder += 'C';
                    }
                    ms0.sizeC *= count[i];
                }
            }
        } catch (NullPointerException e) {
        }
    }
    for (int i = 0; i < ifds.size(); i++) {
        String document = ifds.get(i).getIFDStringValue(IFD.DOCUMENT_NAME);
        if (document == null)
            continue;
        int index = document.indexOf("INDEX");
        String s = document.substring(8, index).trim();
        ch[i] = Integer.parseInt(s);
        if (ch[i] > channelCount)
            channelCount = ch[i];
        int space = document.indexOf(" ", index + 6);
        if (space < 0)
            continue;
        String n = document.substring(index + 6, space).trim();
        idx[i] = Integer.parseInt(n);
        date = document.substring(space, document.indexOf("FORMAT")).trim();
        stamp[i] = DateTools.getTime(date, DATE_FORMAT, ".");
        addGlobalMetaList("Timestamp for plane", stamp[i]);
    }
    ms0.sizeT = 0;
    // determine the axis sizes and ordering
    boolean unique = true;
    for (int i = 0; i < stamp.length; i++) {
        for (int j = i + 1; j < stamp.length; j++) {
            if (stamp[j] == stamp[i]) {
                unique = false;
                break;
            }
        }
        if (unique) {
            ms0.sizeT++;
            if (getDimensionOrder().indexOf('T') < 0) {
                ms0.dimensionOrder += 'T';
            }
        } else if (i > 0) {
            if ((ch[i] != ch[i - 1]) && getDimensionOrder().indexOf('C') < 0) {
                ms0.dimensionOrder += 'C';
            } else if (getDimensionOrder().indexOf('Z') < 0) {
                ms0.dimensionOrder += 'Z';
            }
        }
        unique = true;
    }
    if (getDimensionOrder().indexOf('Z') < 0)
        ms0.dimensionOrder += 'Z';
    if (getDimensionOrder().indexOf('C') < 0)
        ms0.dimensionOrder += 'C';
    if (getDimensionOrder().indexOf('T') < 0)
        ms0.dimensionOrder += 'T';
    if (getSizeC() == 0)
        ms0.sizeC = 1;
    if (getSizeT() == 0)
        ms0.sizeT = 1;
    if (channelCount == 0)
        channelCount = 1;
    if (getSizeZ() <= 1) {
        ms0.sizeZ = ifds.size() / (getSizeT() * channelCount);
    }
    ms0.sizeC *= channelCount;
    ms0.imageCount = getSizeZ() * getSizeT() * getSizeC();
    // cut up comment
    String comment = ifds.get(0).getComment();
    if (comment != null && comment.startsWith("[") && getMetadataOptions().getMetadataLevel() != MetadataLevel.MINIMUM) {
        String[] lines = comment.split("\n");
        for (String line : lines) {
            if (!line.startsWith("[")) {
                int eq = line.indexOf('=');
                if (eq < 0)
                    continue;
                String key = line.substring(0, eq).trim();
                String value = line.substring(eq + 1).trim();
                if (key.equals("VoxelSizeX")) {
                    try {
                        voxelX = Double.parseDouble(value);
                    } catch (NumberFormatException e) {
                    }
                } else if (key.equals("VoxelSizeY")) {
                    try {
                        voxelY = Double.parseDouble(value);
                    } catch (NumberFormatException e) {
                    }
                } else if (key.equals("VoxelSizeZ")) {
                    try {
                        voxelZ = Double.parseDouble(value);
                    } catch (NumberFormatException e) {
                    }
                }
                addGlobalMeta(key, value);
            }
        }
        metadata.remove("Comment");
    }
    ms0.sizeX = tiffReaders[0].getSizeX();
    ms0.sizeY = tiffReaders[0].getSizeY();
    ms0.rgb = tiffReaders[0].isRGB();
    ms0.pixelType = tiffReaders[0].getPixelType();
    ms0.littleEndian = tiffReaders[0].isLittleEndian();
    ms0.interleaved = tiffReaders[0].isInterleaved();
    ms0.falseColor = true;
    ms0.indexed = tiffReaders[0].isIndexed();
    if (isRGB())
        ms0.imageCount /= (getSizeC() / channelCount);
    if (getSizeZ() * getSizeT() * getEffectiveSizeC() != (ifds.size() * tiffReaders.length)) {
        int c = getEffectiveSizeC();
        if (c == 0)
            c = 1;
        ms0.sizeT = (ifds.size() * tiffReaders.length) / (c * getSizeZ());
        ms0.imageCount = getSizeT() * c * getSizeZ();
        if (getSizeT() == 0) {
            ms0.sizeT = 1;
            ms0.imageCount = ifds.size() * tiffReaders.length;
        }
    }
    if (getImageCount() == ifds.size() * getSizeZ() * getSizeT() && ifds.size() > 1) {
        if (getSizeZ() == 1) {
            ms0.sizeZ = ifds.size();
        } else if (getSizeT() == 1) {
            ms0.sizeT = ifds.size();
        } else
            ms0.sizeZ *= ifds.size();
    }
    if (xmlFile != null) {
        // parse XML metadata
        String xml = DataTools.readFile(xmlFile);
        xml = XMLTools.sanitizeXML(PREFIX + xml + SUFFIX);
        LeicaHandler handler = new LeicaHandler(store, getMetadataOptions().getMetadataLevel());
        XMLTools.parseXML(xml, handler);
        metadata = handler.getGlobalMetadata();
        MetadataTools.merge(handler.getGlobalMetadata(), metadata, "");
        core = handler.getCoreMetadataList();
        for (int i = 0; i < getSeriesCount(); i++) {
            CoreMetadata ms = core.get(i);
            if (tiffs.size() < ms.imageCount) {
                int div = ms.imageCount / ms.sizeC;
                ms.imageCount = tiffs.size();
                if (div >= ms.sizeZ)
                    ms.sizeZ /= div;
                else if (div >= ms.sizeT)
                    ms.sizeT /= div;
            }
            ms.dimensionOrder = getSizeZ() > getSizeT() ? "XYCZT" : "XYCTZ";
            ms.rgb = false;
            ms.interleaved = false;
            ms.indexed = tiffReaders[0].isIndexed();
        }
    }
    MetadataTools.populatePixels(store, this, true);
    Length sizeX = FormatTools.getPhysicalSizeX(voxelX);
    Length sizeY = FormatTools.getPhysicalSizeY(voxelY);
    Length sizeZ = FormatTools.getPhysicalSizeZ(voxelZ);
    if (sizeX != null) {
        store.setPixelsPhysicalSizeX(sizeX, 0);
    }
    if (sizeY != null) {
        store.setPixelsPhysicalSizeY(sizeY, 0);
    }
    if (sizeZ != null) {
        store.setPixelsPhysicalSizeZ(sizeZ, 0);
    }
}
Also used : CoreMetadata(loci.formats.CoreMetadata) MetadataStore(loci.formats.meta.MetadataStore) Length(ome.units.quantity.Length) IFDList(loci.formats.tiff.IFDList) TiffParser(loci.formats.tiff.TiffParser) RandomAccessInputStream(loci.common.RandomAccessInputStream) FilePattern(loci.formats.FilePattern) AxisGuesser(loci.formats.AxisGuesser) Location(loci.common.Location)

Example 20 with IFDList

use of loci.formats.tiff.IFDList in project bioformats by openmicroscopy.

the class ZeissTIFFReader method fillMetadataPass1.

@Override
protected void fillMetadataPass1(MetadataStore store) throws FormatException, IOException {
    super.fillMetadataPass1(store);
    int nplanes = tiffInfo.handler.planes.size();
    if (rawCount == 0)
        rawCount = nplanes;
    else if (rawCount != nplanes)
        LOGGER.warn("Problem determining correct number of image planes.  Document reported {}, while {} were found", rawCount, nplanes);
    if (rawCount == 0)
        LOGGER.warn("No image planes found");
    // Determine number of separate timepoints, channels, and z slices.
    for (ZeissTIFFHandler.Plane p : tiffInfo.handler.planes) {
        Plane np = new Plane();
        boolean tag_1047_present = false;
        for (Tag t : p.tagset.tags) {
            if (t.getKeyID() == 1047)
                tag_1047_present = true;
        }
        for (Tag t : p.tagset.tags) {
            // better to use the latter.
            if (t.getKeyID() != 1025 || tag_1047_present == false)
                np.tags.put(t.getKey(), t.getValue());
        }
        np.taglist = p.tagset.tags;
        // Other planes: _files/_meta
        if (nplanes == 1 && tiffInfo.multifile == false)
            np.filename = tiffInfo.origname;
        else
            np.filename = new CaseInsensitiveLocation(tiffInfo.basedir + "/" + tiffInfo.prefix + "_" + p.basename + ".tif").getAbsolutePath();
        int tileid = parseInt(np.tags.get("ImageTile Index"));
        int channelid = parseInt(np.tags.get("Image Channel Index"));
        int sliceid = parseInt(np.tags.get("Image Index Z"));
        int timepointid = parseInt(np.tags.get("Image Index T"));
        int xsize = parseInt(np.tags.get("Camera Frame Width"));
        int ysize = parseInt(np.tags.get("Camera Frame Height"));
        np.site = tileid;
        tileIndices.add(tileid);
        channelIndices.add(channelid);
        zIndices.add(sliceid);
        timepointIndices.add(timepointid);
        if (getSizeX() == 0) {
            core.get(0).sizeX = xsize;
            core.get(0).sizeY = ysize;
        }
        planes.add(np);
        if (bpp == 0) {
            tiffReader.setId(np.filename);
            IFDList ifds = tiffReader.getIFDs();
            tiffReader.close();
            IFD firstIFD = ifds.get(0);
            int bits = firstIFD.getBitsPerSample()[0];
            int samples = firstIFD.getSamplesPerPixel();
            bpp = (bits / 8) * samples;
        }
    }
    // Filter out images with an incomplete number of z slices.
    // This is to work around a probable bug in AxioVision.
    int full = Collections.max(tileIndices);
    int[] indexCount = new int[full + 1];
    int max = 0;
    for (Plane plane : planes) {
        indexCount[plane.site]++;
        if (indexCount[plane.site] > max)
            max = indexCount[plane.site];
    }
    for (int i = 0; i < full + 1; i++) {
        if (indexCount[i] != max)
            tileIndices.remove(i);
    }
    for (Iterator<Plane> i = planes.iterator(); i.hasNext(); ) {
        Plane plane = i.next();
        if (!tileIndices.contains(plane.site)) {
            i.remove();
        }
    }
    // Allocates memory for arrays below
    countImages();
    for (int i = 0; i < planes.size(); i++) {
        Plane plane = planes.get(i);
        int channelid = parseInt(plane.tags.get("Image Channel Index"));
        int sliceid = parseInt(plane.tags.get("Image Index Z"));
        int timepointid = parseInt(plane.tags.get("Image Index T"));
        coordinates[i][0] = sliceid;
        coordinates[i][1] = channelid;
        coordinates[i][2] = timepointid;
        imageFiles[i] = plane.filename;
    }
    int total = tileIndices.size() * channelIndices.size() * zIndices.size() * timepointIndices.size();
    if (total != planes.size())
        LOGGER.warn("Number of image planes not detected correctly: total={} planes.size={}", total, planes.size());
}
Also used : IFD(loci.formats.tiff.IFD) CaseInsensitiveLocation(loci.common.CaseInsensitiveLocation) IFDList(loci.formats.tiff.IFDList)

Aggregations

IFDList (loci.formats.tiff.IFDList)23 IFD (loci.formats.tiff.IFD)20 RandomAccessInputStream (loci.common.RandomAccessInputStream)15 CoreMetadata (loci.formats.CoreMetadata)15 TiffParser (loci.formats.tiff.TiffParser)15 MetadataStore (loci.formats.meta.MetadataStore)12 ArrayList (java.util.ArrayList)9 FormatException (loci.formats.FormatException)9 IOException (java.io.IOException)8 Length (ome.units.quantity.Length)8 Timestamp (ome.xml.model.primitives.Timestamp)8 PhotoInterp (loci.formats.tiff.PhotoInterp)7 Location (loci.common.Location)6 TiffRational (loci.formats.tiff.TiffRational)5 Time (ome.units.quantity.Time)5 HashMap (java.util.HashMap)3 File (java.io.File)2 List (java.util.List)2 Map (java.util.Map)2 StringTokenizer (java.util.StringTokenizer)2