Match legend and Plot size

2019-05-06 15:44发布

问题:

Please Consider :

intense = Reverse[Round[Rationalize /@ N[10^Range[0, 3, 1/3]]]];
values = Range[0, 9/10, 1/10];

intensityLegend = Column[Prepend[MapThread[
                         Function[{intensity, values},
                         Row[{Graphics[{(Lighter[Blue, values]),
                         Rectangle[{0, 0}, {4, 1}], Black, 
                         Text[Style[ToString[intensity], 16, Bold], {2, .5}]}]}]],
                        {intense, values}], Text[Style["Photons Number", Bold, 15]]]];

IntersectionDp1={{1., 588.377}, {2.15443, 580.306}, {4.64159, 573.466}, {10.,560.664}, 
                 {21.5443, 552.031}, {46.4159, 547.57}, {100.,545.051}, 
                 {215.443, 543.578}, {464.159, 542.281}, {1000., 541.346}}


FindD1=ListLogLinearPlot[Map[List, IntersectionDp1], 
                  Frame -> True, 
                  AxesOrigin -> {-1, 0}, 
                  PlotMarkers -> 
                  With[{markerSize = 0.04}, {Graphics[{Lighter[Blue, #], Disk[]}], 
                       markerSize} & /@Range[9/10, 0, -1/10]], Filling -> Axis, 
                  FillingStyle -> Opacity[0.8], 
                  PlotRange -> {{.5, 1100}, {540, 600}},
                  ImageSize->400];

Grid[{{intensityLegend, FindD1}, {intensityLegend, FindD1}}, 
      ItemSize -> {50, 20}, Frame -> True]

How could I get the legend Column Size to Fit the Height of the Plot Area ?

While Row adjust the size I need to use Grid. This is why I duplicated in grid.

回答1:

Working with Image Sizes. The (* <- *) marks the important modifications to your code, the rest are mainly font size thingies:

intense = Reverse[Round[Rationalize /@ N[10^Range[0, 3, 1/3]]]];
values = Range[0, 9/10, 1/10];
imgSize = 400;                                                          (* <- *) 
Off[Ticks::ticks]

IntersectionDp1 =  {{1., 588.377},     {2.15443, 580.306}, {4.64159, 573.466}, 
   {10., 560.664}, {21.5443, 552.031}, {46.4159, 547.57},  {100., 545.051},
   {215.443, 543.578}, {464.159, 542.281}, {1000., 541.346}}

FindD1 = ListLogLinearPlot[Map[List, IntersectionDp1], Frame -> True, 
   AxesOrigin -> {-1, 0}, 
   PlotMarkers -> 
    With[{markerSize = 0.04}, 
     {Graphics[{Lighter[Blue, #], Disk[]}], markerSize} & 
       /@ Range[9/10, 0, -1/10]], Filling -> Axis, FillingStyle -> Opacity[0.8], 
       PlotRange -> {{.5, 1100}, {540, 600}}, ImageSize -> imgSize];    (* <- *) 

intensityLegend =
  Rasterize[Column[
    Prepend[
     Reverse@MapThread[                                                 (* <- *) 
      Function[{intensity, values}, 
       Row[{Graphics[{(Lighter[Blue, values]), 
           Rectangle[{0, 0}, {4, 1}], Black, 
           Text[Style[ToString[intensity], 30, Bold], {2, .5}]}]}]],
      {intense, values}],
     Text[Style["Photons Number", Bold, 25]]]], 
   ImageSize -> {Automatic,                                             (* <- *) 
     IntegerPart@                            
      First[imgSize Cases[AbsoluteOptions[FindD1], 
         HoldPattern[AspectRatio -> x_] -> x]]}];

Grid[{{intensityLegend, FindD1}, {intensityLegend, FindD1}}, Frame -> True]

Where I reversed the intensities column for aesthetic purposes.

Edit

If you don't explicitly specify the ImageSize option for the Plot, you'll disappointingly find that AbsoluteOptions[Plot, "ImageSize"] returns "Automatic" !

Edit Answering the @500's comment bellow

The expression:

   ImageSize -> {Automatic,                                             (* <- *) 
     IntegerPart@                            
      First[imgSize Cases[AbsoluteOptions[FindD1], 
         HoldPattern[AspectRatio -> x_] -> x]]}];

is really a working replacement for something that should work but doesn't to get the image size of a Plot:

   ImageSize -> {Automatic, Last@AbsoluteOptions[FindD1,"ImageSize"]}   

So, what the IntegerPart[...] thing is doing is getting the vertical size of the plot image, multiplying imgSize by the AspectRatio of the Plot.
To understand how it works, run the code and then type:

AbsoluteOptions[FindD1] 

and you will see the Plot options there. Then the Cases[] function is just extracting the AspectRatio option.

In fact there is a cleaner way to do what the Cases[] does. It is:

AbsoluteOptions[FindD1,"AspectRatio"] 

but there is another bug in the AbsoluteOptions function that prevents us to use it this way.



回答2:

How about making the legend a bit smaller?

intensityLegend = 
  Column[Prepend[
    MapThread[
     Function[{intensity, values}, 
      Row[{Graphics[{(Lighter[Blue, values]), 
          Rectangle[{0, 0}, {4, 1}], Black, 
          Text[Style[ToString[intensity], 12, Bold], {2, .5}]}, 
         ImageSize -> 50]}]], {intense, values}], 
    Text[Style["Photons Number", Bold, 15]]]];