Given a temperature adjustment on the range -100 to 100,
apply the following adjustment to each pixel in the image:
r = r + adjustmentValue
g = g
b = b - adjustmentValue
As with any additive RGB adjustment, you’ll need to manually clip the output values to the [0, 255] range.
Here’s a sample of the output, as implemented in the latest development build of my open-source photo editor. Note the temperature slider at the bottom of the screen. Because I find the -100 to 100 range to be a bit too strong, I actually divide the adjustment value by 5, thus limiting the actual adjustment value from -20 to 20:
Because temperature and tint adjustments are usually provided together, here’s the code for basic tint adjustments. It’s even simper than temperature:
Given a tint adjustment on the range -100 to 100,
apply the following adjustment to each pixel in the image:
r = r
g = g + adjustmentValue
b = b
Sample output, using the same sample image from above (note the tint slider at the bottom):
This might be the simplest image processing algorithm I’ve ever posted… :)
(Apologies for the dearth of blog posts over the past few months. The holidays always throw off my schedule, and it takes some time to get things back in order. I’ll try to make more time for articles!)
A new version of PhotoDemon is about ready to release, and anyone who can help give it a final round of testing is most appreciated. Download the 6.2 beta here:
The old MDI “floating-window” interface is gone for good. In its place is a sleek, lightweight tabbed interface.
This was a huge project, and an exciting addition for both casual and professional users. PhotoDemon now provides a fully color-managed workflow across the entire program (including the main viewport, all tool dialogs, and even small things like color selection dialogs).
New color selector
Major improvement over the stock Windows color selection dialog (which hasn’t changed in 20 years). Many thanks to the open-source photo editor GIMP, whose color selector served as the primary inspiration for this one.
Comprehensive Resize options
In past versions, PhotoDemon always required you to resize images using pixel values – but no more! All resize dialogs (Image Resize, Canvas Resize, etc) now support resizing by pixels, percent, or physical units (inches, cm).
All-new JPEG export dialog
As the most common image format, JPEGs deserve special consideration. PhotoDemon’s new JPEG export dialog provides many new features, including the ability to have the software automatically determine an appropriate quality setting for you.
WebP and JPEG-XR support (import and export)
I don’t know if anyone uses these formats, but they’re there if you need ’em!
New Autosave feature
New Content-Aware Resize tool
Content-aware resize is a cutting-edge technique for resizing images without distorting their contents. It was recently added to PhotoShop in version CS4, and nearly all free photo editors lack a comparable tool – but not PhotoDemon!
Improved tool previews
Tool dialogs now provide an option to toggle between “fit whole image on screen” and “show image at 100%”. When showing the image at 100%, the image can be click-dragged, so even large images can be fully inspected. Also, the preview tool now supports “click to set a center point” behavior when relevant.
Asynchronous image metadata handling
Parsing image metadata occupies a huge chunk of the image load process. To improve performance, metadata handling is now completely asynchronous, meaning it will operate in parallel with the rest of the image loading process.
Improved Screen Capture tool
Individual program windows can now be selected from a list, with or without their window decorations (titlebar, borders, etc).
(Note before I begin: the PhotoDemon 6.0 beta should be live by the end of this week. Sorry it took so long to prepare!)
The latest nightly build of PhotoDemon (download it here) includes a bunch of new and improved blur filters. Blur filters are among the most computationally demanding filters in a photo editor, because for each pixel in an image, a bunch of other pixels must also be examined in order to calculate the blur. (Blurs generally work by averaging together groups of pixels. Motion blur averages pixels in a line, radial blur averages pixels in an arc, and normal blur averages pixels in a box or circle shape.)
As a simple example, consider a basic blur with a 200 pixel radius, applied to a 10 megapixel digital photo. For each pixel in the photo (all ten million of them), an area of 200 pixels in each direction must be averaged together. Using a simple box blur, that means a box of 200 pixels left, right, up and down must be tallied (for a net area of 400 * 400, or 160,000 pixel comparisons) in order to calculate the blur. Thus, such an algorithm would require:
10,000,000 pixels * 160,000 calculations per pixel = 1.6 trillion total calculations
Even on a modern processor, that’s an enormous undertaking. Fortunately, mathematicians and coders have developed many clever ways to optimize blur functions. Many of these optimizations appear in the newest PhotoDemon build, so I thought it would be fun to speed-test four of PhotoDemon’s blur tools against two other free photo editors: GIMP and Paint.NET. The results were surprising enough that I thought them worth sharing.
A brief overview of each photo editor:
PhotoDemon: open-source, written in VB6, nightly build 893 (6.0 beta)
GIMP: open-source, written primarily in C, v2.8.6
Paint.NET: closed-source, written primarily in C# (and the .Net framework, per the name), v3.5.11
As benchmarking goes, this was very informal. PhotoDemon reports timing automatically in nightly builds, but for GIMP and Paint.NET I had to resort to using a stopwatch. Normally this is a terrible idea, but the algorithms involved take a very long time to run, so a stopwatch was sufficient for broad timing. (10ths of a second don’t matter much when an algorithm takes twenty minutes to finish…)
All tests were done on Windows 7 (64-bit), on my Core i5 650 (3.2ghz) desktop PC with 8gb of RAM. My PC was middle-of-the-road when I bought it back in 2010, so I’d consider reasonably representative of an “average” PC. All the tools in question appear to be heavily CPU-bound anyway, so it’s doubtful newer processors or more cores would make a meaningful difference.
The test photo I used was a 10 megapixel photo, 3872×2592 specifically, in JPEG format:
With the exception of some very long timings (10+ minutes), all timings were checked twice to make sure results were representative. Very long ones were only checked once due to the wait involved, though I did initiate a second attempt just to make sure my PC wasn’t acting up. (It wasn’t.)
Here are the timing results for four separate blur types, with some notes on my implementation, and what I know or can potentially infer about GIMP and/or Paint.NET’s implementations.
(Due to the large size of the images involved, I saw no reason to upload the output images of each test. Anyone interested can easily reproduce this test on their own PC with images of their choosing.)
Gaussian Blur provides an excellent starting point. Gaussian blur works by averaging a square chunk of pixels, and giving pixels close to the center more weight than pixels far away. It is the most common type of blur tool in photo editing software, probably because its results are aesthetically pleasing, and it is an easy blur function to optimize.
Instead of a naive approach, which would involve the 1.6 trillion calculations mentioned above, most photo editors implement Gaussian Blur using a separable implementation, which cuts the calculations to a much more pleasant 8 billion calculations. Unfortunately, 8 billion calculations is still a lot. (PhotoDemon’s “best quality” option on its Gaussian tool applies a pure Gaussian using separable kernels. On large images, it’s slow. Very slow.)
An even faster approach takes advantage of a neat mathematical relationship between box filters and Gaussian filters: if you keep applying a box filter to a set of data, the result will eventually approach a Gaussian distribution. (Excellent charts available here, courtesy of Nghia Ho.) The Central Limit Theorem shows that repeating a box blur three times results in a function that’s ~97% identical to a true Gaussian.
PhotoDemon uses this as the basis for its three quality settings for Gaussian blur (good, better, and best). Good is a 3x box blur approximation, Better is a 5x, and Best is a true Gaussian. For the chart above, I used the “good” setting because it is by far the fastest. (Note that there’s a bit more to it than just repeating a box blur – how you calculate the box blur size matters; I use a variation of the W3 recommendation available here.)
Take-home message: GIMP’s IIR implementation is excellent – very fast, and it produces a true Gaussian, no estimations. PhotoDemon is surprisingly competitive for a single-threaded VB6 app. Paint.NET’s Gaussian is quite poor both in quality and final result. Its resulting blur is muddier than a true Gaussian, and much slower than you’d expect for a box-blur approximation… so I honestly have no idea how they’ve implemented it.
Motion blur is a bit more problematic than Gaussian blur, because it doesn’t work in a square pattern. A naive approach would have you use something like Bresenham’s algorithm on each pixel, tracing a line at the specified angle and averaging interpolated values as you go.
A much better approach is to simply rotate the image by the requested angle, apply a (very fast) horizontal blur, then rotate the image back into place. If you use a fast rotation algorithm (like the famous 3-shear technique), this can make motion blur very quick.
My PhotoDemon implementation does not use the fast 3-shear technique; it uses a naive, geometric rotation (reverse-mapped) with bilinear interpolation. I expected this to make it quite a bit slower than comparable tools in GIMP and Paint.NET, but I was surprised to discover that both software packages are… well, pretty damn terrible.
Based on a brief perusal of GIMP’s source code, they appear to use the naive Bresenham approach, which explains why it’s so slow.
And so we move to Radial Blur, where we find a surprising role reversal: Paint.NET gives a much better showing here, while GIMP turns in the worst performance yet. Again, a brief look at GIMP’s source code for this function shows a questionable nested-loop approach to the problem. Tracing an arc-like path for each pixel is a bad idea, and while bilinear interpolation is used to improve the output quality – same as PhotoDemon – the time required makes this tool pretty much unusable.
PhotoDemon’s implementation is nothing particularly special, which makes its relative performance so surprising. I use a well-known trick where I convert the image to polar coordinates, apply a horizontal blur, then convert the image back to Cartesian coordinates. A small amount of image quality is lost by the two coordinate conversions, but because we are blurring the image anyway, this doesn’t matter much. That said, for small angles (< 5 degrees), both GIMP and Paint.NET produce better-looking output.
At larger radii, however, PhotoDemon's is much better. Both GIMP and Paint.NET produce Moire patterns, presumably from sampling at discrete intervals, while PhotoDemon’s output is clean and smooth. This can probably be fixed in Paint.NET by using a higher quality setting, but quality setting 2/5 was already slow enough!
Last up is Zoom Blur, and we have a surprising winner! Paint.NET’s zoom blur implementation is excellent – great quality, very fast, and overall a huge improvement from their other blur tools. I have no idea why Zoom Blur is significantly faster than their Gaussian Blur implementation at a comparable pixel size, so I can only assume that some kind of specialized optimizations have been added. Nice work, Paint.NET team!
GIMP… I don’t even know what to say. It’s possible that I triggered some sort of problem with GIMP’s tile-based processing system, because there is no good way to explain a 17-minute processing time for such a straightforward function. Even a naive implementation shouldn’t take anywhere near that long. Their implementation has loops nested five-deep (dear god), and while bilinear interpolation is used to improve output, that algorithm is so poorly written that I frankly think they should consider removing it completely. Even at very low distances, rendering takes forever. The original copyright date on the source file is 1997, so perhaps someone familiar with GIMP’s internals should give this one a second look.
PhotoDemon uses the same trick here as with radial blur. The image is converted to polar coordinates (with swapped x and y values compared to the radial blur conversion), a horizontal blur is applied, then the image is converted back. Again, there is quality loss at low values, and both Paint.NET and GIMP provide better-quality output at very small radii. To mitigate this, I provide a second style on that dialog, which uses an iterative image-sized alpha blend to generate a blur. One of the neat things about that approach is that the image can be zoomed-out as well as zoomed-in.
Blur algorithm performance is hugely variable in both GIMP and Paint.NET. I’ll admit – I find it a bit amusing that my little PhotoDemon project, written with a 15-year-old programming language and compiler, outperforms them so handily in multiple areas, despite my implementations being generally lazy, single-threaded, and heavily CPU-bound. I also call “bullshit” on Paint.NET’s claim about “extensive work going into making Paint.NET the fastest image editor available.” I think the Paint.NET team does great work, and their software is a wonderful improvement over many free and paid photo editors, but its performance is greatly lacking in a number of areas.
Then there is GIMP. While I am very grateful for their software, and have learned to love its many quirks, there’s no denying that whole swaths of its source code are in desperate need of a revamp. I imagine there is no point revisiting items like blur until they complete their migration to GEGL – perhaps then we will see big improvements in the performance of these various blur functions.
If there’s a take-home message to all this, it’s that algorithms will always be more important than programming languages. A well-written algorithm in a “slow” language will often outperform a poorly written algorithm in a “fast” language. VB6 may be forgotten and nearly dead, but I’m happy to see it staying competitive with the titans of the “free photo editor” world. :)
If you read the article all the way to here, I hope you’ll give PhotoDemon a look:
For a free, open-source photo editor, it has a lot of nice features, and I can empirically state that it outperforms GIMP and Paint.NET in at least a few areas! (The current nightly build is pretty much how the next stable release (6.0) will look, minus a few minor bugfixes still to complete.)
This is not a full-blown article – just a quick HOWTO for people who require the latest version of zLib and want to use it from a language (like classic VB) that requires a standard WinAPI interface.
By default, zLib uses C calling conventions (CDECL). Gilles Vollant has helpfully provided an STDCALL version of zLib in the past, but his site only provides version 1.2.5, which dates back to January 2012. zLib is currently on version 1.2.8.
Gilles has contributed his WAPI fixes to the core zLib distribution so that anyone can compile it themselves. To do this, you will need to download:
Once both of those are downloaded (and updated, as VS 2012 will require you to install several service packs), follow these steps to compile zLib yourself:
Extract the entire zLib file and navigate to the /contrib/masmx86 folder. Open the “bld_ml32.bat” file in a text editor.
Add the “/safeseh” switch to both lines in that file (e.g. “ml /safeseh /coff /Zi /c /Flmatch686.lst match686.asm”). Then save and exit.
Navigate to the /contrib/vstudio/vc11/ folder. Open the zlibvc.sln file in your newly installed Visual Studio 2012 Express.
In the Solution Explorer (top-right by default), right-click “zlibstat” then select “Properties” at the bottom.
Go to Configuration Properties -> C/C++ -> Preprocessor, and in the Preprocessor Definitions line remove “ZLIB_WINAPI;” (don’t forget to remove the trailing semicolon).
Now, we need to fix a recently introduced problem that relies on Win8 functionality. In the Solution Explorer, navigate to zlibvc -> iowin32.c. Double-click to open the file.
Find the line of text that reads “#if WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_APP)”. Change this line to “#if WINAPI_FAMILY_ONE_PARTITION(WINAPI_FAMILY_DESKTOP_APP, WINAPI_PARTITION_APP)”. (Thanks to this link for this fix.)
zLib uses a Version number declaration that can cause the build process to fail. To fix this, go back to the Solution Explorer, then navigate to zlibvc -> zlibvc.def. Double-click to open.
Change the line that reads “VERSION 1.2.8” to read “VERSION 1.28”.
Finally, go to the Build -> Configuration Manager menu and change the Active Solution Configuration to “Release”.
Exit that window and press F7 (or click the Build -> Build Solution menu). The project should successfully build.
You can find your newly compiled zlibwapi.dll file in the /contrib/vstudio/vc11/x86/ZlibDllRelease/ folder.
It’s been awhile since I posted any news on PhotoDemon, but not because work has slowed – just the opposite, in fact! The development version of PD is cranking ahead full-steam, and thanks to a number of outside contributors, the next version will include a wider set of improvements than any previous version. There’s still quite a bit of testing and fine-tuning to do, so this article does not include a downloadable beta release – rather, the article is meant to serve as a preview of the upcoming 6.0 release and all the cool new features it provides. (Of course, developers or anyone with access to Visual Basic 6.0 can compile the latest version themselves by visiting PhotoDemon’s GitHub page. New testers and contributors are always welcome!)
First, an explanation on why the next PhotoDemon release will be version 6.0 instead of the expected 5.6. The next release will break backward compatibility with a number of PhotoDemon files, including any saved macros or filters. This break is necessary to implement a large overhaul of PhotoDemon’s internals – an overhaul that makes the program faster, smaller, more stable, and much easier to develop and maintain. The goal is to have all of PhotoDemon’s specialized file formats (including macros) use XML for storage. This allows both users and other software developers to read and edit PhotoDemon files from any general-purpose text editor. This change will also make it much easier to add new macro features without breaking old macro files. (The current macro format was developed over a decade ago, when the program was only meant for personal use, and it is extremely flimsy and difficult to extend – hence the need for a redesign.)
The downside of this change is that any current macros will need to be re-recorded in version 6.0, as version 4.X and 5.X macros will no longer be supported. I apologize for this inconvenience, and I promise to do my best to avoid breaking backward compatibility in the future.
The 6.0 release will also include important interface changes – such as a redesigned main menu and tool window – further supporting the switch to a new major version number, and for developers, the program’s central action processor has been redesigned from the ground up, making it easier than ever to get involved in development.
So with that out of the way, let’s talk about the good stuff, namely: what’s coming in 6.0? Here is a list of features and updates that are already finished and available in the current development build (again, downloadable at https://github.com/tannerhelland/PhotoDemon).
Italian language support
Courtesy of talented contributor GioRock is a new Italian language option for PhotoDemon. Many thanks to GioRock for this huge contribution.
Other internationalization improvements
With the help of GioRock and Frank Donckers (you may remember Frank as the brilliant developer behind PhotoDemon’s language translation engine), a number of other improvements are now available for international PhotoDemon users:
The comma “,” is now supported as a decimal separator in all tools. Previously, use of a comma could lead to critical errors.
Translated text is now automatically resized if it is larger than its tool window. This helps text in verbose languages remain fully readable.
Translations that span multiple lines (such as long tooltips) are now automatically handled by the program. This reduces the burden on translators to manually fit translated text longer than its English equivalent.
New feature: advanced selection tools
PhotoDemon 6.0 includes a completely redesigned selection tool engine. At present, the following dedicated selection tools are available:
Rectangular and Square selections (with optional rounded corners, including variable corner radii)
Elliptical and Circular selections
Line selections: unique to PhotoDemon, this tool allows you to select a line-shaped area, very helpful for things like tilt-shift effects (see below)
Each selection tool supports the following features:
Live selection coordinate and size display
On-canvas resizing by click-dragging nodes
Selections can be nudged or moved via text entry
Shift can be held to lock a 1:1 aspect ratio (e.g. squares or circles)
Live smoothing options: none, antialiased, or variable radius feathering (live feathering is only available on Windows 7)
Live selection types: interior, exterior, or bordered, with live border radius selection
In addition to these dedicated tools, a new Selection menu is available with additional selection-related features.
Select All and Select None
Invert Selection (switch selected and un-selected pixels, with full feathering support!)
Border selection, which takes the current selection and selects only its border
Feather and sharpen selection
Load and save selections
Thanks to the selection engine redesign, these features will automatically work with future selection tool implementations, including polygon/free-draw and “magic wand” selections.
Another huge improvement is integrating all selection actions into the Undo/Redo engine. If you create, move, resize, or apply any other action to a selection, you can now Undo/Redo that operation.
Selections are now fully integrated into the Record Macro tool.
Copy and Crop now support selections of any shape, making it trivial to crop circular or rounded-rectangle regions, or copy them for use in another program. (Feathered selections are automatically converted to 32bpp images, with the feathering applied in the alpha channel.)
Finally, the core Selection tools have been rewritten to use vector coordinates. This means that selections loaded from file are automatically resized to fit the current image, making them extremely useful for Batch Processing operations.
New image metadata (EXIF, XMP, IPTC) support
PhotoDemon now includes the marvelous ExifTool project as an optional plugin. ExifTool is the most comprehensive image metadata handler currently available, and PhotoDemon makes full use of its ability to handle every known type of image metadata, from the popular EXIF format (used in JPEGs) to obscure maker notes for all major DSLR brands.
A new integrated metadata browser automatically sorts metadata by category, and it allows the user to see actual or human-friendly metadata tags. The browser fully integrates with ExifTool’s multilanguage capabilities, sparing translators from any extra work!
When saving images, the Preferences manager now provides options for metadata embedding:
Unique to PhotoDemon is a privacy-centric metadata option, which aims to remove any personally identifying metadata entries, like serial numbers or GPS coordinates. By default, the “preserve all relevant metadata” option is recommended, which will remove any metadata not relevant to a file format (such as removing maker notes when saving RAW files to JPEG), but retain all other metadata entries. Metadata can also be fully stripped from exported files.
Also fun is a new Image -> Metadata -> Map GPS Coordinates option, which becomes available if an image contains GPS data. This option will automatically map the photo’s location in Google Maps.
New tools: too many to mention!
As always, the next release will include a host of new image editing tools. Here’s a small sampling of the latest additions to PhotoDemon’s repertoire:
For sake of brevity, I’ll forgo images of the rest of the new tools, namely:
Pan and zoom
Vibrance (developed by audioglider)
Other improvements and additions for end-users
Transparent images can now be copied/pasted between PhotoDemon and other software. This means you can take an image with multiple layers in GIMP and paste it into PhotoDemon fully composited.
Official RAW image format support; more than 20 RAW filetypes are now supported.
30-40% speed improvements to Gaussian Blur, Smart Blur, and Unsharp Masking thanks to an Integer-only rewrite of the blur engine.
Filters and other long-running actions can now be canceled mid-action by pressing ESC.
Revamped main window interface, as you can see in the screens above. The left-hand toolbar is now images-only, while the right-hand one has been expanded.
Better validation for all text controls. Invalid entries are automatically circled in red.
Alt+T will now let you switch between preview and non-preview modes in all tools.
Improvements and additions for developers and contributors
PhotoDemon can now provide timing reports for all actions passed through the central software processor. Simply enable the DISPLAY_TIMINGS constant when compiling.
New custom slider/text and up/down controls make it easy to utilize PD’s existing validation and translation abilities in your own tool dialogs.
A new string-based filter parameter class makes it easy to tie complex tools with many parameters into the software processor (and thus into recorded macros). No longer do you have to convert param lists to complex custom Variant embeddings.
PhotoDemon now includes a high-performance font rendering class, which makes custom font rendering (with AA) much easier to implement.
Dev builds, including build number, are now automatically detected by the program, making it easy to see which build you’re currently working with.
Support tools, including the custom plugin compressor and master translation file generator, are now synched to GitHub in the /Support subfolder.
A public histogram-generation routine is now available, so you can tap into PhotoDemon’s highly optimized histogram generator for any of your own tools.
Contributors, developers, and translators still welcome!
As always, PhotoDemon can never have enough external contributors, developers, and translators. If you can help with any aspect of the 6.0 release, don’t hesitate to get in touch. Many features in the 6.0 release wouldn’t be possible without outside help, and I’d love to add you to the ever-growing list of talented contributors that make PhotoDemon possible!
If you can’t contribute with coding or translations, donations are another great way to help. Thanks in advance for your small monetary contribution to this completely open-source project, which provides a full-featured photo editor (comprising 60,000 lines of code and more than 50,000 words of translated text in five languages) completely free of charge.
As in past years, all information in this report is taken from Microsoft’s publicly available 2013 10-K filing. Numbers may vary from past reports. When Microsoft moves products between revenue categories, they retroactively adjust the totals for past years so that year-to-year comparisons are accurate. This article uses 2011 and 2012 values as calculated in the 2013 report. All values are in USD.
If you’ve read my past reports, feel free to skip down to the charts. If this is your first time here, let me provide a quick explanation of how Microsoft breaks down its earnings.
Microsoft 2013 earnings tl;dr (“too long, didn’t read”)
Microsoft remained highly profitable in 2013, with solid year-over-year growth in both revenue and operating income.
The Business (Office) division brings in significantly more money than the Windows division (+30% revenue, +70% profit). In fact, nearly half of Microsoft’s 2013 profits came from the Business division alone.
For the first time ever (to my knowledge), the Windows division was actually 3rd in revenue in 2013, behind both Business and Server/Tools. If trends from the past four years continue in 2014, Server and Tools will pass Windows in not just revenue, but profitability as well.
Regardless of division, the vast majority of Microsoft’s profits come from business and OEM sales. Consumer-centric divisions (including XBox, Windows Phone, Bing) are largely irrelevant from a profit standpoint.
Just for fun: in 2012, Apple pulled in double the revenue of Microsoft ($156 billion USD and $74 billion, respectively). Source 1, Source 2.
Microsoft is unique among tech companies for reporting detailed information by product line. Their competitors do not provide such a detailed breakdown; Apple, most notably, is organized around “functional” divisions rather than “product” divisions, making direct financial comparisons between Apple product lines and Microsoft product lines difficult.
There are many theoretical benefits to organizing a company by “function” instead of “products.” One benefit is reduced infighting between product groups, a known problem for Microsoft. Another benefit is the ability to hide losses due to underperforming products. Microsoft had its share of those in the past year, most notably its billion-dollar loss on the Surface RT line of tablets, the impact of which can be seen in the charts below.
Microsoft Total Revenue and Operating Income (June 2012 – June 2013)
Total Revenue: $77,849,000,000
Operating Income: $26,764,000,000
Total Revenue is the total amount of money Microsoft takes in from normal business operations.
Operating Income is calculated as “Operating Revenue – Operating Expenses”. In other words, Operating Income is the profit made from normal business operations. (A more detailed definition is available from Investopedia: “Operating income would not include items such as investments in other firms, taxes or interest expenses. In addition, nonrecurring items such as cash paid for a lawsuit settlement are often not included. Operating income is required to calculate operating margin, which describes a company’s operating efficiency.”)
Operating Income is particularly important when looking at a company like Microsoft. Certain Microsoft divisions take in a great deal of money, but they also require much higher costs to operate. Thus it is relevant to look at not just how much money a certain division brings in, but at how efficiently that division generates its revenue.
Microsoft Revenue and Operating Income by Division (June 2012 – 2013)
Microsoft products (and earnings) are divided into five divisions: Windows, Microsoft Business, Server and Tools, Entertainment and Devices, and Online Services. The types of products and services provided by each segment are as follows.
Microsoft Business – Microsoft Office (including Office Web Apps and Office 365), Microsoft Exchange, Microsoft SharePoint, Microsoft Lync, Yammer (newly acquired in 2012), Microsoft Office Project and Office Visio, and Microsoft Dynamics ERP and CRM. As you’d expect, 85% of Microsoft Business revenue comes from businesses.
PhotoDemon 5.4.1 provides fixes for several issues found in version 5.4 (released two days ago). If you have automatic updates enabled, you will automatically be notified up the update, or you can manually download it here.
5.4.1 fixes the following bugs:
FIXED: Some controls do not display text correctly on Windows XP
FIXED: Some dialogs load very slowly when a translation is active
FIXED: Some edge detection methods fail to initiate when a translation is active
FIXED: Left-hand toolbox text formatting looks poor when a translation is active
FIXED: Tooltips not showing for picture box objects when a translation is active
FIXED: When the last-used folder in the batch process tool contains many images (1000+), the batch tool loads slowly on subsequent uses
FIXED: Minor typographical errors in translation files
This update also includes a few minor modifications and additions:
MODIFIED: In the batch process tool, when a selected image is removed from the batch list, its preview is now erased to prevent confusion
ADDED: further optimizations to translation engine. Program performance should now be much better while translations are active.
ADDED: batch process tool now displays the number of images in the current batch list
PhotoDemon 5.4 is complete. New features include language support (German, French, and Dutch), a full-featured batch processing wizard, shadow/highlight correction, nine new distort tools, vignetting, median noise removal, JPEG and PNG optimization, and more. Download it here.
Highlight feature: support for multiple languages!
This is the biggest addition in version 5.4, and I can only claim partial credit for it. Primary credit goes to Frank Donckers, a fellow VB programmer who prototyped the initial translation engine for me. As if that isn’t incredible enough, Frank also supplied the translations for French, German, and Dutch (Flemish), so I owe him an enormous debt of gratitude. Thank you, Frank!
One of the neatest aspects of this feature is the ability to change the language at run-time via the Language menu. Unlike every program I have ever used, no restart is required. PhotoDemon will dynamically change the program’s entire language immediately, and if you change your mind, you can switch to any other language at any time.
I hope these three languages are only the beginning. If you speak a language other than English, please consider contributing a new PhotoDemon translation! No programming knowledge is required, and you will receive full credit for your work.Contact me for more details.
Nine new Distort-style tools
Add and remove lens distortion. Swirl. Ripple. Pinch and whirl. Waves. Kaleidoscope. Polar conversion (both directions). Figured glass (dents).
Vastly improved file format support
JPEGs now support automatic EXIF rotation on import, and a variety of options on export (Huffman table optimization, progressive scan, thumbnail embedding, specific subsampling). TIFFs support CMYK encoding and a number of compression schemes (none, PackBits, LZW, CCITT 3 and 4, zLib, and more). PNG exporting supports variable compression strength, interlacing, and background color chunk preservation. PPMs can be exported with RAW or ASCII encoding. BMP and TGA files now support RLE encoding. And for icons, animated GIFs, and multipage TIFFs, all images inside a file can now be loaded (instead of just the first one).
These format settings can be accessed from the Tools -> Options menu, and the new Batch Process tool also provides direct access.
Revamped standard tools, including Box Blur, Gaussian Blur, Smart Blur, and Unsharp Masking.
PhotoDemon is now a much better photo editor, thanks to the revamp of its core convolution filters. Larger tool dialogs make it easier to see the result of your actions. Better performance means real-time previews, even at enormous radii (up to 200px for all filters, plus 500px for box blur!). And all convolution algorithms now use specialized edge handling code to make sure every part of the image – from center to border – is handled correctly.
Also, the program’s Gaussian Blur is now a true gaussian blur. There are no shortcuts, no estimations, and it’s still fast enough to preview in real-time.
New advanced color tools, including Shadow/Midtone/Highlight adjustments, color balancing, and monochrome-to-grayscale recovery
New stylize tools, including Film Grain, Vignetting, Modern Art, Trace Contour, Film Noir, and Comic Book
Noise removal via Median Filtering
Automatic image cropping
New Batch Process Wizard
If I had to pick a personal “favorite” new feature in this release, it would be the brand-new batch processing wizard. This tool is a highlight of PhotoDemon’s emphasis on usability, and I researched more than a dozen other image batch processing tools while building it. I could be biased, but I believe PhotoDemon is now the best general-purpose image batch processor available on the web.
Drag-and-drop is now supported when building the list of images to be processed – not only from within the dialog, by dragging between list boxes, but also from Windows Explorer. Live previews make it much easier to find the images you want, while helpful instructions on the left-hand side expose some of the more nuanced functionality.
Page 2 is the barest page of the new wizard. The current version allows you to skip photo editing actions (if you want to just do a batch rename or format conversion, for example), or you can apply any recorded macro. In the next release, I will add a set of “one-click” presets for common actions, like resizing, or optimizing images for the web.
Page 3 asks you to choose an output format. If you want to retain original image formats, that’s cool too – PhotoDemon now supports this! Alternatively, you can select a single output format, with access to the program’s full range of detailed format settings. In the example above, you can see all the options available for JPEGs, including new support for optimization (lossless file size reduction), thumbnails, progressive encoding, and specific subsampling.
The final page asks you to select an output folder where PhotoDemon can save the processed images. New to this release is a wide range of renaming options – things like adding custom text to each filename, removing text from each filename, changing case, and replacing spaces with underscores for web-bound images. Additionally, original filenames can be retained, or PhotoDemon can just use ascending numbers.
So that’s the new batch wizard! I’d love feedback from power users, as there are a lot of moving parts to the batch tool, and while I have been very thorough in my own testing, it’s impossible to test every combination of variables. So if you find anything that doesn’t work, please let me know.
As is usual with each PhotoDemon update, a number of existing tools received redesigns or new features. Gamma correction now displays live gamma curves, and each color component (red, green, and blue) can be adjusted individually. Dilate and Erode use a new algorithm that’s significantly more optimized, meaning sizes up to 200px radius can be previewed in real-time. Monochrome conversion supports any two color (not just black and white), while the printing and histogram dialogs were completely overhauled to make them more user-friendly.
Universal color depth support at import and export time
PhotoDemon can now write 1, 4, 8, 24, and 32bpp variations of every supported file format. By default, when saving images, color depth detection is completely automated – the program will count the number of colors in an image and automatically select the most appropriate color depth for the output file. Alternatively, you can set a preference to manually specify color depth at save time. This also works for grayscale images; for example, the JPEG encoder will now detect grayscale images and write out 8bpp JPEGs accordingly. Alpha thresholding is also available when saving 32bpp images to 8bpp (e.g. PNG to GIF).
This feature was a nightmare to implement, as PhotoDemon supports a huge variety of file formats, and each one has a detailed list of color depths it does or does not support. Full support for transparency adds a whole other layer of complexity. But now that the feature is completely implemented and rigorously tested, I can’t imagine it any other way. Color depth is not something users should have to worry about, and automatic handling should be a feature of every photo editor (rather than pestering you for color depth every time you save… *cough* GIMP *cough*).
New feature: pngnq-s9 plugin for optimizing PNG files
At the request of a good friend, PhotoDemon now provides integrated support for the pngnq-s9 variety of the famous pngnq library. For the uninitiated, pngnq provides a way to reduce 32bpp PNG files to 8bpp while still preserving complex alpha channels, allowing for file size reductions of up to 75%. Pngnq provides superior results over other tools by using a neural network to reduce image colors, unlike the brute-force median cut algorithm used by software like pngquant. See here for a gallery of sample images if you’re curious.
Pngnq-s9 is a further improvement over stock pngnq, including cool features like YUV color space matching for better results, and the ability to preserve alpha values of 0 and 255. When saving 32bpp PNG files to 8bpp, PhotoDemon will now lean on pngnq-s9 to do the heavy lifting.
In the next version of PhotoDemon, pngnq-s9 support will be integrated into the batch process wizard as a new “optimize for web” option. For now, if you want to test out the feature, head to Tools -> Options -> Saving, and change the “set outgoing color depth” option to “ask me what color depth I want to use”. Then save a 32bpp PNG image to 8bpp and compare the file size.
New plugin manager and plugin downloader
Sometimes it makes sense for PhotoDemon to use an existing open-source project instead of me writing a new feature from scratch. These support libraries are included as “plugins”, and there are four of them in current version. Each one provides indispensable features (like scanner support) at a fraction of the cost involved to write such a feature from scratch.
Some of these plugins expose additional functionality, but it has always been a challenge for PhotoDemon to expose these additional features to the user. So the program now has a detailed plugin manager, where advanced users can change settings on a per-plugin basis, including activating or deactivating plugins as necessary. The manager also tracks availability and version numbers of each plugin.
Many canvas and interface improvements
Larger effect and tool previews. Persistent zoom-in/zoom-out buttons. Image URLs and files can now be directly pasted as new images. Improved drag/drop support, including drag/drop from common dialogs. New “Safe” save behavior to avoid overwriting original files. New Close All Images menu. New algorithms for auto-zoom when images are loaded, meaning much better results at all screen sizes. Tool and file panels can now be hidden. Higher-quality dynamic icons for the program, taskbar, child windows, and Recent Images list. Improved support for low screen resolutions.
Program-wide performance improvements
More aggressive memory management means lower resource usage. Program loading has been heavily streamlined, and now happens in less than a second on modern hardware. Image loading is much faster and more robust, including better support for damaged or incomplete image files.
More robust and comprehensive error handling
When loading multiple images, the program will now suppress warnings and failures (such as invalid files) until all images have been loaded. Many subclassing issues have been resolved – so no more surprise crashes! Overall this release should be extremely stable.
This release was a lot bigger than I’d like future releases to be. The biggest delay came from adding language support, as that affected every piece of text in every part of the program (nearly 10,000 words in total!). Now that language support is complete, I foresee future releases being much tidier and quicker.
A developer’s work is never done, and a roadmap for version 5.6 is already being worked on. Some features that didn’t make the cut for 5.4 – like improvements to the selection tool, or a “smart resize” option – were cut at the last minute, and they will be among the first features added to 5.6. The batch process wizard will see a number of additions, and I’d love to add some advanced multilanguage features, like a way for casual users to fix or adjust translations on-the-fly. I also think I’m finally ready to tackle the monumental task of writing a user manual… should be fun!
Today I made an interesting discovery: my PhotoDemon release dates are slipping further and further apart.
PhotoDemon 4.3 – 10 August 2012
PhotoDemon 4.4 – 21 August 2012 (11 days later)
PhotoDemon 5.0 – 21 September 2012 (31 days later)
PhotoDemon 5.2 – 28 November 2012 (68 days later)
PhotoDemon 5.4 – …? (76 days and counting)
If I throw together a quick chart for the delay between releases, a clear trend emerges:
According to the chart, I still have a good for or five months available to work on the next release…
Actually, PhotoDemon 5.4 is rapidly nearing completion! My excuse for this latest delay is a good one, and I imagine you already inferred it from the title of the article… but in case you didn’t:
The next PhotoDemon release will include support for multiple languages, with French, German, and Dutch (Vlaams) officially supported at release.
Language support has been a monster to implement on account of the large amount of text in the project, not to mention classic VB’s utter lack of usable translation libraries. As a result, an entirely novel language engine was written from scratch, with (quite lovely) XML files being used to supply the actual translation data.
To give you an idea of the scope: as part of the translation process, I wrote a separate program whose sole purpose was to extract all necessary text from the PhotoDemon source code so that a “master” language file could be assembled. According to it, PhotoDemon contains almost 1400 unique phrases, with a total of more than 7800 words. Every one of those phrase occurrences needed code added to handle the actual text substitution, and then there’s the obvious challenge of the translation itself.
Fortunately, I didn’t tackle this project alone. An absolutely amazing contributor by the name of Frank Donckers contacted me with the initial prototype of the translation engine, and it is Frank who is supplying the French, German, and Dutch translation text. I could not have built this feature without him – so thank you, Frank!
At present, the translation engine is pretty much complete in terms of base functionality – all program text is translated on the fly, and the user is free to change languages at run-time at their leisure (no restart required!). The coding solution behind this is quite elegant, if I might say so, and users shouldn’t experience any noticeable performance hit while a translation is active. The only noticeable delay might be an additional second or two of start-up time on older machines, on account of the translation XML file being loaded and parsed. I’ve got some ideas for speeding up this process, however, so even that delay may disappear by release time.
I would love to include official support for additional languages. If you are fluent in a language other than English, please consider contributing a new translation!
No programming experience or specialized software is required to translate. I’ve got a master translation file ready to go – all that’s needed is to plug in the translated text in whatever language you might speak.
If you’re familiar with XML or HTML, you can see how simple the translation document is. Each phrase consists of original text and translated text, and that’s all there is to it. The lines in green are just comments added for convenience, in this case comments written by the language extraction tool. Translators can safely ignore these.
Before wrapping up, I should mention one rather large caveat with multiple language support – at present, only “ANSI” (Windows-1252) languages are supported. I apologize for this, but one of the problems with classic VB is its inability to handle unicode characters without major hacking – and by major hacking, I mean replacing every user interface aspect of the project, as well as every string library. If I ever port PhotoDemon to another programming language (something I often consider), Unicode support would be much more feasible, but I’m afraid it’s not on the present roadmap.
I need at least a couple more weeks to hammer out a few remaining issues with version 5.4, which leaves plenty of time for any ambitious translators out there to pitch in and contribute a new translation before release day. If it helps, note that your name will be visibly displayed as the translator in not only the language source file, but I’ll also add you to the special thanks section of the program, the PhotoDemon website, and the README file.
I can always be reached via this contact form – so that’s the place to go if you’re willing to help. Thank you in advance!
One of the new features in the development branch of my open-source photo editor is a simple tool for correcting lens distortion. I thought I’d share the algorithm I use, in case others find it useful. (There are very few useful examples of lens correction on the Internet – most articles simply refer to existing software packages, rather than explaining how the software works.)
Lens distortion is a complex beast, and a lot of approaches have been developed to deal with it. Some professional software packages address the problem by providing a comprehensive list of cameras and lenses – then the user just picks their equipment from the list, and the software applies a correction algorithm using a table of hard-coded values. This approach requires way more resources than a small developer like myself could handle, so I chose a simpler solution: a universal algorithm that allows the user to apply their own correction, with two tunable parameters for controlling the strength of the correction.
The key part of the algorithm is less than ten lines of code, so there’s not much work involved. The effect is also fast enough to preview in real-time.
Before sharing the algorithm, let me demonstrate its output. Here is a sample photo that suffers from typical spherical distortion:
Pay special attention to the lines on the floor and the glass panels on the right.
Here’s the same image, as corrected by the algorithm in this article:
My use of simple bilinear resampling blurs the output slightly; a more sophisticated resampling technique would produce clearer results.
A key feature of the algorithm is that it works at any aspect ratio – rectangular images, like the one above, are handled just fine, as are perfectly square images.
Anyway, here is the required code, as pseudocode:
strength as floating point >= 0. 0 = no change, high numbers equal stronger correction.
zoom as floating point >= 1. (1 = no change in zoom)
set halfWidth = imageWidth / 2
set halfHeight = imageHeight / 2
if strength = 0 then strength = 0.00001
set correctionRadius = squareroot(imageWidth ^ 2 + imageHeight ^ 2) / strength
for each pixel (x,y) in destinationImage
set newX = x - halfWidth
set newY = y - halfHeight
set distance = squareroot(newX ^ 2 + newY ^ 2)
set r = distance / correctionRadius
if r = 0 then
set theta = 1
set theta = arctangent(r) / r
set sourceX = halfWidth + theta * newX * zoom
set sourceY = halfHeight + theta * newY * zoom
set color of pixel (x, y) to color of source image pixel at (sourceX, sourceY)
That’s all there is to it. Note that you’ll need to do some bounds checking, as sourceX and sourceY may lie outside the bounds of the original image. Note also that sourceX and sourceY will be floating-point values – so for best results, you’ll want to interpolate the color used instead of just clamping sourceX and sourceY to integer values.
I should mention that the algorithm works just fine without the zoom parameter. I added the zoom parameter after some experimentation; specifically, I find zoom useful in two ways:
On images with only minor lens distortion, zooming out reduces stretching artifacts at the edges of the corrected image
On images with severe distortion, such as true fish-eye photos, zooming-out retains more of the source material
If we attempt to correct the image without applying any zoom, the image must be stretched so far that much of the edges are lost completely:
By utilizing a zoom parameter, it is possible to include more of the image in the finished result:
Again, I only use a simple resampling technique; a more sophisticated one would produce clearer results at the edges.
If you’d like to see my actual source code, check out this GitHub link. The fun begins at line 194. I also include an optional radius parameter, which allows the user to correct only a subset of the image (rather than the entire thing), but other than that the code is identical to what you see above.