All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.ttzero.excel.reader.BIFF8Sheet Maven / Gradle / Ivy

/*
 * Copyright (c) 2019-2020, [email protected] All Rights Reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package org.ttzero.excel.reader;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.ttzero.excel.entity.e3.Block;
import org.ttzero.excel.entity.e3.MergedSheetSubStream;
import org.ttzero.excel.entity.e3.SheetInfo;
import org.ttzero.excel.entity.e3.SheetSubStream;
import org.ttzero.excel.entity.e3.ShortBlock;

import java.util.Iterator;
import java.util.List;

import static org.ttzero.excel.reader.ExcelReader.COPY_ON_MERGED;

/**
 * BIFF8 format Worksheet
 *
 * @author guanquan.wang at 2019-04-16 16:55
 */
public class BIFF8Sheet implements Sheet {
    private final Logger LOGGER = LoggerFactory.getLogger(getClass());

    public BIFF8Sheet() { }

    public BIFF8Sheet(BIFF8Sheet sheet) {
        this.name = sheet.name;
        this.index = sheet.index;
        this.header = sheet.header;
        this.hidden = sheet.hidden;
        this.dimension = sheet.dimension;
        this.reader = sheet.reader;
        this.sheetInfo = sheet.sheetInfo;
        this.standard_sector = sheet.standard_sector;
        this.loaded = sheet.loaded;
        this.stream = sheet.stream;
    }

    protected String name;
    protected int index; // per sheet index of workbook
//        , size = -1; // size of rows per sheet
    protected HeaderRow header;
    protected boolean hidden; // state hidden
    protected BIFF8Reader reader;
    protected SheetSubStream stream;
    protected SheetInfo sheetInfo;
    protected Dimension dimension;
    /**
     * Mark the workbook in standard sector or short-sector
     */
    protected boolean standard_sector = true;

    /**
     * Mark loaded flag
     */
    protected boolean loaded;

    protected void setReader(BIFF8Reader reader) {
        this.reader = reader;
    }

    protected void setName(String name) {
        this.name = name;
    }

    /**
     * The worksheet name
     *
     * @return the sheet name
     */
    @Override
    public String getName() {
        return name;
    }

    /**
     * The index of worksheet located at the workbook
     *
     * @return the index(zero base)
     */
    @Override
    public int getIndex() {
        return index;
    }

    /**
     * The worksheet id, I don't know how to get it, return index temporarily
     *
     * @return id of worksheet
     */
    @Override
    public int getId() {
        return index;
    }

    protected void setIndex(int index) {
        this.index = index;
    }

    /**
     * size of rows.
     *
     * @return size of rows
     *      -1: unknown size
     * @deprecated use {@link #getDimension()} to getting full range address
     */
    @Deprecated
    @Override
    public int getSize() {
        return dimension != null ? dimension.lastRow - dimension.firstRow + 1 : -1;
    }

    /**
     * Returns The range address of the used area in
     * the current sheet
     * 

* NOTE: This method can only guarantee accurate row ranges * * @return worksheet {@link Dimension} ranges */ @Override public Dimension getDimension() { return dimension; } /** * Test Worksheet is hidden */ @Override public boolean isHidden() { return hidden; } /** * Returns the header of the list. * The first non-empty line defaults to the header information. * * @return the HeaderRow */ @Override public Row getHeader() { // Find the first row as header if (header == null) { BIFF8Row row = stream.firstRow(); if (row != null) { header = row.asHeader(); row.setHr(header); } } return header; } /** * Set the binding type * * @param clazz the binding type * @return sheet */ @Override public Sheet bind(Class clazz) { if (getHeader() != null) { try { header.setClassOnce(clazz); } catch (IllegalAccessException | InstantiationException e) { throw new ExcelReadException(e); } } return this; } /** * Parse Sheet-Sub-Stream * * @return Sheet */ @Override public BIFF8Sheet load() { if (!loaded) { loaded = true; if (reader.gs == null) { reader.gs = reader.parseGlobalSetting(); if (reader.gs == null) { throw new ExcelReadException("Miss the GlobalSetting. Maybe the file has be corrupted."); } } LOGGER.debug("Loading Worksheet: {}", sheetInfo.toString()); stream = getStream(); stream.setRowSupplier(this::createRow); stream.get(standard_sector ? new Block(reader.context, reader.gs.getFirstSid()).init() : new ShortBlock(reader.context, reader.gs.getFirstSid()).init()); dimension = stream.getRange(); } return this; } /** * Returns a {@link ShareStringParser} * * @return SheetSubStream */ protected SheetSubStream getStream() { SheetSubStream stream; switch (reader.option) { case COPY_ON_MERGED: stream = new MergedSheetSubStream(reader.gs, sheetInfo); break; default: stream = new SheetSubStream(reader.gs, sheetInfo); } return stream; } /** * Iterating each row of data contains header information and blank lines * * @return a row iterator */ @Override public Iterator iterator() { return new RowSetIterator(stream::nextRow, false); } /** * Iterating over data rows without header information and blank lines * * @return a row iterator */ @Override public Iterator dataIterator() { Iterator nIter = new RowSetIterator(stream::nextRow, true); if (nIter.hasNext()) { Row row = nIter.next(); if (header == null) header = row.asHeader(); row.setHr(header); } return nIter; } /** * List all pictures in workbook * * @return picture list or null if not exists. */ @Override public List listPictures() { if (reader.drawings == null && reader.gs.getMsoDrawingGroupBlockIndex() != null) { reader.drawings = new BIFF8Drawings(Block.loadWithIndex(reader.gs.getMsoDrawingGroupBlockIndex()), reader.all()); } return reader.drawings != null ? reader.drawings.listPictures(this) : null; } @Override public BIFF8Row createRow() { return new BIFF8Row(); } /** * Close resource */ @Override public void close() { // Nothing } @Override public BIFF8Sheet asSheet() { return (this instanceof BIFF8CalcSheet || this instanceof BIFF8MergeSheet) ? new BIFF8Sheet(this) : this; } @Override public BIFF8CalcSheet asCalcSheet() { return !(this instanceof BIFF8CalcSheet) ? new BIFF8CalcSheet(this) : (BIFF8CalcSheet) this; } @Override public BIFF8MergeSheet asMergeSheet() { return !(this instanceof BIFF8MergeSheet) ? new BIFF8MergeSheet(this) : (BIFF8MergeSheet) this; } @Override public String toString() { return "Sheet name: " + name + " has " + getDimension(); } @Override public Sheet reset() { loaded = false; load(); return this; } } /** * A sub {@link BIFF8Sheet} to parse cell calc */ class BIFF8CalcSheet extends BIFF8Sheet implements CalcSheet { BIFF8CalcSheet(BIFF8Sheet sheet) { this.name = sheet.name; this.index = sheet.index; this.header = sheet.header; this.hidden = sheet.hidden; this.dimension = sheet.dimension; this.reader = sheet.reader; this.sheetInfo = sheet.sheetInfo; this.standard_sector = sheet.standard_sector; this.loaded = sheet.loaded; this.stream = sheet.stream; } } /** * A sub {@link BIFF8Sheet} to copy value on merge cells */ class BIFF8MergeSheet extends BIFF8Sheet implements MergeSheet { BIFF8MergeSheet(BIFF8Sheet sheet) { this.name = sheet.name; this.index = sheet.index; this.header = sheet.header; this.hidden = sheet.hidden; this.dimension = sheet.dimension; this.reader = sheet.reader; this.sheetInfo = sheet.sheetInfo; this.standard_sector = sheet.standard_sector; if (sheet.loaded) { if (sheet.stream == null) this.stream = getStream(); else if (!(sheet.stream instanceof MergedSheetSubStream)) this.stream = MergedSheetSubStream.of(sheet.stream); else this.stream = sheet.stream; } } /** * Returns a {@link MergedSheetSubStream} * * @return MergedSheetSubStream */ @Override protected SheetSubStream getStream() { return new MergedSheetSubStream(reader.gs, sheetInfo); } @Override public Grid getMergeGrid() { return stream != null ? ((MergedSheetSubStream) stream).getMergeCells(): null; } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy