コード例 #1
0
ファイル: IfoReader.java プロジェクト: thedarkman/feinrip
  /**
   * Reads a PGC structure and completes the {@link DvdTitle} with the data found there.
   *
   * @param vts random access to the VTS file
   * @param title {@link DvdTitle} to complete
   * @param offset Offset of the PGC structure to be read
   */
  private void readVtsPgc(
      IfoRandomAccessFile vts, DvdTitle title, DvdTitleSet titleSet, long offset)
      throws IOException {
    vts.at(offset).skip(2);

    int chapters = vts.readu8();
    int cellCount = vts.readu8();
    LOG.debug("  chapters: %d, cells: %d", chapters, cellCount);

    title.setTotalTimeMs(vts.readBcdTimeMs());

    vts.skip(4);

    for (int ix = 0; ix < 8; ix++) {
      int snr = vts.readu8();
      if ((snr & 0x80) != 0) {
        DvdAudio audio = titleSet.getAudios().get(ix);
        int streamId = snr & 0x07;
        if (streamId == 0) {
          streamId = ix;
        }
        streamId += audio.getMode().getBaseStreamId();
        audio.setStreamId(streamId);
      }
      vts.skip(1);
    }

    for (int ix = 0; ix < 32; ix++) {
      int snr = vts.readu8();
      int sWide = vts.readu8();
      int sLetterbox = vts.readu8();
      int sPanScan = vts.readu8();
      if ((snr & 0x80) != 0) {
        snr &= 0x1F;
        sWide &= 0x1F;
        sLetterbox &= 0x1F;
        sPanScan &= 0x1F;

        DvdSubtitle sub = titleSet.getSubs().get(ix);
        if (titleSet.getAspect() == Aspect.ASPECT_16_9) {
          sub.setStreamWideId((sWide > 0 ? sWide : ix) + 0x20);
        } else {
          sub.setStream43Id((snr > 0 ? snr : ix) + 0x20);
        }

        if (titleSet.isLetterboxEnabled()) {
          sub.setStreamLetterboxId((sLetterbox > 0 ? sLetterbox : ix) + 0x20);
        }

        if (titleSet.isPanScanEnabled()) {
          sub.setStreamPanScanId((sPanScan > 0 ? sPanScan : ix) + 0x20);
        }
      }
    }

    vts.skip(8);
    for (int ix = 0; ix < 16; ix++) {
      title.getColors()[ix] = (int) vts.readu32();
    }

    vts.skip(2);
    int programMapOffset = vts.readu16();
    int cellPlaybackOffset = vts.readu16();

    int[] cells = new int[chapters];
    vts.at(offset + programMapOffset);
    for (int ix = 0; ix < chapters; ix++) {
      cells[ix] = vts.readu8();
    }

    for (int ix = 0; ix < chapters; ix++) {
      int current = cells[ix];
      int next = (ix + 1 < chapters ? cells[ix + 1] : cellCount);
      long ms = 0;
      while (current < next) {
        vts.at(offset + cellPlaybackOffset + ((current - 1) * 0x18) + 4);
        ms += vts.readBcdTimeMs();
        current++;
      }
      if (ms > 0 || next != cellCount) {
        title.getChapterTimeMs().add(ms);
      }
    }
  }