Another notch in the utility belt
22 May 2012 Leave a comment
Having been largely an all-thumbs c# programmer for the last year or so I’ve had little opportunity to add to the world of Excel know-how (and I don’t really feel qualified to say much about the .Net world yet, even if I did once get a Tweet from Jon Skeet). I do keep an eye out for Excel questions on StackOverflow, though, and one caught my eye this morning.
The questioner wanted to add a zero to a chart range. Not sure why he didn’t just add an extra constant value at the end (start or beginning) of the range, but perhaps he couldn’t (maybe the data was in another, read-only workbook?). Anyway, I came up with something that extended an existing trick a little and I thought it was mildly interesting.
Using a named formula in a chart series is1 a fairly well-known idea theses days. It lets us define a dynamic series (usually using OFFSET()) and have our charts update automagically as our series grow and shrink. What I hadn’t previously thought of2 was that I could use a VBA function call as the Name’s “Refers to” with the result being useable in a chart Series definition.
Turns out it could.
Public Function PrependZero(rng As range) Dim val As Variant, res As Variant Dim idx As Long val = Application.Transpose(rng.Columns(1).Value) ' nifty! ReDim res(LBound(val) To UBound(val) + 1) res(LBound(res)) = 0 ' this is where the function lives up to its name For idx = LBound(val) To UBound(val) res(idx + 1) = val(idx) ' copy the remainder Next PrependZero = res End Function
(That Transpose thing is handy – I hadn’t known about it as a way of getting a 1-D range value as a vector. Two transposes needed for data along a row.)
You could use this approach for lots of things. Like, well, lots of things. Honestly, you don’t need me to spell them out.
1 This makes me a little sad – it was a source of Excel-fu that impressed people to a quite disproportionate degree. Array formulae and VBA classes still have this power.
2 I’m aware that I might be the last kid in the class here. Be gentle.