private void SerObject(PdfObject obj, ByteBuffer bb, int level, IDictionary <PdfIndirectReference, byte[]> serializedCache) { if (level <= 0) { return; } if (obj == null) { bb.Append("$Lnull"); return; } PdfIndirectReference reference = null; ByteBuffer savedBb = null; if (obj.IsIndirectReference()) { reference = (PdfIndirectReference)obj; byte[] cached = serializedCache.Get(reference); if (cached != null) { bb.Append(cached); return; } else { savedBb = bb; bb = new ByteBuffer(); obj = reference.GetRefersTo(); } } if (obj.IsStream()) { SerDic((PdfDictionary)obj, bb, level - 1, serializedCache); bb.Append("$B"); if (level > 0) { bb.Append(md5.Digest(((PdfStream)obj).GetBytes(false))); } } else { if (obj.IsDictionary()) { SerDic((PdfDictionary)obj, bb, level - 1, serializedCache); } else { if (obj.IsArray()) { SerArray((PdfArray)obj, bb, level - 1, serializedCache); } else { if (obj.IsString()) { bb.Append("$S").Append(obj.ToString()); } else { // TODO specify length for strings, streams, may be names? if (obj.IsName()) { bb.Append("$N").Append(obj.ToString()); } else { bb.Append("$L").Append(obj.ToString()); } } } } } // PdfNull case is also here if (savedBb != null) { serializedCache.Put(reference, bb.ToByteArray()); savedBb.Append(bb.GetInternalBuffer()); } }
/// <summary>Marks object behind wrapper to be saved as indirect.</summary> /// <param name="document">a document the indirect reference will belong to.</param> /// <returns>object itself.</returns> public virtual iText.Kernel.Pdf.PdfObjectWrapper <T> MakeIndirect(PdfDocument document, PdfIndirectReference reference) { GetPdfObject().MakeIndirect(document, reference); return(this); }
protected internal virtual PdfObject CopyObject(PdfObject obj, PdfDocument documentTo, bool allowDuplicating ) { if (obj is PdfIndirectReference) { obj = ((PdfIndirectReference)obj).GetRefersTo(); } if (obj == null) { obj = PdfNull.PDF_NULL; } if (CheckTypeOfPdfDictionary(obj, PdfName.Catalog)) { ILog logger = LogManager.GetLogger(typeof(PdfReader)); logger.Warn(iText.IO.LogMessageConstant.MAKE_COPY_OF_CATALOG_DICTIONARY_IS_FORBIDDEN); obj = PdfNull.PDF_NULL; } PdfIndirectReference indirectReference = obj.GetIndirectReference(); PdfDocument.IndirectRefDescription copiedObjectKey = null; bool tryToFindDuplicate = !allowDuplicating && indirectReference != null; if (tryToFindDuplicate) { copiedObjectKey = new PdfDocument.IndirectRefDescription(indirectReference); PdfIndirectReference copiedIndirectReference = copiedObjects.Get(copiedObjectKey); if (copiedIndirectReference != null) { return(copiedIndirectReference.GetRefersTo()); } } SerializedObjectContent serializedContent = null; if (properties.smartMode && tryToFindDuplicate && !CheckTypeOfPdfDictionary(obj, PdfName.Page)) { serializedContent = smartModeSerializer.SerializeObject(obj); PdfIndirectReference objectRef = smartModeSerializer.GetSavedSerializedObject(serializedContent); if (objectRef != null) { copiedObjects.Put(copiedObjectKey, objectRef); return(objectRef.refersTo); } } PdfObject newObject = obj.NewInstance(); if (indirectReference != null) { if (copiedObjectKey == null) { copiedObjectKey = new PdfDocument.IndirectRefDescription(indirectReference); } PdfIndirectReference indRef = newObject.MakeIndirect(documentTo).GetIndirectReference(); if (serializedContent != null) { smartModeSerializer.SaveSerializedObject(serializedContent, indRef); } copiedObjects.Put(copiedObjectKey, indRef); } newObject.CopyContent(obj, documentTo); return(newObject); }
private void LoadPage(int pageNum) { PdfIndirectReference targetPage = pageRefs[pageNum]; if (targetPage != null) { return; } //if we go here, we have to split PdfPages that contains pageNum int parentIndex = FindPageParent(pageNum); PdfPages parent = parents[parentIndex]; PdfArray kids = parent.GetKids(); if (kids == null) { throw new PdfException(PdfException.InvalidPageStructure1).SetMessageParams(pageNum + 1); } int kidsCount = parent.GetCount(); // we should handle separated pages, it means every PdfArray kids must contain either PdfPage or PdfPages, // mix of PdfPage and PdfPages not allowed. bool findPdfPages = false; // NOTE optimization? when we already found needed index for (int i = 0; i < kids.Size(); i++) { PdfDictionary page = kids.GetAsDictionary(i); // null values not allowed in pages tree. if (page == null) { throw new PdfException(PdfException.InvalidPageStructure1).SetMessageParams(pageNum + 1); } PdfObject pageKids = page.Get(PdfName.Kids); if (pageKids != null) { if (pageKids.IsArray()) { findPdfPages = true; } else { // kids must be of type array throw new PdfException(PdfException.InvalidPageStructure1).SetMessageParams(pageNum + 1); } } } if (findPdfPages) { // handle mix of PdfPage and PdfPages. // handle count property! IList <PdfPages> newParents = new List <PdfPages>(kids.Size()); PdfPages lastPdfPages = null; for (int i = 0; i < kids.Size() && kidsCount > 0; i++) { PdfDictionary pdfPagesObject = kids.GetAsDictionary(i); if (pdfPagesObject.GetAsArray(PdfName.Kids) == null) { // pdfPagesObject is PdfPage // possible if only first kid is PdfPage if (lastPdfPages == null) { lastPdfPages = new PdfPages(parent.GetFrom(), document, parent); kids.Set(i, lastPdfPages.GetPdfObject()); newParents.Add(lastPdfPages); } else { // Only remove from kids if we did not replace the entry with new PdfPages kids.Remove(i); i--; } // decrement count first so that page is not counted twice when moved to lastPdfPages parent.DecrementCount(); lastPdfPages.AddPage(pdfPagesObject); kidsCount--; } else { // pdfPagesObject is PdfPages int from = lastPdfPages == null?parent.GetFrom() : lastPdfPages.GetFrom() + lastPdfPages.GetCount(); lastPdfPages = new PdfPages(from, kidsCount, pdfPagesObject, parent); newParents.Add(lastPdfPages); kidsCount -= lastPdfPages.GetCount(); } } parents.JRemoveAt(parentIndex); for (int i = newParents.Count - 1; i >= 0; i--) { parents.Add(parentIndex, newParents[i]); } // recursive call, to load needed pageRef. // NOTE optimization? add to loadPage startParentIndex. LoadPage(pageNum); } else { int from = parent.GetFrom(); // Possible exception in case kids.getSize() < parent.getCount(). // In any case parent.getCount() has higher priority. // NOTE optimization? when we already found needed index for (int i = 0; i < parent.GetCount(); i++) { PdfDictionary kid = kids.GetAsDictionary(i); // make sure it's a dictionary if (kid != null) { pageRefs[from + i] = kid.GetIndirectReference(); } } } }
public virtual void PrimitivesTest() { String data = "<</Size 70." + "/Value#20 .1" + "/Root 46 0 R" + "/Info 44 0 R" + "/ID[<736f6d652068657820737472696e672>(some simple string )<8C2547D58D4BD2C6F3D32B830BE3259D2>-70.1--0.2]" + "/Name1 --15" + "/Prev ---116.23 >>"; RandomAccessSourceFactory factory = new RandomAccessSourceFactory(); PdfTokenizer tok = new PdfTokenizer(new RandomAccessFileOrArray(factory.CreateSource(data.GetBytes(iText.IO.Util.EncodingUtil.ISO_8859_1 )))); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.StartDic); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Name); PdfName name = new PdfName(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("Size", name.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Number); PdfNumber num = new PdfNumber(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("70.", num.ToString()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Name); name = new PdfName(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("Value ", name.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Number); num = new PdfNumber(tok.GetByteContent()); NUnit.Framework.Assert.AreNotSame("0.1", num.ToString()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Name); name = new PdfName(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("Root", name.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Ref); PdfIndirectReference @ref = new PdfIndirectReference(null, tok.GetObjNr(), tok.GetGenNr()); NUnit.Framework.Assert.AreEqual("46 0 R", @ref.ToString()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Name); name = new PdfName(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("Info", name.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Ref); @ref = new PdfIndirectReference(null, tok.GetObjNr(), tok.GetGenNr()); NUnit.Framework.Assert.AreEqual("44 0 R", @ref.ToString()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Name); name = new PdfName(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("ID", name.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.StartArray); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.String); NUnit.Framework.Assert.AreEqual(tok.IsHexString(), true); PdfString str = new PdfString(tok.GetByteContent(), tok.IsHexString()); NUnit.Framework.Assert.AreEqual("some hex string ", str.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.String); NUnit.Framework.Assert.AreEqual(tok.IsHexString(), false); str = new PdfString(tok.GetByteContent(), tok.IsHexString()); NUnit.Framework.Assert.AreEqual("some simple string ", str.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.String); NUnit.Framework.Assert.AreEqual(tok.IsHexString(), true); str = new PdfString(tok.GetByteContent(), tok.IsHexString()); NUnit.Framework.Assert.AreEqual("\u008C%G\u00D5\u008DK\u00D2\u00C6\u00F3\u00D3+\u0083\u000B\u00E3%\u009D " , str.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Number); num = new PdfNumber(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("-70.1", num.ToString()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Number); num = new PdfNumber(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("-0.2", num.ToString()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.EndArray); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Name); name = new PdfName(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("Name1", name.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Number); num = new PdfNumber(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("0", num.ToString()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Name); name = new PdfName(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("Prev", name.GetValue()); tok.NextValidToken(); NUnit.Framework.Assert.AreEqual(tok.GetTokenType(), PdfTokenizer.TokenType.Number); num = new PdfNumber(tok.GetByteContent()); NUnit.Framework.Assert.AreEqual("-116.23", num.ToString()); }
/// <summary>Marks object to be saved as indirect.</summary> /// <param name="document">a document the indirect reference will belong to.</param> /// <returns>object itself.</returns> public override PdfObject MakeIndirect(PdfDocument document, PdfIndirectReference reference) { return((iText.Kernel.Pdf.PdfNull)base.MakeIndirect(document, reference)); }
protected internal virtual PdfObject SetIndirectReference(PdfIndirectReference indirectReference) { this.indirectReference = indirectReference; return(this); }
/// <summary>Indicates is the object has been set as modified or not.</summary> /// <remarks>Indicates is the object has been set as modified or not. Useful for incremental updates (e.g. appendMode). /// </remarks> /// <returns>true is object has been set as modified, otherwise false.</returns> public virtual bool IsModified() { PdfIndirectReference indirectReference = GetIndirectReference(); return(indirectReference != null && indirectReference.CheckState(MODIFIED)); }
/// <summary>Indicates is the object has been flushed or not.</summary> /// <returns>true is object has been flushed, otherwise false.</returns> public virtual bool IsFlushed() { PdfIndirectReference indirectReference = GetIndirectReference(); return(indirectReference != null && indirectReference.CheckState(FLUSHED)); }
private void SerObject(PdfObject obj, int level, ByteBufferOutputStream bb, IntHashtable serialized) { if (level <= 0) { return; } if (obj == null) { bb.Append("$Lnull"); return; } PdfIndirectReference reference = null; ByteBufferOutputStream savedBb = null; if (obj.IsIndirectReference()) { reference = (PdfIndirectReference)obj; int key = GetCopyObjectKey(obj); if (serialized.ContainsKey(key)) { bb.Append((int)serialized.Get(key)); return; } else { savedBb = bb; bb = new ByteBufferOutputStream(); } } if (obj.IsStream()) { bb.Append("$B"); SerDic((PdfDictionary)obj, level - 1, bb, serialized); if (level > 0) { md5.Reset(); bb.Append(md5.Digest(((PdfStream)obj).GetBytes(false))); } } else { if (obj.IsDictionary()) { SerDic((PdfDictionary)obj, level - 1, bb, serialized); } else { if (obj.IsArray()) { SerArray((PdfArray)obj, level - 1, bb, serialized); } else { if (obj.IsString()) { bb.Append("$S").Append(obj.ToString()); } else { if (obj.IsName()) { bb.Append("$N").Append(obj.ToString()); } else { bb.Append("$L").Append(obj.ToString()); } } } } } if (savedBb != null) { int key = GetCopyObjectKey(reference); if (!serialized.ContainsKey(key)) { serialized.Put(key, CalculateHash(bb.GetBuffer())); } savedBb.Append(bb); } }