0
$\begingroup$

I have a rather complex looking plot which is a combination of graphics objects, generated by

data = Import["o2ld.csv"];
data2 = Import["stemld.csv"];

a1 = ListContourPlot[data, Contours -> 25, Axes -> False, 
PlotRangePadding -> 0, Frame -> False, 
ColorFunction -> "DarkRainbow", PlotRange -> {0.001, 100}];

a2 = ListPlot3D[data2, ClippingStyle -> None, Mesh -> None, 
ColorFunction -> "TemperatureMap", PlotRange -> {0.001, 1}, 
PlotStyle -> Opacity[0.33]];

level = -0.01; gr = 
Graphics3D[{Texture[a1], EdgeForm[], 
 Polygon[{{0, 0, level}, {200, 0, level}, {200, 200, level}, 
{0, 200, level}}, 
 VertexTextureCoordinates -> {{0, 0}, {1, 0}, {1, 1}, {0, 
 1}}]}, Lighting -> "Neutral"];

 out = Show[a2, gr, PlotRange -> All, BoxRatios -> {1, 1, 1}, 
 BoxStyle -> Directive[Dashed, Black, Thin], 
 ViewPoint -> {-0.35, -2, 1.5}, 
 AxesLabel -> {"x", "y", "Proportion"}, 
 LabelStyle -> Directive[Blue, Bold], 
 Ticks -> {{{0, 0}, {40, 0.5}, {80, 1}, {120, 1.5}, {160, 2}, 
 {200,  2.5}}, {{0, 0}, {40, 0.5}, {80, 1}, {120, 1.5}, {160, 
 2}, {200,  2.5}}, {0, 0.5, 1}}, ImageSize -> Large]

Which produces graphics like; enter image description here

What I would like to do is add a bar legend to the right of the right, based on the values from data (a1). I can create the precise bar easily enough with

 vr = BarLegend[{"DarkRainbow", {0, Max[data]}}, 25];

But as this is not a graphics object, I cannot get it to display in with Show. Nor can I seem to get it working with epilog or inset. Does anyone have any idea how to include the bar to the right? I can included csv files for ease of recreation if required, downloadable in a RAR here.

$\endgroup$
2
$\begingroup$

This is one of those "I'm not even sure how to ask this" kind of questions. You could be asking any (or all) of the following questions.

How do I add a legend to appear on a ListContourPlot?

All you need to do is add PlotLegends->Automatic to your ListContourPlot:

a1=ListContourPlot[data, Contours->25,Axes->False,
  PlotRangePadding->0, Frame->False,ColorFunction->"DarkRainbow", 
  PlotRange->{0.001,100}, PlotLegends->Automatic];

The legend will be drawn on the same 3D surface as its associated plot.

How do I make a BarLegend object into a Graphics object?

It already is a Graphics object in StandardForm. From the docs:

BarLegend is displayed in StandardForm as a graphics object.

How do I place a Graphics object in the Epilog of a Graphics3D object?

Use Epilog with Inset to position the object.

vr = BarLegend[{"DarkRainbow", {0, Max[data]}}, 25];
out = Show[a2, gr, PlotRange -> All, BoxRatios -> {1, 1, 1}, 
BoxStyle -> Directive[Dashed, Black, Thin], 
ViewPoint -> {-0.35, -2, 1.5}, 
AxesLabel -> {"x", "y", "Proportion"}, 
LabelStyle -> Directive[Blue, Bold], 
Ticks -> {{{0, 0}, {40, 0.5}, {80, 1}, {120, 1.5}, {160, 2}, 
{200,  2.5}}, {{0, 0}, {40, 0.5}, {80, 1}, {120, 1.5}, {160, 
2}, {200,  2.5}}, {0, 0.5, 1}}, ImageSize -> Large, 
Epilog -> Inset[vr, {Right, Center}, {Right, Center}]]

The object will sit in front of the 3D object and will not move as the 3D object is rotated.

How do I place a Graphics object wherever I want in the scene of a Graphics3D object?

It should be the same as you did with the ListContourPlot a1, but the ListPlot3D a2 disappears every time I try it. Must be a bug.

vr = BarLegend[{"DarkRainbow", {0, Max[data]}}, 25];
legendLeft = 190; legendWidth = 40; 
legendHeight = 200; legendDepth = 100;
legend3D = 
  Graphics3D[{EdgeForm[], {Texture[
      Rasterize[vr, Background -> None, ImageResolution -> 200]], 
     Polygon[{{legendLeft, legendDepth, 0}, {legendLeft + legendWidth,
         legendDepth, 0}, {legendLeft + legendWidth, legendDepth, 
        legendHeight}, {legendLeft, legendDepth, legendHeight}}, 
      VertexTextureCoordinates -> {{0, 0}, {1, 0}, {1, 1}, {0, 1}}]}}];

out = Show[a2, gr, legend3D, PlotRange -> All, BoxRatios -> {1, 1, 1},
   BoxStyle -> Directive[Dashed, Black, Thin], 
  ViewPoint -> {-0.35, -2, 1.5}, 
  AxesLabel -> {"x", "y", "Proportion"}, 
  LabelStyle -> Directive[Blue, Bold], 
  Ticks -> {{{0, 0}, {40, 0.5}, {80, 1}, {120, 1.5}, {160, 2}, {200, 
  2.5}}, {{0, 0}, {40, 0.5}, {80, 1}, {120, 1.5}, {160, 2}, {200, 
  2.5}}, {0, 0.5, 1}}, ImageSize -> Large]

$\endgroup$
  • $\begingroup$ Excellent answer! Thank you! $\endgroup$ – DRG Jan 7 at 20:13
0
$\begingroup$

Following on from the excellent answer by Robert Jacobson, I eventually found it's possible too to use placed with the graphics object in A2, as laid out below.

data = Import["o2ld.csv"];
data2 = Import["stemld.csv"];

a1 = ListContourPlot[data, Contours -> 25, Axes -> False, 
PlotRangePadding -> 0, Frame -> False, 
ColorFunction -> "DarkRainbow", PlotRange -> {0.001, 100}];

 a2 = Legended[
 ListPlot3D[data2, ClippingStyle -> None, Mesh -> None, 
ColorFunction -> "TemperatureMap", PlotRange -> {0.001, 1}, 
PlotStyle -> Opacity[0.33], ImageSize -> 500], 
 Placed[BarLegend[{"DarkRainbow", {0, Max[data]}}, 25, 
 LegendLayout -> "Row", LegendMarkerSize -> 500, 
 LabelStyle -> {FontSize -> 16}], Below]];

level = -0.01; gr = 
Graphics3D[{Texture[a1], EdgeForm[], 
Polygon[{{0, 0, level}, {200, 0, level}, {200, 200, level}, {0, 
  200, level}}, 
VertexTextureCoordinates -> {{0, 0}, {1, 0}, {1, 1}, {0, 1}}]}, 
Lighting -> "Neutral"];

vr = BarLegend[{"DarkRainbow", {0, Max[data]}}, 25];

out = Show[a2, gr, PlotRange -> All, BoxRatios -> {1, 1, 1}, 
 BoxStyle -> Directive[Dashed, Black, Thin], 
 ViewPoint -> {-0.35, -2, 1.5}, 
 AxesLabel -> {" mm", "  mm", "Ratio"}, 
 LabelStyle -> {Directive[Black], FontSize -> 15}, 
 PlotLabel -> 
  Style["(a) (i) Spatial map of stem divisions", FontSize -> 20], 
  Ticks -> {{{0, 0}, {40, 0.5}, {80, 1}, {120, 1.5}, {160, 2}, {200, 
   2.5}}, {{0, 0}, {40, 0.5}, {80, 1}, {120, 1.5}, {160, 2}, {200,
    2.5}}, {0, 0.5, 1}}, ImageSize -> 700];

This yields the image below (with minor stylistic differences to original, just for clarity, but idea should be there). So this is another option anyway!

enter image description here

$\endgroup$

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.