Skip to content


Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
branch: master
Commits on Apr 27, 2015
  1. Implement much simpler GDI font creation wrappers

    I've implemented these inside the Font_Management module, and will
    eventually look at cleaning up pdFont to simply wrap these improved
    creation functions.
    As for pdTextRenderer, it will now create a fallback GDI font object if
    GDI+ fails for whatever reason.  (The potential list of failure reasons
    is longer than I can write in a single commit message... ha ha)
    My next commit may take awhile, as my next task is new
    fontGlyphCollection and fontGlyph classes, which manage raw path data
    for individual character glyphs.  A ton of code has to be written before
    I can test these functions, so I don't know that intermediate commits
    will be very helpful.
  2. pdTextRenderer: finish refactoring to prep for dual GDI/GDI+ backends

    The existing pure-GDI+ code path is still completely functional, so the
    debug text tool implementation will still work.  However, it's now
    trivial for the class to switch paths if/when GDI+ fails on a font.
    Now to start work on the GDI path.
  3. Start prep work for OpenType font conversion

    This is going to be a hideously ugly project, but it's theoretically
    doable.  GDI supports OpenType fonts (and has for years), so I should be
    able to parse GDI glyphs, convert them from quadratic splines to GDI+
    compatible Bezier curves, then import them to GDI+ as a GraphicsPath.
    This would allow me to use GDI+ to render OpenType fonts, enabling all
    the nice GDI+ features we have for TrueType fonts.  Fingers crossed that
    it works.
    This commit is mostly a bunch of refactoring to make the new behavior
    easier to implement.
Commits on Apr 26, 2015
  1. pdComboBox_Font: start working on a font-specific drop down

    I thought about working this functionality directly into pdComboBox, but
    it's not worth the trouble, IMO.  A font selection dropdown is a really
    odd duck for a couple reasons:
    1) Its list contents are managed 100% internally, so it shouldn't expose
    any add/remove/clear type functionality.
    2) It has some incredibly specific rendering requirements, as we have to
    create hundreds (possibly thousands) of fonts on-the-fly.  That kind of
    messy work would just clutter up a normal combo box.
    3) It requires a lot of interop with the separate Font_Management
    module, as this class doesn't do things like query the system for fonts;
    instead, it relies on the module to do that.
    4) For saving/loading presets in a "portable app friendly" manner, this
    class needs to store the text contents of the combo box rather than the
    .ListIndex (as the availability of fonts will vary from system to
    Anyway, those are a few of the reasons that this is its own control.
    I'll be cracking away at this over the next few weeks amidst other UI
  2. New: build system-specific font cache at startup

    Performance should be excellent.  On my old Win 7 PC, a system with ~250
    fonts averages 12-13 ms to retrieve and sort the list of installed
    fonts.  (Sorting is required because Windows returns fonts in an
    arbitrary order, and we need to mirror the output to various drop-downs
    throughout the program.)
    (Also, this makes me wonder why GIMP's startup font detection is so
    horrifically slow.)
  3. pdProfiler: fix potential error on actions that happen too quickly

    Like the new font caching operation, lol - glad I caught this
  4. pdStringStack: add alphabetic sort function

    Many thanks to Ellis Dee for his original "Snake Sort" algorithm, shared
    here in 2007:
    "Snake Sort" works especially well on lists that are comprised of
    individually sorted sub-lists.  Windows returns fonts in exactly this
    fashion (strange blocks of 5-10 fonts, sorted alphabetically, before
    starting over again), so this is an ideal sort function for my current
    use case.
  5. Text tool: improve performance when creating a new layer

    You can now click to create a text box at default size, or drag-release
    to set a specific size.  (This was worth fixing now as I'm creating a
    *lot* of text layers during testing.)
Commits on Apr 25, 2015
  1. Text tool: add a few more features for debugging purposes

    Text hinting and clarity are worth testing, given Microsoft's general
    inability to write a coherent graphics library.  As expected, ClearType
    is broken on 32-bpp rendering targets, but even more odd is that Non-AA
    + hinting (TextRenderingHintSingleBitPerPixelGridFit) is also
    inexplicably broken.  For some reason, this setting forcibly sets target
    alpha values to zero *only where the font is displayed*, effectively
    making text transparent regardless of existing alpha.  WTF.  (Only
    tested on Win 7 so far, but since GDI+ is deprecated I expect similar
    behavior elsewhere)
    At this rate, I may look at implementing a Pango text backend sooner
    rather than later.
Commits on Apr 24, 2015
  1. Finish support for text layers in PDI files

    Sorry, forgot to do this before; text layers were being saved, but not
    their width and height (because those are generic vector parameters,
    shared among all vector layers).
    Text layers should save/load just fine now.
  2. Add font color to text tool UI

    While there are (obviously) a ton more font options to expose, this is a
    decent start for testing.
    I'm going to take a detour now, and start overhauling the way the tool
    options panel works (specifically issue #166).  This will simplify
    further work on the text tool UI, especially as I start to implement
    multiple text option panels.
    While the text tool works pretty well already, note that things like
    converting text layers to image layers, or merging text and image
    layers, have not been implemented yet.  There are also some on-canvas UI
    quirks (like ugly pauses when a text layer is first created) that need
    to be addressed.  These are all on my to-do list.
  3. Implement basic text tool UI

    Text, font, and font size can now be set.  Typing out text results in an
    immediate preview at quite good performance(YYYEEEEAAAAHHHHH).
    This commit also fixes a severe compositor bug where modified layers
    sometimes weren't being reflected on-screen.  Oops!
    Tons of UI changes and improvements are coming, but I needed a bare
    minimum of text features so I can debug things like the new
    pdTextRenderer class.
  4. Text layers: implement core on-canvas UI

    Text layers can now be created, moved around, and resized.
  5. pdCanvas: start laying groundwork for text layer creation and interac…

    Only partially implemented at present, so I can't guarantee the program
    won't crash when selecting the text tool.  Use at your own risk!
  6. When creating new layers, explicitly specify layer type

    Important now that we have more than just raster layers
  7. GDI+ wrapper: add external functions for managing GDI+ brushes

    We need these to fill strings
  8. pdLayer: flesh out tons of text layer properties and behaviors

    Still more to do, but this is a good start
  9. pdTextRenderer: add actual string render function

    With this commit, pdTextRenderer is finally ready for a first round of
Commits on Apr 23, 2015
  1. pdTextRenderer: wrap up bulk of property get/set functionality

    A class instance can now be properly serialized to/from XML, which is
    the main functionality required for PDI storage and Undo/Redo
    functionality.  GDI+ objects are also cached and cleaned when relevant,
    and font caching has been implemented to minimize churn.
    Next, it's time to work on the actual rendering bits.
  2. pdTextRenderer: continue filling in functionality

    (This was supposed to be part of the previous commit)
  3. pdTextRenderer: continue filling in functionality

    Lots of tedious work, but someone's got to do it...
  4. pdTextRenderer: add support for GDI+ font retrieval

    Unfortunately, GDI+ is only compatible with TrueType fonts (sigh).  But
    at least it makes it straightforward to retrieve Unicode-compatible font
Commits on Apr 22, 2015
  1. Add text and vector layer support to PDI files

    For size and performance reasons, text and vector layers do not store a
    raster copy of their contents.  The raster copy is created on-the-fly at
    Thanks to careful planning, vector layers should not require any special
    handling in the Undo engine (which uses a variety of PDI file types to
    read/write Undo data efficiently), or even the generic PDI load/save
    functions, aside from this commit which involves retrieving
    layer-specific data as a generic byte stream or Unicode text block.  The
    PDI read/write functions simply lean on pdLayer to properly generate or
    parse layer-specific XML data on a per-layer-type basis.
    As such, future vector layers should not require commits like this; only
    pdLayer itself will need to be updated.
Commits on Apr 21, 2015
Commits on Apr 20, 2015
  1. Text tool: start work on bare-bones UI bits

    The text tool is going to be a massive project, since text is PD's first
    true vector tool.  As such, the pdLayer object is going to require many
    updates.  (Obviously, once this project is done, adding future vector
    tools - shapes, pen, etc - will be much easier thanks to having a
    functional vector management pipeline.)
    Text tool is also a UI nightmare since a lot of user-facing options are
    relevant, and PD will need a dedicated edit box for text entry. (I do
    not plan to implement on-canvas editing - sorry!  Blame WAPI for this.)
    Special user controls like a font-specific combo box are also important,
    not just here but elsewhere in the project, so that's another big
    component of this work.
    At first, I'm hoping to simply implement a "bare bones" version of a
    text tool, to make sure my vector engine design is sound.  (I also need
    to write a new GDI+ font manager, which is going to take some time.)
    Once a bare bones implementation is functional and the new vector
    pipeline is in place, I can dedicate a lot more time to cleaning up the
    text tool UI and expanding available features.
  2. pdCompositor: fix issue where changing blend mode...

    ...would cause the layer to seemingly "shift" its on-screen appearance
    while zoomed out.
Commits on Apr 18, 2015
  1. Wrap up this round of compositor optimizations

    I'm sure there will be more to optimize in the future, but as of now
    (build 70), PD's viewport pipeline is in a great place.  Everything is
    more fluid and better organized, and the viewport pipeline and
    compositor will only need a few lines of code to handle paint tools.
    As an added bonus, paint operations will automatically receive all layer
    features for free (opacity, blend modes, subpixel positioning, etc)
    without any work on the part of the brush engine.  Very exciting.
  2. pdCompositor: implement viewport caching for normal blend mode

    Oooohhh boy, this is exciting.  With this commit, I believe PD now has
    the most fluid viewport of any open-source photo editor.  Regardless of
    layer count, size, blend mode, or opacity, PD can now render interactive
    viewport actions (e.g. moving layers) with excellent responsiveness.
    There's none of the ridiculous chunky choppiness of other photo editors
    (*cough* GIMP *cough* Paint.NET) or the sluggishness of old PD versions.
    As an added bonus, sub-pixel positioning is actually displayed *more
    accurately* after this update!
    This is all possible with minimal impact to memory usage as well, so I
    consider this a pretty sweet win.  I'm also feeling a lot better about
    implementing paint tools, as choppiness is murder when trying to do
    accurate painting work.
  3. pdCompositor: implement non-destructive FX and blend mode caching

    This greatly reduces the viewport render penalty for non-destructive
    effects and/or custom blend modes on the default pipeline.  The current
    viewport chunk of each layer is now cached AFTER non-destructive effects
    are applied, so we only need to regenerate it after changes are made.
    Similarly, the temp copy of each layer required for custom blend-mode
    compositing is also cached, so when doing something like moving a layer
    around, all other layers with custom blend modes will render much
    This was a prerequisite to paint tools.  I may also look at caching
    resized versions of each layer when zoomed-out, to further improve
    render performance.
Something went wrong with that request. Please try again.