コード例 #1
0
    /// <summary>
    /// Writes a Glyphs to the content stream.
    /// </summary>
    private void WriteGlyphs(Glyphs glyphs)
    {
      WriteSaveState("begin Glyphs", glyphs.Name);

      // Transform also affects clipping and opacity mask
      bool transformed = glyphs.RenderTransform != null;
      if (transformed)
        WriteRenderTransform(glyphs.RenderTransform);

      bool clipped = glyphs.Clip != null;
      if (clipped)
        WriteClip(glyphs.Clip);

      if (glyphs.Opacity < 1)
        MultiplyOpacity(glyphs.Opacity);

      if (glyphs.OpacityMask != null)
        WriteOpacityMask(glyphs.OpacityMask);

      XMatrix textMatrix = new XMatrix();

      textMatrix.TranslatePrepend(glyphs.OriginX, glyphs.OriginY);
      glyphs.OriginX = glyphs.OriginY = 0; // HACK: do not change model

      double emSize = glyphs.FontRenderingEmSize;
      textMatrix.ScalePrepend(glyphs.FontRenderingEmSize);
      glyphs.FontRenderingEmSize = 1; // HACK: do not change model


      bool boldSimulation = (glyphs.StyleSimulations & StyleSimulations.BoldSimulation) == StyleSimulations.BoldSimulation;

      // just a draft...
      if (boldSimulation)
      {
        boldSimulation = true;

        // draw black stroke if it is not a solid color brush
        XColor color = XColor.FromArgb(0, 0, 0);
        if (glyphs.Fill is SolidColorBrush)
        {
          SolidColorBrush brush = glyphs.Fill as SolidColorBrush;
          color = brush.Color;
        }
        WriteLiteral(String.Format(CultureInfo.InvariantCulture, "{0:0.###} {1:0.###} {2:0.###}  RG\n", color.R / 255.0, color.G / 255.0, color.B / 255.0));
        WriteLiteral("{0:0.###} w\n", emSize / 50);
      }

      if ((glyphs.StyleSimulations & StyleSimulations.ItalicSimulation) == StyleSimulations.ItalicSimulation)
      {
        textMatrix.SkewPrepend(-20, 0);
      }

      XForm xform = null;
      XImage ximage = null;
      RealizeFill(glyphs.Fill, ref xform, ref ximage);
      RealizeFont(glyphs);

      if (boldSimulation)
        WriteLiteral("2 Tr\n", 1);

      double x = glyphs.OriginX;
      double y = glyphs.OriginY;


      //switch (format.Alignment)
      //{
      //  case XStringAlignment.Near:
      //    // nothing to do
      //    break;

      //  case XStringAlignment.Center:
      //    x += (rect.Width - width) / 2;
      //    break;

      //  case XStringAlignment.Far:
      //    x += rect.Width - width;
      //    break;
      //}

      PdfFont realizedFont = this.graphicsState.realizedFont;
      Debug.Assert(realizedFont != null);
      realizedFont.AddChars(glyphs.UnicodeString);

      OpenTypeDescriptor descriptor = realizedFont.FontDescriptor.descriptor;

      //if (bold && !descriptor.IsBoldFace)
      //{
      //  // TODO: emulate bold by thicker outline
      //}

      //if (italic && !descriptor.IsBoldFace)
      //{
      //  // TODO: emulate italic by shearing transformation
      //}

#if true
      string s2 = "";
      string s = glyphs.UnicodeString;
      if (!String.IsNullOrEmpty(s))
      {
        int length = s.Length;
        for (int idx = 0; idx < length; idx++)
        {
          char ch = s[idx];
          int glyphID = 0;
          if (descriptor.fontData.cmap.symbol)
          {
            glyphID = (int)ch + (descriptor.fontData.os2.usFirstCharIndex & 0xFF00);
            glyphID = descriptor.CharCodeToGlyphIndex((char)glyphID);
          }
          else
            glyphID = descriptor.CharCodeToGlyphIndex(ch);
          s2 += (char)glyphID;
        }
      }
      s = s2;
#endif

      byte[] bytes = PdfEncoders.RawUnicodeEncoding.GetBytes(s);
      bytes = PdfEncoders.FormatStringLiteral(bytes, true, false, true, null);
      string text = PdfEncoders.RawEncoding.GetString(bytes);
      if (glyphs.IsSideways)
      {
        textMatrix.RotateAtPrepend(-90, new XPoint(x, y));
        XPoint pos = new XPoint(x, y);
        AdjustTextMatrix(ref pos);
        //WriteTextTransform(textMatrix);
        WriteLiteral("{0} Tj\n", text);
      }
      else
      {
#if true
        //if (glyphs.BidiLevel % 2 == 1)
        //  WriteLiteral("-1 Tc\n");

        if (!textMatrix.IsIdentity)
          WriteTextTransform(textMatrix);

        WriteGlyphsInternal(glyphs, null);
#else
        XPoint pos = new XPoint(x, y);
        AdjustTextMatrix(ref pos);
        WriteLiteral("{0:0.###} {1:0.###} Td {2} Tj\n", pos.x, pos.y, text);
        //PdfEncoders.ToStringLiteral(s, PdfStringEncoding.RawEncoding, null));
#endif
      }
      WriteRestoreState("end Glyphs", glyphs.Name);
    }