RE: GridPlot
- To: mathgroup at smc.vnet.net
- Subject: [mg45869] RE: [mg45795] GridPlot
- From: "Wolf, Hartmut" <Hartmut.Wolf at t-systems.com>
- Date: Wed, 28 Jan 2004 05:19:06 -0500 (EST)
- Sender: owner-wri-mathgroup at wolfram.com
>-----Original Message----- >From: Selwyn Hollis [mailto:sh2.7183 at misspelled.erthlink.net] To: mathgroup at smc.vnet.net >Sent: Sunday, January 25, 2004 9:05 AM >To: mathgroup at smc.vnet.net >Subject: [mg45869] [mg45795] GridPlot > > >I've never much liked the way the GridLines option works in Plot. So >for my own amusement I decided to try something different, and it >turned into a nice exercise, I think. I thought some of you might be >interested in the result, which is the following (rough) >function named >GridPlot. What it basically does is stretch automatically-generated >tickmarks out to form grid lines. (The GridColor option lets you can >change their color.) > > >GridPlot[f_, {x_, xmin_, xmax_}, opts___] := > Module[{a, b, c, d, grph, fullgrph, gridcolor}, > gridcolor = GridColor /. {opts} /. > {GridColor -> GrayLevel[0.85]}; > fullgrph = FullGraphics[grph = Plot[f, {x, xmin, xmax}, > DisplayFunction -> Identity, > Evaluate[DeleteCases[{opts},GridColor->_]]]]; > {{a, b}, {c, d}} = PlotRange /. AbsoluteOptions[grph]; > Show[ fullgrph /.{ > {GrayLevel[0.], AbsoluteThickness[t_], > Line[{{u_,y1_},{u_,y2_}}]}/; (y2-y1<d-c) -> > {gridcolor, AbsoluteThickness[t], Line[{{u,c},{u,d}}]}, > {GrayLevel[0.], AbsoluteThickness[t_], > Line[{{x1_,y_},{x2_,y_}}]}/; (x2-x1<b-a) -> > {gridcolor, AbsoluteThickness[t], Line[{{a,y},{b,y}}]} > }, > grph, PlotRange -> {{a,b},{c,d}}, Axes -> True] ] > >GridPlot[{1/x, Cos[x], Sin[x]}, {x, 0, 2Pi}] > > > >Regards, >----- >Selwyn Hollis >http://www.math.armstrong.edu/faculty/hollis >(edit reply-to to reply) > Selwyn, as you declare this as a programming exercise I'm free to make comments and to propose an alternative. First, I agree that the Plot options in general, and for the GridLines in particular are not easy to master. If this constitutes a problem for the (not so experienced) users of your code, your students e.g., it appears appropriate to supply a more convenient interface. My own private attitude is different however: try to understand -- albeight this might cost some effort -- the basics (as is part of core Mathematica) precisely. This avoids irritations if something goes wrong: I then simply have one interface _less_ to struggle with. The point may be simply illustrated by GridPlot[{1/x, Cos[x], Sin[x]}, {x, 0, 2Pi}, AspectRatio -> Automatic] against Plot[{1/x, Cos[x], Sin[x]}, {x, 0, 2Pi}, AspectRatio -> Automatic, GridLines -> ({Thread[{Range[.2, 6.4, .2], xStyle}], Thread[{Range[-1., 4., .2], yStyle}]} /. {xStyle | yStyle -> {GrayLevel[.85]}})] I would not say that the GridLines option was overly complex (but might need some trial and error). As you see, your proposed GridPlot looses the option AspectRatio, e.g. There are other minor points of passing the options, which you can read off my alternative example (coming below soon). Obviously you had to struggle to get at the Ticks to make your gridlines from. The solution appears to be delicate. Drawing the gridlines as primitives (instead of options to Show) forces you to draw the graphics twice (which redundantly blows up the Graphics objects). Finally everything is dedicated to Plot. Here I propose a different solution, namely wrapper code which is thought to cooperate with more (all?) plot functions. I also define the default coloring of the grid as a default option. Needs["Utilities`FilterOptions`"] Options[makeGrid] = {GridStyle -> GrayLevel[0.85]}; Attributes[makeGrid] = HoldAll; makeGrid[plotfcn_[args__, opts___?OptionQ]] := Module[{grph, gridstyle}, gridstyle = Flatten[{GridStyle /. Flatten[{opts}] /. Options[makeGrid]}]; grph = Block[{$DisplayFunction = Identity}, With[{plotopts = FilterOptions[plotfcn, opts]}, plotfcn[args, plotopts]]]; Show[grph, GridLines -> Take[If[Frame /. Options[grph, Frame], FrameTicks, Ticks] /. FullOptions[grph], 2] /. {pos_, _, _, _} :> {pos, gridstyle}, FilterOptions[Graphics, opts]]] As you see, I extract the grid positions from the FrameTicks or Ticks via the standard (stable?) interface. I also allow to specify more than one graphical directive for the grid lines. Examples of usage: Needs["Graphics`Graphics`"] Plot[{1/x, Cos[x], Sin[x]}, {x, 0, 2Pi}, GridStyle -> {Hue[0, .2, 1], Thickness[.01]}, AspectRatio -> Automatic] // makeGrid pp = LogLogPlot[Exp[2x/Pi + Sin[x]], {x, 0., 6}] // makeGrid PolarPlot[{4/(2 + Cos[t]), 4 Cos[t] - 2}, {t, 0, 2 Pi}, AspectRatio -> Automatic, Frame -> True, PlotStyle -> {Hue[2/3], Hue[0]}] // makeGrid So you just add the new GridStyle option to the other plotting options and wrap with makeGrid. A warning in place: this is just a coding example, *not* released production code. It should be put into a package first, then its should defend against misuse (with not a plot function), and this must be done in a way as not to introduce problems with the sequence of loading graphical packages. Another point of weakness is the grabbing of the frame ticks. I simply take them from the bottom and the left; but there might be none there. It's however not difficult to solve this ("I leave it as an exercise"), and similar cases. Then you must go through extensive testing, of course -- but I will not do this work, that is beyond a post to the newsgroup. Perhaps the best way would be to incorporate this into the Graphics`Graphics` package (which then also would supply the necessary extension for Plot), and leave the function makeGrid invisible to the user (everthing would be directed by the option then). However, this should be released from WRI, I myself would never do that, in order to keep my code compatible with the "mainstream". Kind regards, yours, Hartmut
- Follow-Ups:
- Re: RE: GridPlot
- From: Selwyn Hollis <sh2.7183@misspelled.erthlink.net>
- Re: RE: GridPlot