protected internal virtual void CheckResources(PdfDictionary resources) { if (resources == null) { return; } PdfDictionary xObjects = resources.GetAsDictionary(PdfName.XObject); PdfDictionary shadings = resources.GetAsDictionary(PdfName.Shading); PdfDictionary patterns = resources.GetAsDictionary(PdfName.Pattern); if (xObjects != null) { foreach (PdfObject xObject in xObjects.Values()) { PdfStream xObjStream = (PdfStream)xObject; PdfObject subtype = null; bool isFlushed = xObjStream.IsFlushed(); if (!isFlushed) { subtype = xObjStream.Get(PdfName.Subtype); } if (PdfName.Image.Equals(subtype) || isFlushed) { // if flushed still may be need to check colorspace in given context CheckImage(xObjStream, resources.GetAsDictionary(PdfName.ColorSpace)); } else { if (PdfName.Form.Equals(subtype)) { CheckFormXObject(xObjStream); } } } } if (shadings != null) { foreach (PdfObject shading in shadings.Values()) { PdfDictionary shadingDict = (PdfDictionary)shading; if (!IsAlreadyChecked(shadingDict)) { CheckColorSpace(PdfColorSpace.MakeColorSpace(shadingDict.Get(PdfName.ColorSpace)), resources.GetAsDictionary (PdfName.ColorSpace), true, null); } } } if (patterns != null) { foreach (PdfObject p in patterns.Values()) { if (p.IsStream()) { PdfStream pStream = (PdfStream)p; if (!IsAlreadyChecked(pStream)) { CheckResources(pStream.GetAsDictionary(PdfName.Resources)); } } } } }
private void PopulateSignatureNames() { if (acroForm == null) { return; } IList <Object[]> sorter = new List <Object[]>(); foreach (KeyValuePair <String, PdfFormField> entry in acroForm.GetFormFields()) { PdfFormField field = entry.Value; PdfDictionary merged = field.GetPdfObject(); if (!PdfName.Sig.Equals(merged.Get(PdfName.FT))) { continue; } PdfDictionary v = merged.GetAsDictionary(PdfName.V); if (v == null) { continue; } PdfString contents = v.GetAsString(PdfName.Contents); if (contents == null) { continue; } else { contents.MarkAsUnencryptedObject(); } PdfArray ro = v.GetAsArray(PdfName.ByteRange); if (ro == null) { continue; } int rangeSize = ro.Size(); if (rangeSize < 2) { continue; } int length = ro.GetAsNumber(rangeSize - 1).IntValue() + ro.GetAsNumber(rangeSize - 2).IntValue(); sorter.Add(new Object[] { entry.Key, new int[] { length, 0 } }); } JavaCollectionsUtil.Sort(sorter, new SignatureUtil.SorterComparator()); if (sorter.Count > 0) { try { if (((int[])sorter[sorter.Count - 1][1])[0] == document.GetReader().GetFileLength()) { totalRevisions = sorter.Count; } else { totalRevisions = sorter.Count + 1; } } catch (System.IO.IOException) { } // TODO: add exception handling (at least some logger) for (int k = 0; k < sorter.Count; ++k) { Object[] objs = sorter[k]; String name = (String)objs[0]; int[] p = (int[])objs[1]; p[1] = k + 1; sigNames.Put(name, p); orderedSignatureNames.Add(name); } } }
private static PdfDictionary CopyObject(PdfDictionary source, PdfDictionary destPage, bool parentChangePg, StructureTreeCopier.StructElemCopyingParams copyingParams) { PdfDictionary copied; if (copyingParams.IsCopyFromDestDocument()) { //TODO: detect wether object is needed to be cloned at all copied = source.Clone(ignoreKeysForClone); if (source.IsIndirect()) { copied.MakeIndirect(copyingParams.GetToDocument()); } PdfDictionary pg = source.GetAsDictionary(PdfName.Pg); if (pg != null) { if (copyingParams.IsCopyFromDestDocument()) { if (pg != destPage) { copied.Put(PdfName.Pg, destPage); parentChangePg = true; } else { parentChangePg = false; } } } } else { copied = source.CopyTo(copyingParams.GetToDocument(), ignoreKeysForCopy, true); PdfDictionary obj = source.GetAsDictionary(PdfName.Obj); if (obj != null) { // Link annotations could be not added to the toDocument, so we need to identify this case. // When obj.copyTo is called, and annotation was already copied, we would get this already created copy. // If it was already copied and added, /P key would be set. Otherwise /P won't be set. obj = obj.CopyTo(copyingParams.GetToDocument(), JavaUtil.ArraysAsList(PdfName.P), false); copied.Put(PdfName.Obj, obj); } PdfDictionary nsDict = source.GetAsDictionary(PdfName.NS); if (nsDict != null) { PdfDictionary copiedNsDict = CopyNamespaceDict(nsDict, copyingParams); copied.Put(PdfName.NS, copiedNsDict); } PdfDictionary pg = source.GetAsDictionary(PdfName.Pg); if (pg != null) { PdfDictionary pageAnalog = copyingParams.GetPage2page().Get(pg); if (pageAnalog == null) { pageAnalog = destPage; parentChangePg = true; } else { parentChangePg = false; } copied.Put(PdfName.Pg, pageAnalog); } } PdfObject k = source.Get(PdfName.K); if (k != null) { if (k.IsArray()) { PdfArray kArr = (PdfArray)k; PdfArray newArr = new PdfArray(); for (int i = 0; i < kArr.Size(); i++) { PdfObject copiedKid = CopyObjectKid(kArr.Get(i), copied, destPage, parentChangePg, copyingParams); if (copiedKid != null) { newArr.Add(copiedKid); } } if (!newArr.IsEmpty()) { if (newArr.Size() == 1) { copied.Put(PdfName.K, newArr.Get(0)); } else { copied.Put(PdfName.K, newArr); } } } else { PdfObject copiedKid = CopyObjectKid(k, copied, destPage, parentChangePg, copyingParams); if (copiedKid != null) { copied.Put(PdfName.K, copiedKid); } } } return(copied); }
/// <summary>Creates a Type 3 font based on an existing font dictionary, which must be an indirect object.</summary> /// <param name="fontDictionary">a dictionary of type <code>/Font</code>, must have an indirect reference.</param> internal PdfType3Font(PdfDictionary fontDictionary) : base(fontDictionary) { subset = true; embedded = true; fontProgram = new Type3Font(false); fontEncoding = DocFontEncoding.CreateDocFontEncoding(fontDictionary.Get(PdfName.Encoding), toUnicode); PdfDictionary charProcsDic = GetPdfObject().GetAsDictionary(PdfName.CharProcs); PdfArray fontMatrixArray = GetPdfObject().GetAsArray(PdfName.FontMatrix); if (GetPdfObject().ContainsKey(PdfName.FontBBox)) { PdfArray fontBBox = GetPdfObject().GetAsArray(PdfName.FontBBox); fontProgram.GetFontMetrics().SetBbox(fontBBox.GetAsNumber(0).IntValue(), fontBBox.GetAsNumber(1).IntValue( ), fontBBox.GetAsNumber(2).IntValue(), fontBBox.GetAsNumber(3).IntValue()); } else { fontProgram.GetFontMetrics().SetBbox(0, 0, 0, 0); } int firstChar = NormalizeFirstLastChar(fontDictionary.GetAsNumber(PdfName.FirstChar), 0); int lastChar = NormalizeFirstLastChar(fontDictionary.GetAsNumber(PdfName.LastChar), 255); for (int i = firstChar; i <= lastChar; i++) { shortTag[i] = 1; } int[] widths = FontUtil.ConvertSimpleWidthsArray(fontDictionary.GetAsArray(PdfName.Widths), firstChar, 0); double[] fontMatrix = new double[6]; for (int i = 0; i < fontMatrixArray.Size(); i++) { fontMatrix[i] = ((PdfNumber)fontMatrixArray.Get(i)).GetValue(); } SetFontMatrix(fontMatrix); if (toUnicode != null && toUnicode.HasByteMappings() && fontEncoding.HasDifferences()) { for (int i = 0; i < 256; i++) { int unicode = fontEncoding.GetUnicode(i); PdfName glyphName = new PdfName(fontEncoding.GetDifference(i)); if (unicode != -1 && !glyphName.GetValue().Equals(FontEncoding.NOTDEF) && charProcsDic.ContainsKey(glyphName )) { ((Type3Font)GetFontProgram()).AddGlyph(i, unicode, widths[i], null, new Type3Glyph(charProcsDic.GetAsStream (glyphName), GetDocument())); } } } IDictionary <int, int?> unicodeToCode = null; if (toUnicode != null) { try { unicodeToCode = toUnicode.CreateReverseMapping(); } catch (Exception) { } } foreach (PdfName glyphName in charProcsDic.KeySet()) { int unicode = AdobeGlyphList.NameToUnicode(glyphName.GetValue()); int code = -1; if (fontEncoding.CanEncode(unicode)) { code = fontEncoding.ConvertToByte(unicode); } else { if (unicodeToCode != null && unicodeToCode.ContainsKey(unicode)) { code = (int)unicodeToCode.Get(unicode); } } if (code != -1 && GetFontProgram().GetGlyphByCode(code) == null) { ((Type3Font)GetFontProgram()).AddGlyph(code, unicode, widths[code], null, new Type3Glyph(charProcsDic.GetAsStream (glyphName), GetDocument())); } } FillFontDescriptor(fontDictionary.GetAsDictionary(PdfName.FontDescriptor)); }
protected internal override void CheckAnnotation(PdfDictionary annotDic) { PdfName subtype = annotDic.GetAsName(PdfName.Subtype); if (subtype == null) { throw new PdfAConformanceException(PdfAConformanceException.ANNOTATION_TYPE_0_IS_NOT_PERMITTED).SetMessageParams ("null"); } if (forbiddenAnnotations.Contains(subtype)) { throw new PdfAConformanceException(PdfAConformanceException.ANNOTATION_TYPE_0_IS_NOT_PERMITTED).SetMessageParams (subtype.GetValue()); } PdfNumber ca = annotDic.GetAsNumber(PdfName.CA); if (ca != null && ca.FloatValue() != 1.0) { throw new PdfAConformanceException(PdfAConformanceException.AN_ANNOTATION_DICTIONARY_SHALL_NOT_CONTAIN_THE_CA_KEY_WITH_A_VALUE_OTHER_THAN_1 ); } if (!annotDic.ContainsKey(PdfName.F)) { throw new PdfAConformanceException(PdfAConformanceException.AN_ANNOTATION_DICTIONARY_SHALL_CONTAIN_THE_F_KEY ); } int flags = (int)annotDic.GetAsInt(PdfName.F); if (!CheckFlag(flags, PdfAnnotation.PRINT) || CheckFlag(flags, PdfAnnotation.HIDDEN) || CheckFlag(flags, PdfAnnotation .INVISIBLE) || CheckFlag(flags, PdfAnnotation.NO_VIEW)) { throw new PdfAConformanceException(PdfAConformanceException.THE_F_KEYS_PRINT_FLAG_BIT_SHALL_BE_SET_TO_1_AND_ITS_HIDDEN_INVISIBLE_AND_NOVIEW_FLAG_BITS_SHALL_BE_SET_TO_0 ); } if (subtype.Equals(PdfName.Text) && (!CheckFlag(flags, PdfAnnotation.NO_ZOOM) || !CheckFlag(flags, PdfAnnotation .NO_ROTATE))) { throw new PdfAConformanceException(PdfAConformanceLogMessageConstant.TEXT_ANNOTATIONS_SHOULD_SET_THE_NOZOOM_AND_NOROTATE_FLAG_BITS_OF_THE_F_KEY_TO_1 ); } if (annotDic.ContainsKey(PdfName.C) || annotDic.ContainsKey(PdfName.IC)) { if (!ICC_COLOR_SPACE_RGB.Equals(pdfAOutputIntentColorSpace)) { throw new PdfAConformanceException(PdfAConformanceException.DESTOUTPUTPROFILE_IN_THE_PDFA1_OUTPUTINTENT_DICTIONARY_SHALL_BE_RGB ); } } PdfDictionary ap = annotDic.GetAsDictionary(PdfName.AP); if (ap != null) { if (ap.ContainsKey(PdfName.D) || ap.ContainsKey(PdfName.R)) { throw new PdfAConformanceException(PdfAConformanceException.APPEARANCE_DICTIONARY_SHALL_CONTAIN_ONLY_THE_N_KEY_WITH_STREAM_VALUE ); } if (PdfName.Widget.Equals(annotDic.GetAsName(PdfName.Subtype)) && PdfName.Btn.Equals(annotDic.GetAsName(PdfName .FT))) { if (ap.GetAsDictionary(PdfName.N) == null) { throw new PdfAConformanceException(PdfAConformanceException.N_KEY_SHALL_BE_APPEARANCE_SUBDICTIONARY); } } else { if (ap.GetAsStream(PdfName.N) == null) { throw new PdfAConformanceException(PdfAConformanceException.APPEARANCE_DICTIONARY_SHALL_CONTAIN_ONLY_THE_N_KEY_WITH_STREAM_VALUE ); } } CheckResourcesOfAppearanceStreams(ap); } if (PdfName.Widget.Equals(subtype) && (annotDic.ContainsKey(PdfName.AA) || annotDic.ContainsKey(PdfName.A) )) { throw new PdfAConformanceException(PdfAConformanceException.WIDGET_ANNOTATION_DICTIONARY_OR_FIELD_DICTIONARY_SHALL_NOT_INCLUDE_A_OR_AA_ENTRY ); } if (annotDic.ContainsKey(PdfName.AA)) { throw new PdfAConformanceException(PdfAConformanceException.AN_ANNOTATION_DICTIONARY_SHALL_NOT_CONTAIN_AA_KEY ); } if (CheckStructure(conformanceLevel)) { if (contentAnnotations.Contains(subtype) && !annotDic.ContainsKey(PdfName.Contents)) { throw new PdfAConformanceException(PdfAConformanceException.ANNOTATION_OF_TYPE_0_SHOULD_HAVE_CONTENTS_KEY) .SetMessageParams(subtype.GetValue()); } } }
/// <summary>Removes annotation content item from the tag structure.</summary> /// <remarks> /// Removes annotation content item from the tag structure. /// If annotation is not added to the document or is not tagged, nothing will happen. /// </remarks> /// <returns> /// /// <see cref="TagTreePointer"/> /// instance which points at annotation tag parent if annotation was removed, /// otherwise returns null. /// </returns> public virtual TagTreePointer RemoveAnnotationTag(PdfAnnotation annotation) { PdfStructElem structElem = null; PdfDictionary annotDic = annotation.GetPdfObject(); PdfNumber structParentIndex = (PdfNumber)annotDic.Get(PdfName.StructParent); if (structParentIndex != null) { PdfObjRef objRef = document.GetStructTreeRoot().FindObjRefByStructParentIndex(annotDic.GetAsDictionary(PdfName .P), structParentIndex.IntValue()); if (objRef != null) { PdfStructElem parent = (PdfStructElem)objRef.GetParent(); parent.RemoveKid(objRef); structElem = parent; } } annotDic.Remove(PdfName.StructParent); annotDic.SetModified(); if (structElem != null) { return(new TagTreePointer(document).SetCurrentStructElem(structElem)); } return(null); }
private static PdfDictionary CopyObject(PdfDictionary source, ICollection <PdfObject> objectsToCopy, PdfDocument toDocument, IDictionary <PdfDictionary, PdfDictionary> page2page, bool copyFromDestDocument) { PdfDictionary copied; if (copyFromDestDocument) { copied = source.Clone(ignoreKeysForCopy); if (source.IsIndirect()) { copied.MakeIndirect(toDocument); } } else { copied = source.CopyTo(toDocument, ignoreKeysForCopy, true); } if (source.ContainsKey(PdfName.Obj)) { PdfDictionary obj = source.GetAsDictionary(PdfName.Obj); if (!copyFromDestDocument && obj != null) { // Link annotations could be not added to the toDocument, so we need to identify this case. // When obj.copyTo is called, and annotation was already copied, we would get this already created copy. // If it was already copied and added, /P key would be set. Otherwise /P won't be set. obj = obj.CopyTo(toDocument, iText.IO.Util.JavaUtil.ArraysAsList(PdfName.P), false); copied.Put(PdfName.Obj, obj); } } PdfDictionary pg = source.GetAsDictionary(PdfName.Pg); if (pg != null) { //TODO It is possible, that pg will not be present in the page2page map. Consider the situation, // that we want to copy structElem because it has marked content dictionary reference, which belongs to the page from page2page, // but the structElem itself has /Pg which value could be arbitrary page. copied.Put(PdfName.Pg, page2page.Get(pg)); } PdfObject k = source.Get(PdfName.K); if (k != null) { if (k.IsArray()) { PdfArray kArr = (PdfArray)k; PdfArray newArr = new PdfArray(); for (int i = 0; i < kArr.Size(); i++) { PdfObject copiedKid = CopyObjectKid(kArr.Get(i), copied, objectsToCopy, toDocument, page2page, copyFromDestDocument ); if (copiedKid != null) { newArr.Add(copiedKid); } } // TODO new array may be empty or with single element copied.Put(PdfName.K, newArr); } else { PdfObject copiedKid = CopyObjectKid(k, copied, objectsToCopy, toDocument, page2page, copyFromDestDocument); if (copiedKid != null) { copied.Put(PdfName.K, copiedKid); } } } return(copied); }
internal static Type1Font CreateFontProgram(PdfDictionary fontDictionary, FontEncoding fontEncoding, CMapToUnicode toUnicode) { PdfName baseFontName = fontDictionary.GetAsName(PdfName.BaseFont); String baseFont; if (baseFontName != null) { baseFont = baseFontName.GetValue(); } else { baseFont = FontUtil.CreateRandomFontName(); } if (!fontDictionary.ContainsKey(PdfName.FontDescriptor)) { Type1Font type1StdFont; try { //if there are no font modifiers, cached font could be used, //otherwise a new instance should be created. type1StdFont = (Type1Font)FontProgramFactory.CreateFont(baseFont, true); } catch (Exception) { type1StdFont = null; } if (type1StdFont != null) { return(type1StdFont); } } iText.Kernel.Font.DocType1Font fontProgram = new iText.Kernel.Font.DocType1Font(baseFont); PdfDictionary fontDesc = fontDictionary.GetAsDictionary(PdfName.FontDescriptor); fontProgram.subtype = fontDesc.GetAsName(PdfName.Subtype); FillFontDescriptor(fontProgram, fontDesc); PdfNumber firstCharNumber = fontDictionary.GetAsNumber(PdfName.FirstChar); int firstChar = firstCharNumber != null?Math.Max(firstCharNumber.IntValue(), 0) : 0; int[] widths = FontUtil.ConvertSimpleWidthsArray(fontDictionary.GetAsArray(PdfName.Widths), firstChar, fontProgram .GetMissingWidth()); fontProgram.avgWidth = 0; int glyphsWithWidths = 0; for (int i = 0; i < 256; i++) { Glyph glyph = new Glyph(i, widths[i], fontEncoding.GetUnicode(i)); fontProgram.codeToGlyph.Put(i, glyph); if (glyph.HasValidUnicode()) { //FontEncoding.codeToUnicode table has higher priority if (fontEncoding.ConvertToByte(glyph.GetUnicode()) == i) { fontProgram.unicodeToGlyph.Put(glyph.GetUnicode(), glyph); } } else { if (toUnicode != null) { glyph.SetChars(toUnicode.Lookup(i)); } } if (widths[i] > 0) { glyphsWithWidths++; fontProgram.avgWidth += widths[i]; } } if (glyphsWithWidths != 0) { fontProgram.avgWidth /= glyphsWithWidths; } return(fontProgram); }