//==============================================================================
void LowLevelGraphicsPostScriptRenderer::fillPath (const Path& path, const AffineTransform& t)
{
    if (stateStack.getLast()->fillType.isColour())
    {
        writeClip();

        Path p (path);
        p.applyTransform (t.translated ((float) stateStack.getLast()->xOffset,
                                        (float) stateStack.getLast()->yOffset));
        writePath (p);

        writeColour (stateStack.getLast()->fillType.colour);

        out << "fill\n";
    }
    else if (stateStack.getLast()->fillType.isGradient())
    {
        // this doesn't work correctly yet - it could be improved to handle solid gradients, but
        // postscript can't do semi-transparent ones.
        notPossibleInPostscriptAssert   // you can disable this warning by setting the WARN_ABOUT_NON_POSTSCRIPT_OPERATIONS flag at the top of this file

        writeClip();
        out << "gsave ";

        {
            Path p (path);
            p.applyTransform (t.translated ((float) stateStack.getLast()->xOffset, (float) stateStack.getLast()->yOffset));
            writePath (p);
            out << "clip\n";
        }

        const Rectangle<int> bounds (stateStack.getLast()->clip.getBounds());

        // ideally this would draw lots of lines or ellipses to approximate the gradient, but for the
        // time-being, this just fills it with the average colour..
        writeColour (stateStack.getLast()->fillType.gradient->getColourAtPosition (0.5f));
        out << bounds.getX() << ' ' << -bounds.getBottom() << ' ' << bounds.getWidth() << ' ' << bounds.getHeight() << " rectfill\n";

        out << "grestore\n";
    }
}
void LowLevelGraphicsPostScriptRenderer::fillRect (const Rectangle<float>& r)
{
    if (stateStack.getLast()->fillType.isColour())
    {
        writeClip();
        writeColour (stateStack.getLast()->fillType.colour);

        Rectangle<float> r2 (r.translated ((float) stateStack.getLast()->xOffset,
                                           (float) stateStack.getLast()->yOffset));

        out << r2.getX() << ' ' << -r2.getBottom() << ' ' << r2.getWidth() << ' ' << r2.getHeight() << " rectfill\n";
    }
    else
    {
        Path p;
        p.addRectangle (r);
        fillPath (p, AffineTransform::identity);
    }
}
    //////////////////////////////////////////////////////////////////////////////////////////
    // RtfWriter::writeHeader
    //! Writes RTF header
    //! 
    //! \param[in] font - Font name
    //! 
    //! \throw wtl::domain_error - I/O error occurred
    //////////////////////////////////////////////////////////////////////////////////////////
    void  writeHeader(const char* font)
    {
      // Header
      writeString("{\\rtf1\\ansi");

      // Set codepage + language
      setCodePage(1250);
      setDefaultFont(0);
      setLanguage(2057);      // English UK  (0x0809 == 2057)

      // Font table
      writeString("{\\fonttbl{\\f0\\fswiss\\fcharset0 ");
      write(font);
      writeString(";}}\n");

      // Colour table
      writeString("{\\colortbl");
      writeString(";");  // Define colour 0 as 'auto-colour'
      for (COLORREF c : Colours)
        writeColour(c);
      writeString("}\n");


      // Unknown previous formatting: //\\sa200\\sl276\\slmult1
      // 
      // \saN == spacing after
      // \slN == space between lines
      // \smult == Line spacing multiple
      // \pard == reset paragraph formatting

      // Set view: 0==None, 1==Page Layout view, 2==Outline view, 3==Master Document view, 4==Normal view, 5==Online Layout view
      writeString("\\viewkind4");

      // Set unicode destination (not sure)
      writeString("\\uc1 ");

      // Reset paragraph
      resetParagraph();
    }