Controlling the placement of the y-axis

I use ListPlot for showing the results of my numeric computation.

I make my own ticks, so I never know before hand where the vertical center of my plot will be. I want to put the y-axis in the center (because it's a center of symmetry in my task) of the plot by default. I know about AxesOrigin, but it doesn't take Center as a value. How can I put the y-axis in the center automatically without caring about ticks?

-
We really need to know the form of the data you give toListPlot takes. Is it {y1, y2, ..., yn} or is it {{x1, y1}, {x2, y2}, ..., {xn, yn}}? –  m_goldberg Jul 28 at 12:17
I use the first variant of data. –  user12297 Jul 28 at 15:43

Assuming the data is just a list of y-ordinates.

data = Table[Exp[-x^2], {x, -2., 2., .1}];
lbls = Range[-2., 2., .5];
xTicks = {Rescale[#, {-2., 2.}, {1, Length@data1}], #} & /@ lbls;


The center of plot will be at Length[data] + 1)/2., so AxesOrigin can be used to place the y-axis:

ListPlot[data,
Joined -> True,
Ticks -> {xTicks, Automatic},
AxesOrigin -> {(Length[data] + 1)/2., Automatic}]


-
Thank you very much! –  user12297 Jul 28 at 15:45

You may use:

center[gr_Graphics] := Show[gr, AxesOrigin -> {Mean @ First @ PlotRange @ gr, 0}]


Example:

dat = Table[TriangleWave[x] + RandomReal[0.3], {x, 3/4, 7/4, 0.01}];

ListPlot[dat] // center


The code above assumes you want to place the horizontal axis at zero. You could use Automatic instead for default placement, or if you wish to center both axes you can use:

centerXY[gr_Graphics] := Show[gr, AxesOrigin -> Mean /@ PlotRange @ gr]


As eldo commented and m_goldberg alluded to above if your data is of the form {y1, y2, y3, ...} you can use simply: AxesOrigin -> {Length@dat / 2, 0}. I felt that this was a trivial solution and unlikely to be the situation that precipitated the question.

-
@Mr.Wizard Length@dat/2. would give the same result: 50.5 –  eldo Jul 28 at 13:01
@eldo Only for data of the form {y1, y2, y3, ...}. My method will also handle {{x1, y1}, {x2, y2}, ...}. I suppose I should include that point in the answer. –  Mr.Wizard Jul 28 at 13:05
@Mr.Wizard I think the latter case could be handled with mid = (data[[-1, 1]] - data[[1, 1]])/2 –  eldo Jul 28 at 13:07
@eldo Frankly I didn't think of that. You'll need to pick between those two forms based on the data (to make it universal) but that should be a good solution. Why don't you post an answer? –  Mr.Wizard Jul 28 at 13:09
@Mr.Wizard How about you take my figures and I delete my answer? :) You get all the votes anyway ;o( –  Öskå Jul 28 at 13:28

Would something like that fit?

Module[{p = ListPlot[Thread@{Sort@RandomReal[{-500, 140}, 100],
Sort@RandomReal[{-1, 1}, 100]},
Filling -> Axis, ImageSize -> 300], r},
r = PlotRange /. AbsoluteOptions[p, PlotRange];
GraphicsRow@{p, Show[p, AxesOrigin -> {Mean@r[[1]], Automatic}]}]


-
Well nuts. I didn't see this answer before posting. (Blind?) I just posted something very similar, though I think a bit cleaner. Would you like me to edit your answer to include (or replace with) that, or shall I leave my answer? –  Mr.Wizard Jul 28 at 12:38
@Mr.Wizard I don't mind the two answers, the idea is the same but yours is cleaner indeed. Although I like my figures the most :D at least on can see the different before/after :) –  Öskå Jul 28 at 12:40
Okay. And I agree your plots look nicer. :-) –  Mr.Wizard Jul 28 at 12:41

Using Mr. Wizard's data the same plot could be obtained with

ListPlot[dat, AxesOrigin -> {Length@dat/2, 0}]


With given X-coordinates like in

dat = {{0, 0}, {1, 2}, {2, 3}, {3, 4}, {4, 5}, {101, 10}};

mid = (dat[[-1, 1]] - dat[[1, 1]])/2.


50.5

ListLinePlot[dat, AxesOrigin -> {mid, 0}, PlotRange -> All]

-