/// <summary> /// Reads chunkd from input stream, adds to ChunksList, and returns it. /// If it's skipped, a PngChunkSkipped object is created /// </summary> /// <returns></returns> private AbstractPngChunk ReadChunk(byte[] chunkid, int clen, bool skipforced) { if (clen < 0) { throw new PngjInputException("invalid chunk lenght: " + clen); } // skipChunksByIdSet is created lazyly, if fist IHDR has already been read if (skipChunkIdsSet is null && CurrentChunkGroup > ChunksList.CHUNK_GROUP_0_IDHR) { skipChunkIdsSet = new Dictionary <string, int>(); if (SkipChunkIds is object) { foreach (var id in SkipChunkIds) { skipChunkIdsSet.Add(id, 1); } } } var chunkidstr = ChunkHelper.ToString(chunkid); var critical = ChunkHelper.IsCritical(chunkidstr); var skip = skipforced; if (MaxTotalBytesRead > 0 && clen + offset > MaxTotalBytesRead) { throw new PngjInputException("Maximum total bytes to read exceeeded: " + MaxTotalBytesRead + " offset:" + offset + " clen=" + clen); } // an ancillary chunks can be skipped because of several reasons: if (CurrentChunkGroup > ChunksList.CHUNK_GROUP_0_IDHR && !ChunkHelper.IsCritical(chunkidstr)) { skip = skip || (SkipChunkMaxSize > 0 && clen >= SkipChunkMaxSize) || skipChunkIdsSet.ContainsKey(chunkidstr) || (MaxBytesMetadata > 0 && clen > MaxBytesMetadata - bytesChunksLoaded) || !ChunkHelper.ShouldLoad(chunkidstr, ChunkLoadBehaviour); } AbstractPngChunk pngChunk; if (skip) { PngHelperInternal.SkipBytes(inputStream, clen); PngHelperInternal.ReadInt4(inputStream); // skip - we dont call PngHelperInternal.skipBytes(inputStream, clen + 4) for risk of overflow pngChunk = new PngChunkSkipped(chunkidstr, ImgInfo, clen); } else { var chunk = new ChunkRaw(clen, chunkid, true); _ = chunk.ReadChunkData(inputStream, critical); pngChunk = AbstractPngChunk.Factory(chunk, ImgInfo); if (!pngChunk.Crit) { bytesChunksLoaded += chunk.Len; } } pngChunk.Offset = offset - 8L; chunksList.AppendReadChunk(pngChunk, CurrentChunkGroup); offset += clen + 4L; return(pngChunk); }
public void RtpPacketEncodingTest() { var outpacket = new RtpPacketData(); var rtpPacketDataListRecycler = new ObjectPool <List <RtpPacketData> >(() => new List <RtpPacketData>()); var rtpPacketDataRecycler = new ObjectPool <RtpPacketData>(() => new RtpPacketData()); var ctxFactory = new JpegFrameContextFactory(VideoConstants.VideoBlockSize, VideoConstants.VideoBlockSize); var frameBlockPool = new ObjectPool <FrameBlock>(() => new FrameBlock(ctxFactory)); outpacket.SequenceNumber = 255; outpacket.PayloadType = RtpPayloadType.Audio; Queue <FrameBlock> queue = GetFrameBlockQueue(); var vqc = new VideoQualityController(1); vqc.RemoteSessions = _remoteSessions; var helper = new ChunkHelper(VideoConstants.MaxPayloadSize, frameBlockPool, vqc); // var videoChunkPool = new ObjectPool<ByteStream>(() => new ByteStream(VideoConstants.MaxPayloadSize), bs => bs.Reset()); var chunk = new ByteStream(VideoConstants.MaxPayloadSize); helper.GetNextChunkFromQueue(queue, chunk); outpacket.Payload = chunk.Data; outpacket.PayloadLength = (ushort)chunk.DataLength; var data = new ByteStream(outpacket.BuildPacket()); RtpPacketData inpacket = RtpPacketData.GetPacketsFromData(data, rtpPacketDataListRecycler, rtpPacketDataRecycler)[0]; Assert.AreEqual(outpacket.SequenceNumber, inpacket.SequenceNumber); Assert.AreEqual(RtpPayloadType.Audio, inpacket.PayloadType); Assert.AreEqual(outpacket.PayloadLength, inpacket.PayloadLength); }
void UpdatePlayerVisibleChunks(PlayerChunkLoadState state) { if (state.Entity == null) { return; } state.ChunksToUnload.Clear(); _tempVisList.Clear(); var centerPos = ChunkHelper.GetChunkIdFromCoords(state.Entity.Position); var dim = (WorldOptions.MaxLoadRadius - 1) * 2; ChunkHelper.Spiral(dim, dim, (x, y) => { _tempVisList.Add(centerPos.Add(x, 0, y)); }); foreach (var c in _tempVisList) { if (state.SentChunks.Contains(c) || state.SendQueue.Contains(c) || state.LoadGenQueue.Contains(c)) { continue; } state.LoadGenQueue.Enqueue(c); } var maxLoadDistance = WorldOptions.ChunkUnloadDistance * WorldOptions.ChunkUnloadDistance; foreach (var c in state.SentChunks) { var dist = Int3.SquareDistanceFlat(centerPos, c); if (dist > maxLoadDistance) { state.ChunksToUnload.Add(c); } } }
public override void ParseFromRaw(ChunkRaw c) { int nullsep = -1; var array = c.Data; int length = array.Length; for (int i = 0; i < length; i++) // look for first zero { if (array[i] != 0) { continue; } nullsep = i; break; } if (nullsep < 0 || nullsep > length - 2) { throw new System.Exception("bad zTXt chunk: no separator found"); } key = ChunkHelper.ToString(array, 0, nullsep); int compmet = (int)array[nullsep + 1]; if (compmet != 0) { throw new System.Exception("bad zTXt chunk: unknown compression method"); } byte[] uncomp = ChunkHelper.CompressBytes(array, nullsep + 2, length - nullsep - 2, false); // uncompress val = ChunkHelper.ToString(uncomp); }
public void ChunkHelperTest() { Queue <FrameBlock> queue = GetFrameBlockQueue(); int initialLength = queue.Count; var ctxFactory = new JpegFrameContextFactory(VideoConstants.VideoBlockSize, VideoConstants.VideoBlockSize); var videoChunkPool = new ObjectPool <ByteStream>(() => new ByteStream(VideoConstants.MaxPayloadSize), bs => bs.Reset()); var frameBlockPool = new ObjectPool <FrameBlock>(() => new FrameBlock(ctxFactory)); var vqc = new VideoQualityController(1); vqc.RemoteSessions = _remoteSessions; var helper = new ChunkHelper(VideoConstants.MaxPayloadSize, frameBlockPool, vqc); var buffer = videoChunkPool.GetNext(); Assert.IsTrue(helper.GetNextChunkFromQueue(queue, buffer)); Assert.IsTrue(queue.Count < initialLength); var blocks = helper.ParseChunk(buffer, 1); Assert.AreEqual(queue.Count + blocks.Length, initialLength); Assert.IsTrue(blocks.Length > 0); foreach (var block in blocks) { Assert.AreEqual(block.BlockX, block.BlockY); Assert.AreEqual(block.BlockX + 1, block.EncodedStream.Length); } }
protected override CSharpCodeWritingScope BuildClassDeclaration(CSharpCodeWriter writer) { // Grab the last model chunk so it gets intellisense. var modelChunk = ChunkHelper.GetModelChunk(Context.ChunkTreeBuilder.ChunkTree); Model = modelChunk != null ? modelChunk.ModelType : _defaultModel; // If there were any model chunks then we need to modify the class declaration signature. if (modelChunk != null) { writer.Write(string.Format(CultureInfo.InvariantCulture, "public class {0} : ", Context.ClassName)); var modelVisitor = new ModelChunkVisitor(writer, Context); // This generates the base class signature modelVisitor.Accept(modelChunk); writer.WriteLine(); return(new CSharpCodeWritingScope(writer)); } else { return(base.BuildClassDeclaration(writer)); } }
/// <summary> /// Reads chunks before first IDAT. Position before: after IDHR (crc included) /// Position after: just after the first IDAT chunk id Returns length of first /// IDAT chunk , -1 if not found /// </summary> /// private void ReadFirstChunks() { if (!FirstChunksNotYetRead()) { return; } var clen = 0; var found = false; var chunkid = new byte[4]; // it's important to reallocate in each CurrentChunkGroup = ChunksList.CHUNK_GROUP_1_AFTERIDHR; while (!found) { clen = PngHelperInternal.ReadInt4(inputStream); offset += 4; if (clen < 0) { break; } PngHelperInternal.ReadBytes(inputStream, chunkid, 0, 4); offset += 4; if (PngCsUtils.arraysEqual4(chunkid, Hjg.Pngcs.Chunks.ChunkHelper.b_IDAT)) { found = true; CurrentChunkGroup = ChunksList.CHUNK_GROUP_4_IDAT; // add dummy idat chunk to list chunksList.AppendReadChunk(new PngChunkIDAT(ImgInfo, clen, offset - 8), CurrentChunkGroup); break; } else if (PngCsUtils.arraysEqual4(chunkid, Hjg.Pngcs.Chunks.ChunkHelper.b_IEND)) { throw new PngjInputException("END chunk found before image data (IDAT) at offset=" + offset); } var chunkids = ChunkHelper.ToString(chunkid); if (chunkids.Equals(ChunkHelper.PLTE, System.StringComparison.Ordinal)) { CurrentChunkGroup = ChunksList.CHUNK_GROUP_2_PLTE; } ReadChunk(chunkid, clen, false); if (chunkids.Equals(ChunkHelper.PLTE, System.StringComparison.Ordinal)) { CurrentChunkGroup = ChunksList.CHUNK_GROUP_3_AFTERPLTE; } } var idatLen = found ? clen : -1; if (idatLen < 0) { throw new PngjInputException("first idat chunk not found!"); } iIdatCstream = new PngIDatChunkInputStream(inputStream, idatLen, offset); idatIstream = new ZlibInputStream(iIdatCstream, true); }
/// <summary> /// Reads chunks before first IDAT. Position before: after IDHR (crc included) /// Position after: just after the first IDAT chunk id Returns length of first /// IDAT chunk , -1 if not found /// </summary> /// void ReadFirstChunks() { if (!FirstChunksNotYetRead()) { return; } int clen = 0; bool found = false; byte[] chunkid = new byte[4]; // it's important to reallocate in each this.CurrentChunkGroup = ChunksList.CHUNK_GROUP_1_AFTERIDHR; while (!found) { clen = PngHelperInternal.ReadInt4(inputStream); offset += 4; if (clen < 0) { break; } PngHelperInternal.ReadBytes(inputStream, chunkid, 0, 4); offset += 4; if (PngCsUtils.arraysEqual4(chunkid, Pngcs.Chunks.ChunkHelper.b_IDAT)) { found = true; this.CurrentChunkGroup = ChunksList.CHUNK_GROUP_4_IDAT; // add dummy idat chunk to list chunksList.AppendReadChunk(new PngChunkIDAT(ImgInfo, clen, offset - 8), CurrentChunkGroup); break; } else if (PngCsUtils.arraysEqual4(chunkid, Pngcs.Chunks.ChunkHelper.b_IEND)) { throw new PngjInputException("END chunk found before image data (IDAT) at offset=" + offset); } string chunkids = ChunkHelper.ToString(chunkid); if (chunkids.Equals(ChunkHelper.PLTE)) { this.CurrentChunkGroup = ChunksList.CHUNK_GROUP_2_PLTE; } ReadChunk(chunkid, clen, false); if (chunkids.Equals(ChunkHelper.PLTE)) { this.CurrentChunkGroup = ChunksList.CHUNK_GROUP_3_AFTERPLTE; } } int idatLen = found ? clen : -1; if (idatLen < 0) { throw new PngjInputException("first idat chunk not found!"); } iIdatCstream = new PngIDatChunkInputStream(inputStream, idatLen, offset); idatIstream = ZlibStreamFactory.createZlibInputStream(iIdatCstream, true); if (!crcEnabled) { iIdatCstream.DisableCrcCheck(); } }
public void ReadFirstChunks() { if (!FirstChunksNotYetRead()) { return; } int num = 0; bool flag = false; byte[] array = new byte[4]; CurrentChunkGroup = 1; while (!flag) { num = PngHelperInternal.ReadInt4(inputStream); offset += 4L; if (num < 0) { break; } PngHelperInternal.ReadBytes(inputStream, array, 0, 4); offset += 4L; if (PngCsUtils.arraysEqual4(array, ChunkHelper.b_IDAT)) { flag = true; CurrentChunkGroup = 4; chunksList.AppendReadChunk(new PngChunkIDAT(ImgInfo, num, offset - 8), CurrentChunkGroup); break; } if (PngCsUtils.arraysEqual4(array, ChunkHelper.b_IEND)) { throw new PngjInputException("END chunk found before image data (IDAT) at offset=" + offset.ToString()); } string text = ChunkHelper.ToString(array); if (text.Equals("PLTE")) { CurrentChunkGroup = 2; } ReadChunk(array, num, skipforced: false); if (text.Equals("PLTE")) { CurrentChunkGroup = 3; } } int num2 = flag ? num : (-1); if (num2 < 0) { throw new PngjInputException("first idat chunk not found!"); } iIdatCstream = new PngIDatChunkInputStream(inputStream, num2, offset); idatIstream = ZlibStreamFactory.createZlibInputStream(iIdatCstream, leaveOpen: true); if (!crcEnabled) { iIdatCstream.DisableCrcCheck(); } }
/// <summary> Creates an empty raw chunk </summary> internal ChunkRaw(int length, string idb, bool alloc) { this.Id = idb; this.IdBytes = ChunkHelper.ToBytes(Id); this.Data = null; this.crcval = 0; this.Len = length; if (alloc) { AllocData(); } }
public PngChunk ReadChunk(byte[] chunkid, int clen, bool skipforced) { if (clen < 0) { throw new PngjInputException("invalid chunk lenght: " + clen.ToString()); } if (skipChunkIdsSet == null && CurrentChunkGroup > 0) { skipChunkIdsSet = new Dictionary <string, int>(); if (SkipChunkIds != null) { string[] skipChunkIds = SkipChunkIds; foreach (string key in skipChunkIds) { skipChunkIdsSet.Add(key, 1); } } } string text = ChunkHelper.ToString(chunkid); PngChunk pngChunk = null; bool flag = ChunkHelper.IsCritical(text); bool flag2 = skipforced; if (MaxTotalBytesRead > 0 && clen + offset > MaxTotalBytesRead) { throw new PngjInputException("Maximum total bytes to read exceeeded: " + MaxTotalBytesRead.ToString() + " offset:" + offset.ToString() + " clen=" + clen.ToString()); } if (CurrentChunkGroup > 0 && !ChunkHelper.IsCritical(text)) { flag2 = (flag2 || (SkipChunkMaxSize > 0 && clen >= SkipChunkMaxSize) || skipChunkIdsSet.ContainsKey(text) || (MaxBytesMetadata > 0 && clen > MaxBytesMetadata - bytesChunksLoaded) || !ChunkHelper.ShouldLoad(text, ChunkLoadBehaviour)); } if (flag2) { PngHelperInternal.SkipBytes(inputStream, clen); PngHelperInternal.ReadInt4(inputStream); pngChunk = new PngChunkSkipped(text, ImgInfo, clen); } else { ChunkRaw chunkRaw = new ChunkRaw(clen, chunkid, alloc: true); chunkRaw.ReadChunkData(inputStream, crcEnabled | flag); pngChunk = PngChunk.Factory(chunkRaw, ImgInfo); if (!pngChunk.Crit) { bytesChunksLoaded += chunkRaw.Length; } } pngChunk.Offset = offset - 8; chunksList.AppendReadChunk(pngChunk, CurrentChunkGroup); offset += (long)clen + 4L; return(pngChunk); }
void CreateInitialSendQueue(PlayerChunkLoadState state) { Vector3 spawnPoint = ServerPlayerEntityManager.Instance.GetLastSavedPosition(state.Client); var centerChunk = ChunkHelper.GetChunkIdFromCoords(spawnPoint); var queue = state.LoadGenQueue; var dim = (WorldOptions.ChunkLoadRadius - 1) * 2; ChunkHelper.Spiral(dim, dim, (x, z) => { queue.Enqueue(centerChunk.Add(x, 0, z)); }); }
/// <summary>Queues the chunk at the writer</summary> /// <param name="chunk">Chunk, ready for write</param> /// <param name="lazyOverwrite">Ovewrite lazily equivalent chunks</param> /// <remarks>Warning: the overwriting applies to equivalent chunks, see <c>ChunkPredicateEquiv</c> /// and will only make sense for queued (not yet writen) chunks /// </remarks> public void QueueChunk(PngChunk chunk, bool lazyOverwrite) { ChunksListForWrite cl = GetChunkListW(); if (ReadOnly) { throw new PngjException("cannot set chunk : readonly metadata"); } if (lazyOverwrite) { ChunkHelper.TrimList(cl.GetQueuedChunks(), new ChunkPredicateEquiv(chunk)); } cl.Queue(chunk); }
void LoadGenWorldOrigin() { var lg = ServerLandGenerator.Instance; lg.ClearQueue(); lg.ImmediateMode = true; var dim = (WorldOptions.ChunkLoadRadius - 1) * 2; ChunkHelper.Spiral(dim, dim, GenOrLoad); ChunkHelper.Spiral(dim, dim, (x, y) => { _keepaliveChunks.Add(new Int3(x, 0, y)); }); DebugOutput.LogFormat("Initial world generation. Chunks total: {0}, to generate: {1}", dim * dim, lg.QueueCount); lg.TryStartGeneration(); lg.ImmediateMode = false; }
/// <summary> /// Activates when a new state is set for the draw chunk borders event /// </summary> /// <param name="newState">The new state of the option</param> public void DrawBordersChange(bool newState) { if (newState == false) { // Clear all lines ChunkDrawer.Instance.ClearChunkBorders(); } else { // Add all chunks to the drawing list ChunkHelper.LoopOverChunks(loadedChunks, (Chunk chunk) => { ChunkDrawer.Instance.DrawChunkBorder(chunk); }); } }
public override ChunkRaw CreateRawChunk() { if (key.Length == 0) { throw new System.Exception("Text chunk key must be non empty"); } var ba = new System.IO.MemoryStream(); ChunkHelper.WriteBytesToStream(ba, ChunkHelper.ToBytes(key)); ba.WriteByte(0); // separator ba.WriteByte(0); // compression method: 0 byte[] textbytes = ChunkHelper.CompressBytes(ChunkHelper.ToBytes(val), true); ChunkHelper.WriteBytesToStream(ba, textbytes); byte[] b = ba.ToArray(); ChunkRaw chunk = CreateEmptyChunk(b.Length, false); chunk.Data = b; return(chunk); }
/// <summary> /// copy chunks from reader - copy_mask : see ChunksToWrite.COPY_XXX /// If we are after idat, only considers those chunks after IDAT in PngReader /// TODO: this should be more customizable /// </summary> /// private void CopyChunks(PngReader reader, int copy_mask, bool onlyAfterIdat) { bool idatDone = CurrentChunkGroup >= ChunksList.CHUNK_GROUP_4_IDAT; if (onlyAfterIdat && reader.CurrentChunkGroup < ChunksList.CHUNK_GROUP_6_END) throw new PngjException("tried to copy last chunks but reader has not ended"); foreach (PngChunk chunk in reader.GetChunksList().GetChunks()) { int group = chunk.ChunkGroup; if (group < ChunksList.CHUNK_GROUP_4_IDAT && idatDone) continue; bool copy = false; if (chunk.Crit) { if (chunk.Id.Equals(ChunkHelper.PLTE, StringComparison.InvariantCultureIgnoreCase)) { if (ImgInfo.Indexed && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_PALETTE)) copy = true; if (!ImgInfo.Greyscale && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL)) copy = true; } } else { // ancillary bool text = chunk is PngChunkTextVar; bool safe = chunk.Safe; // notice that these if are not exclusive if (ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL)) copy = true; if (safe && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL_SAFE)) copy = true; if (chunk.Id.Equals(ChunkHelper.tRNS, StringComparison.InvariantCultureIgnoreCase) && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_TRANSPARENCY)) copy = true; if (chunk.Id.Equals(ChunkHelper.pHYs, StringComparison.InvariantCultureIgnoreCase) && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_PHYS)) copy = true; if (text && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_TEXTUAL)) copy = true; if (ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALMOSTALL) && !(ChunkHelper.IsUnknown(chunk) || text || chunk.Id.Equals(ChunkHelper.hIST, StringComparison.InvariantCultureIgnoreCase) || chunk.Id.Equals(ChunkHelper.tIME, StringComparison.InvariantCultureIgnoreCase))) copy = true; if (chunk is PngChunkSkipped) copy = false; } if (copy) chunksList.Queue(PngChunk.CloneChunk(chunk, ImgInfo)); } }
public ProceduralLevel(LevelGraph graph, LevelGeneratorPreset preset, bool setIsStatic) { //IMPORTANT, multiply with the door size. Doors require the chunk to be aligned on the grid on GENERATION time //Ensure, that chunks are on the grid, since the doors align to the grid regardless of the chunk position, which //Will result in shifted doorpositions on repositioning the chunks tmpChunkPos = DoorDefinition.GlobalSize * -5000f; tmpChunkStep = DoorDefinition.GlobalSize * -50f; isGenerating = true; this.preset = preset; this.hallwayTiling = preset.HallwayTiling; this.distance = preset.RoomDistance; this.rootnode = graph.Rootnode; this.spacing = preset.Spacing; this.isSeparate = preset.IsSeparateRooms; this.hallwayMaterials = preset.HallwayMaterials; this.helper = new ChunkHelper(preset); this.debugData = new DebugData(); this.chunkInstantiator = ChunkInstantiator.Instance; this.hallwayMeta = new List <HallwayMeta> (); this.positionMeta = new List <RoomTransformation>(); this.levelMetadata = new LevelMetadata(); this.setIsStatic = setIsStatic; GenerateLevel(graph); if (!isConstraintError) { ApplyTransformation(); CreateHallways(); } else { HandleRollback(); } helper.CleanUp(); ChunkInstantiator.RemoveManualProperties(); isGenerating = false; }
public bool Matches(PngChunk c) { return(ChunkHelper.Equivalent(c, chunk)); }
/// <summary> Sets profile name and profile </summary> /// <param name="name">profile name </param> /// <param name="profile">profile (latin1 string)</param> public void SetProfileNameAndContent(string name, string profile) => SetProfileNameAndContent(name, ChunkHelper.ToBytes(profileName));
/// <summary> /// copy chunks from reader - copy_mask : see ChunksToWrite.COPY_XXX /// If we are after idat, only considers those chunks after IDAT in PngReader /// TODO: this should be more customizable /// </summary> /// private void CopyChunks(PngReader reader, int copy_mask, bool onlyAfterIdat) { if (reader is null) { throw new ArgumentNullException(nameof(reader)); } var idatDone = CurrentChunkGroup >= ChunksList.CHUNK_GROUP_4_IDAT; if (onlyAfterIdat && reader.CurrentChunkGroup < ChunksList.CHUNK_GROUP_6_END) { throw new PngjException("tried to copy last chunks but reader has not ended"); } foreach (var chunk in reader.GetChunksList().Chunks) { var group = chunk.ChunkGroup; if (group < ChunksList.CHUNK_GROUP_4_IDAT && idatDone) { continue; } var copy = false; if (chunk.Crit) { if (chunk.Id.Equals(ChunkHelper.PLTE, StringComparison.Ordinal)) { if (ImgInfo.Indexed && ChunkHelper.MaskMatch(copy_mask, ChunkCopyBehaviour.COPY_PALETTE)) { copy = true; } if (!ImgInfo.Greyscale && ChunkHelper.MaskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL)) { copy = true; } } } else { // ancillary var text = (chunk is AbstractPngChunkTextVar); var safe = chunk.Safe; // notice that these if are not exclusive if (ChunkHelper.MaskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL)) { copy = true; } if (safe && ChunkHelper.MaskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL_SAFE)) { copy = true; } if (chunk.Id.Equals(ChunkHelper.tRNS, StringComparison.Ordinal) && ChunkHelper.MaskMatch(copy_mask, ChunkCopyBehaviour.COPY_TRANSPARENCY)) { copy = true; } if (chunk.Id.Equals(ChunkHelper.pHYs, StringComparison.Ordinal) && ChunkHelper.MaskMatch(copy_mask, ChunkCopyBehaviour.COPY_PHYS)) { copy = true; } if (text && ChunkHelper.MaskMatch(copy_mask, ChunkCopyBehaviour.COPY_TEXTUAL)) { copy = true; } if (((ChunkHelper.MaskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALMOSTALL) && !ChunkHelper.IsUnknown(chunk)) || text || chunk.Id.Equals(ChunkHelper.hIST, StringComparison.Ordinal) || chunk.Id.Equals(ChunkHelper.tIME, StringComparison.Ordinal))) { copy = true; } if (chunk is PngChunkSkipped) { copy = false; } } if (copy) { _ = chunksList.Queue(AbstractPngChunk.CloneChunk(chunk, ImgInfo)); } } }
public PngReader(Stream inputStream, string filename) { this.filename = ((filename == null) ? "" : filename); this.inputStream = inputStream; chunksList = new ChunksList(null); metadata = new PngMetadata(chunksList); offset = 0L; CurrentChunkGroup = -1; ShouldCloseStream = true; MaxBytesMetadata = 5242880L; MaxTotalBytesRead = 209715200L; SkipChunkMaxSize = 2097152; SkipChunkIds = new string[1] { "fdAT" }; ChunkLoadBehaviour = ChunkLoadBehaviour.LOAD_CHUNK_ALWAYS; byte[] array = new byte[8]; PngHelperInternal.ReadBytes(inputStream, array, 0, array.Length); offset += array.Length; if (!PngCsUtils.arraysEqual(array, PngHelperInternal.PNG_ID_SIGNATURE)) { throw new PngjInputException("Bad PNG signature"); } CurrentChunkGroup = 0; int num = PngHelperInternal.ReadInt4(inputStream); offset += 4L; if (num != 13) { throw new Exception("IDHR chunk len != 13 ?? " + num.ToString()); } byte[] array2 = new byte[4]; PngHelperInternal.ReadBytes(inputStream, array2, 0, 4); if (!PngCsUtils.arraysEqual4(array2, ChunkHelper.b_IHDR)) { throw new PngjInputException("IHDR not found as first chunk??? [" + ChunkHelper.ToString(array2) + "]"); } offset += 4L; PngChunkIHDR pngChunkIHDR = (PngChunkIHDR)ReadChunk(array2, num, skipforced: false); bool alpha = (pngChunkIHDR.Colormodel & 4) != 0; bool palette = (pngChunkIHDR.Colormodel & 1) != 0; bool grayscale = pngChunkIHDR.Colormodel == 0 || pngChunkIHDR.Colormodel == 4; ImgInfo = new ImageInfo(pngChunkIHDR.Cols, pngChunkIHDR.Rows, pngChunkIHDR.Bitspc, alpha, grayscale, palette); rowb = new byte[ImgInfo.BytesPerRow + 1]; rowbprev = new byte[rowb.Length]; rowbfilter = new byte[rowb.Length]; interlaced = (pngChunkIHDR.Interlaced == 1); deinterlacer = (interlaced ? new PngDeinterlacer(ImgInfo) : null); if (pngChunkIHDR.Filmeth != 0 || pngChunkIHDR.Compmeth != 0 || (pngChunkIHDR.Interlaced & 0xFFFE) != 0) { throw new PngjInputException("compmethod or filtermethod or interlaced unrecognized"); } if (pngChunkIHDR.Colormodel < 0 || pngChunkIHDR.Colormodel > 6 || pngChunkIHDR.Colormodel == 1 || pngChunkIHDR.Colormodel == 5) { throw new PngjInputException("Invalid colormodel " + pngChunkIHDR.Colormodel.ToString()); } if (pngChunkIHDR.Bitspc != 1 && pngChunkIHDR.Bitspc != 2 && pngChunkIHDR.Bitspc != 4 && pngChunkIHDR.Bitspc != 8 && pngChunkIHDR.Bitspc != 16) { throw new PngjInputException("Invalid bit depth " + pngChunkIHDR.Bitspc.ToString()); } }
internal ChunkRaw(int length, byte[] idbytes, bool alloc) : this(length, ChunkHelper.ToString(idbytes), alloc) { }
/// <summary> Sets profile name and profile </summary> /// <param name="name">profile name </param> /// <param name="profile">profile (uncompressed)</param> public void SetProfileNameAndContent(string name, byte[] profile) { profileName = name; compressedProfile = ChunkHelper.CompressBytes(profile, true); }
/// <summary> This uncompresses the string! </summary> public byte[] GetProfile() => ChunkHelper.CompressBytes(compressedProfile, false);
/// <summary> /// Constructs a PNGReader objet from a opened Stream /// </summary> /// <remarks>The constructor reads the signature and first chunk (IDHR)<seealso cref="FileHelper.CreatePngReader(string)"/> /// </remarks> /// /// <param name="inputStream"></param> /// <param name="filename">Optional, can be the filename or a description.</param> public PngReader(Stream inputStream, String filename) { this.filename = (filename == null) ? "" : filename; this.inputStream = inputStream; this.chunksList = new ChunksList(null); this.metadata = new PngMetadata(chunksList); this.offset = 0; // set default options this.CurrentChunkGroup = -1; this.ShouldCloseStream = true; this.MaxBytesMetadata = 5 * 1024 * 1024; this.MaxTotalBytesRead = 200 * 1024 * 1024; // 200MB this.SkipChunkMaxSize = 2 * 1024 * 1024; this.SkipChunkIds = new string[] { "fdAT" }; this.ChunkLoadBehaviour = Hjg.Pngcs.Chunks.ChunkLoadBehaviour.LOAD_CHUNK_ALWAYS; // starts reading: signature byte[] pngid = new byte[8]; PngHelperInternal.ReadBytes(inputStream, pngid, 0, pngid.Length); offset += pngid.Length; if (!PngCsUtils.arraysEqual(pngid, PngHelperInternal.PNG_ID_SIGNATURE)) { throw new PngjInputException("Bad PNG signature"); } CurrentChunkGroup = ChunksList.CHUNK_GROUP_0_IDHR; // reads first chunk IDHR int clen = PngHelperInternal.ReadInt4(inputStream); offset += 4; if (clen != 13) { throw new Exception("IDHR chunk len != 13 ?? " + clen); } byte[] chunkid = new byte[4]; PngHelperInternal.ReadBytes(inputStream, chunkid, 0, 4); if (!PngCsUtils.arraysEqual4(chunkid, ChunkHelper.b_IHDR)) { throw new PngjInputException("IHDR not found as first chunk??? [" + ChunkHelper.ToString(chunkid) + "]"); } offset += 4; PngChunkIHDR ihdr = (PngChunkIHDR)ReadChunk(chunkid, clen, false); bool alpha = (ihdr.Colormodel & 0x04) != 0; bool palette = (ihdr.Colormodel & 0x01) != 0; bool grayscale = (ihdr.Colormodel == 0 || ihdr.Colormodel == 4); // creates ImgInfo and imgLine, and allocates buffers ImgInfo = new ImageInfo(ihdr.Cols, ihdr.Rows, ihdr.Bitspc, alpha, grayscale, palette); rowb = new byte[ImgInfo.BytesPerRow + 1]; rowbprev = new byte[rowb.Length]; rowbfilter = new byte[rowb.Length]; interlaced = ihdr.Interlaced == 1; deinterlacer = interlaced ? new PngDeinterlacer(ImgInfo) : null; // some checks if (ihdr.Filmeth != 0 || ihdr.Compmeth != 0 || (ihdr.Interlaced & 0xFFFE) != 0) { throw new PngjInputException("compmethod or filtermethod or interlaced unrecognized"); } if (ihdr.Colormodel < 0 || ihdr.Colormodel > 6 || ihdr.Colormodel == 1 || ihdr.Colormodel == 5) { throw new PngjInputException("Invalid colormodel " + ihdr.Colormodel); } if (ihdr.Bitspc != 1 && ihdr.Bitspc != 2 && ihdr.Bitspc != 4 && ihdr.Bitspc != 8 && ihdr.Bitspc != 16) { throw new PngjInputException("Invalid bit depth " + ihdr.Bitspc); } }
/// <summary> /// Writes a new file with several text chunks, reads it back and compares /// </summary> public static void test() { Dictionary <string, string> texts = new Dictionary <String, String>(); texts.Add("key1", "val"); texts.Add("empty1", ""); texts.Add("unicode1", "Hernán"); texts.Add("zero1", "Hola\0chau"); texts.Add("key2", "val"); texts.Add("empty2", ""); texts.Add("unicode2", "Hernán"); texts.Add("zero2", "Hola\0chau"); texts.Add("key3", "val"); texts.Add("empty3", ""); texts.Add("unicode3", "Hernán"); texts.Add("zero3", "Hola\0chau"); texts.Add("nolatin1", "Hernán\u1230"); String suffix = "text"; PngWriter png = TestsHelper.prepareFileTmp(suffix); png.GetMetadata().SetText("key1", texts["key1"], false, false); png.GetMetadata().SetText("key2", texts["key2"], true, false); png.GetMetadata().SetText("key3", texts["key3"], true, true); png.GetMetadata().SetText("empty1", texts["empty1"], false, false); png.GetMetadata().SetText("empty2", texts["empty2"], true, false); png.GetMetadata().SetText("empty3", texts["empty3"], true, true); png.GetMetadata().SetText("unicode1", texts["unicode1"], false, false); png.GetMetadata().SetText("unicode2", texts["unicode2"], true, false); png.GetMetadata().SetText("unicode3", texts["unicode3"], true, true); png.GetMetadata().SetText("nolatin1", texts["nolatin1"], false, false); png.GetMetadata().SetText("zero1", texts["zero1"], false, false); png.GetMetadata().SetText("zero2", texts["zero2"], true, false); png.GetMetadata().SetText("zero3", texts["zero3"], true, true); TestsHelper.endFileTmp(png); PngReader pngr = TestsHelper.getReaderTmp(suffix); pngr.ReadSkippingAllRows(); int ok = 0; foreach (PngChunk c in pngr.GetChunksList().GetChunks()) { if (!ChunkHelper.IsText(c)) { continue; } ok++; PngChunkTextVar ct = (PngChunkTextVar)c; String key = ct.GetKey(); String val = ct.GetVal(); Console.WriteLine(c.Id + " chunk. Key:" + key + " val='" + val + "'"); if (!val.Equals(texts[key])) { Console.WriteLine("ERROR: expected '" + texts[key] + "' got '" + val + "' key=" + key + " id=" + c.Id); } } if (ok != texts.Keys.Count) { throw new Exception("number of text chunks does not coincide"); } Console.WriteLine("done"); }
public void CopyChunks(PngReader reader, int copy_mask, bool onlyAfterIdat) { bool flag = CurrentChunkGroup >= 4; if (onlyAfterIdat && reader.CurrentChunkGroup < 6) { throw new PngjException("tried to copy last chunks but reader has not ended"); } foreach (PngChunk chunk in reader.GetChunksList().GetChunks()) { if (chunk.ChunkGroup >= 4 || !flag) { bool flag2 = false; if (chunk.Crit) { if (chunk.Id.Equals("PLTE")) { if (ImgInfo.Indexed && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_PALETTE)) { flag2 = true; } if (!ImgInfo.Greyscale && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL)) { flag2 = true; } } } else { bool flag3 = chunk is PngChunkTextVar; bool safe = chunk.Safe; if (ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL)) { flag2 = true; } if (safe && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALL_SAFE)) { flag2 = true; } if (chunk.Id.Equals("tRNS") && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_TRANSPARENCY)) { flag2 = true; } if (chunk.Id.Equals("pHYs") && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_PHYS)) { flag2 = true; } if (flag3 && ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_TEXTUAL)) { flag2 = true; } if (ChunkHelper.maskMatch(copy_mask, ChunkCopyBehaviour.COPY_ALMOSTALL) && !(ChunkHelper.IsUnknown(chunk) | flag3) && !chunk.Id.Equals("hIST") && !chunk.Id.Equals("tIME")) { flag2 = true; } if (chunk is PngChunkSkipped) { flag2 = false; } } if (flag2) { chunksList.Queue(PngChunk.CloneChunk(chunk, ImgInfo)); } } } }
public string GetProfileAsString() => ChunkHelper.ToString(GetProfile());