14
$\begingroup$

Bug introduced in v9 or earlier and persisting through v10.3.0


There are 3 ways to convert a Raster into an Image : only 1 works for me with versions 10.0.1,10.0.2,10.1.0,10.2.0,10.3.0 , and 2 work with version 9 (same computer, OS X 10.9.5)

Has anyone the same problem or is it localized to me and why ?

(This question is actually related to a previous post concerning a problem to import DICOM images)

Here are the tests :

0. The test object

First, let' s define the test object : a Raster with specific rectangular shape and scale.

data = {{-90, 1, 50}, {30, 0.5, -30}, {75, 1000, -1900}};
shape = {{0, 0}, {10, 2}};
scale = {-100, 100};

myraster = Raster[data, shape, scale];

This is how it looks :

Graphics[myraster, Axes -> True]

enter image description here

For comparison, this is how it looks when you omit the shape and scale :

Graphics[Raster[data], Axes -> True]

enter image description here

1. Image@Raster

According to the documentation (V9 or v10), it should be possible to convert a Raster primitive directly into an Image object :

doc. Raster

Whether I am using version 9 or 10.0.1, the raster is not correctly converted: the shape and scale of the raster were not taken into account !?

Image@myraster
Through@{Head, ImageType, ImageDimensions, Options}[%]

enter image description here

In versions 10.0.2, 10.1.0, 10.2.0,10.3.0 the output is a little bit different but still not correct:

enter image description here

2. Image@Graphics@Raster

This conversion works in version 9 but not in version 10.0.1, 10.0.2, 10.1.0, 10.2.0

Image@Graphics@myraster
Through@{Head, ImageType, ImageDimensions, Options}[%]

The result looks like Image@Raster:

v10.0.1:

enter image description here

v10.0.2, v10.1.0, v10.2.0, v10.3.0:

enter image description here

v.9 : OK !

enter image description here

3. Rasterize: OK but ...

According to the documentation (V9 or v10), Image@Graphics effectively uses the Rasterize function.

enter image description here

This is OK, it works for me the same way with both v9, but also with v10.0.1, v10.0.2, v10.1.0, v10.2.0, v10.3.0 !

enter image description here

But how is it possible that in v10, Image@Graphics does not work if it effectively uses Rasterize which does work ... !??

4. To sum up

enter image description here

$\endgroup$
  • $\begingroup$ All: Based on my analysis (below) I believe this is a bug therefore I am tagging it as such. If anyone disagrees please let me know! $\endgroup$ – Mr.Wizard Oct 29 '14 at 1:04
  • $\begingroup$ Has there been any attempt to fix the bug? $\endgroup$ – Ali Hashmi Jul 19 '18 at 8:20
  • $\begingroup$ @AliHashmi Probably no as it is still the same problem in v. 11.3.0 (at least on OSX). $\endgroup$ – SquareOne Jul 19 '18 at 22:28
9
$\begingroup$

Good question. I believe it is the result of an incomplete attempt to optimize conversion of Raster objects to Image objects; a bug in other words. Note that when the axes are included the output is correct:

Image @ Graphics[myraster, Axes -> True]  (* v10.0.1 *)

enter image description here

Trace of the correct conversion

Running a Trace with option TraceInternal -> True on Image @ Graphics[myraster, Axes -> True] (very slow to print) reveals that this call is made:

MathLink`FrontEndBlock[
 MathLink`CallFrontEnd[
  ExportPacket[
   Notebook[{Cell[
      BoxData[GraphicsBox[
        RasterBox[{{-90, 1, 50}, {30, 0.5`, -30}, {75, 1000, -1900}}, {{0, 0}, {10, 
           2}}, {-100, 100}], Axes -> True]], "Output", ShowCellBracket -> False, 
      Magnification -> 1.`, Background -> Automatic, CellContext -> "Global`", 
      GraphicsBoxOptions -> {ImageSize -> Medium}, 
      Graphics3DBoxOptions -> {ImageSize -> Medium}, 
      InsetBoxOptions -> {DefaultBaseStyle -> {"Inset", 
          GraphicsBoxOptions -> {ImageSize -> Automatic}, 
          Graphics3DBoxOptions -> {ImageSize -> Automatic}}}]}, 
    WindowSize -> {550.`, 360.`}], "BitmapPacket", 
   ColorSpace -> RGBColor, Verbose -> True, "AlphaChannel" -> False, 
   "DataCompression" -> True]], LinkObject["daahs_shm", 3, 1]]

This sends an ExportPacket of type "BitmapPacket" to LinkObject["daahs_shm", 3, 1] which is apparently a library that does the actual conversion.

Note that the complete Raster data is preserved in this ExportPacket in the form of a RasterBox.

  • The same call appears in the Trace of Rasterize @ Graphics @ myraster in v10 and in Mathematica 7.0.1 when evaluating Image @ Graphics @ myraster except for a few variations such as the name of the LinkObject.

Trace of the incorrect conversion

However when Image[myraster] is used something else entirely is observed. First it is handed off to:

Image`FromRaster[Raster[{{-90,1,50},{30,0.5,-30},{75,1000,-1900}},{{0,0},{10,2}},{-100,100}]]

The array data is extracted (omitting your shape and scale data):

Image`ImageDump`array$2281 = 
 Raster[{{-90, 1, 50}, {30, 0.5, -30}, {75, 1000, -1900}}, {{0, 0}, {10, 2}}, {-100, 
    100}][[1]]
{{-90, 1, 50}, {30, 0.5, -30}, {75, 1000, -1900}}

This data is "massaged" a bit for color space, packing, etc., then sent to Image, e.g.:

Image[Image`ImageDump`array$2281, OptionValue[Image`ImageDump`info$2279, DataType], 
 ColorSpace -> Image`ImageDump`cs$2281, Interleaving -> Image`ImageDump`il$2281]

Some other options are used but nowhere in this call is the shape or scale data used.

When the Graphics expression contains only a Raster a different function is called but the result is the same. First it is passed to:

Image`FromGraphicsRaster[\!\(\*
GraphicsBox[
    RasterBox[{{-90, 1, 50}, {30, 0.5, -30}, {75, 1000, -1900}}, {{0, 0}, {10, 2}}, {-100,
      100}]]\)]

So we have conversion to Box form, unlike Image[myraster], but then the array data is extracted and passed to Image as above, again without accounting for the second and third parameters of Raster (or RasterBox) as far as I can tell.

It is worth noting that the Trace on Image[myraster] is much shorter than on the full conversion shown at the top of this answer, so the idea of optimization is not misplaced. However it is not yet complete.

Proposed workaround

For now it is possible to bypass this incomplete optimization merely by wrapping the Raster in List:

Image @ Graphics[{myraster}]

enter image description here

$\endgroup$
  • $\begingroup$ Great ! And, what is your conclusion concerning Rasterize ? $\endgroup$ – SquareOne Oct 29 '14 at 11:08
  • $\begingroup$ Also, please could you tell me what is the exact syntax you use to Trace. Before posting I tried that on Image, but for example the output of Trace[Image[myraster]] gives me no information (it just repeats the command, shows the data and the result, that's all ...). But using the same form to Trace Rasterize, it gives me pages of detailed info ... $\endgroup$ – SquareOne Oct 29 '14 at 11:20
  • $\begingroup$ @SquareOne I did not Trace Rasterize yet but I will do so. I expect that a similar ExportPacket call will occur. For Trace you need to add the option TraceInternal -> True to see behind the curtain but be careful as there is a considerable chance you will hang Mathematica. In v10 the front end freezes while printing (unlike v7) but it is still working so be patient; however you should watch the RAM usage as it continually increases and you may need to terminate Mathematica. $\endgroup$ – Mr.Wizard Oct 29 '14 at 20:43
  • $\begingroup$ @SquareOne If printing the entire trace (i.e. "show all") is not possible you will have to capture the output of Trace and view it one piece at a time. $\endgroup$ – Mr.Wizard Oct 29 '14 at 20:46
  • 2
    $\begingroup$ +1 A nice bit of detective work. I think you are correct about the optimisation. If you set SetSystemOptions["ImageProcessingOptions" -> {"Verbose" -> True}] you get some debug output referring to "fast conversion". $\endgroup$ – Simon Woods Oct 29 '14 at 21:21

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.