Thank you Albert for your reply. Your suggestion of using a Pane and right
alignment to obviate the proportional font problem works.
I believe that NumberForm was originally designed for monospace fonts. This
was generally good enough. The Help for NumberForm says that it controls how
the number 'prints' and not that it's purpose is to convert the number to a
string. In any case, now that we have much easier dynamics, and constructs
like Panel with its proportional font (which I like), there will be much
more formatting of numbers within lines of text. NumberForm no longer works
properly for this purpose. We can end up getting a lot of 'jitter'. If
somehow we could pad with blank characters that had the same widths as "-"
and "0" in the font then that would be the simplest solution. If that
solution could be implemented within NumberForm (and maybe it is impossible)
the average user would find it relatively easy to use. The solution you give
is slightly heavy lifting for most users. Just because a solution is
possible doesn't mean that it will be readily available to most users. They
are going to spend a lot of time looking at NumberPadding and NumberSigns
because that is the obvious indicated path.
In any case, here is a routine, starting with your suggestions, for
formatting proportional font numbers in lines of text.
NumberFormPane::usage =
"NumberFormPane[number,digitspecs,imagesize,opts] will display a \
number formatted with NumberForm within a Pane with the given \
imagesize. Options for both Pane and NumberForm may be given. By \
default the number is displayed right justified in the Pane and with \
the Baseline aligned with the surrounding Baseline. This allows \
numbers, even with proportional fonts, to be displayed in a fixed \
position within lines of text.";
Options[NumberFormPane] =
Join[Options[NumberForm],
FilterRules[Options[Pane], Except[ImageSize]]];
NumberFormPane[number_?NumericQ, digitspecs_, imagesize_,
opts : OptionsPattern[]] :=
Pane[NumberForm[number, digitspecs,
FilterRules[{opts}, Options[NumberForm]]], ImageSize -> imagesize,
Sequence[FilterRules[{opts}, Options[Pane]]],
Alignment -> {Right, Baseline},
BaselinePosition -> Baseline,
ImageSizeAction -> "ShrinkToFit"]
Here is one test:
Module[
{x = 0., fs = 16},
Panel[
Column[
{Row[{-15 <= "x" <= 15, Spacer[5],
Slider[Dynamic[x], {-15, 15, .001}], Spacer[5],
InputField[Dynamic[x], FieldSize -> {5, 1.2}]}],
Row[{"x variable:", Spacer[5],
Dynamic@NumberFormPane[x, {6, 3}, Round[{4 fs, fs}]],
Spacer[5], "in value."}]
}],
Style["Number Formatting Problem", 16],
BaseStyle -> {FontSize -> fs}]
]
The following is an example where not enough space has been left for the
length of the number with larger negative values. Then ShrinkToFit is used.
Module[
{x = 0., fs = 16},
Panel[
Column[
{Row[{-15 <= "x" <= 15, Spacer[5],
Slider[Dynamic[x], {-15, 15, .001}], Spacer[5],
InputField[Dynamic[x], FieldSize -> {5, 1.2}]}],
Row[{"x variable:", Spacer[5],
Dynamic@NumberFormPane[x, {6, 3}, {50, 16}],
Spacer[5], "in value."}]
}],
Style["Number Formatting Problem", 16],
BaseStyle -> {FontSize -> fs},
ImageSize -> {500, 80}]
]
Without specifying the ImageSize for the Panel, we would get some jumping of
the Panel height. So there is still a certain amount of diddling and that is
why being able to pad with proper width spaces would be an easier solution.
--
David Park
djmpark at comcast.net
http://home.comcast.net/~djmpark/
"Albert Retey" <awnl at gmx-topmail.de> wrote in message
news:gcn4bv$76e$1 at smc.vnet.net...
> David Park wrote:
>> I would like to write numbers in a dynamic display such that as the
>> numbers
>> are varied the width and positioning of the digits, fill spaces, and
>> signs
>> remained fixed. Now I know that I can do this if I pick a monspace font
>> such
>> as Courier. However, I would like to do this within Panels and in general
>> with proportional fonts. The font that is used within Panels is given by
>> evaluating CurrentValue["PanelFontFamily"] and gives "Segoe UI". It's a
>> nice
>> looking font and I'm happy with it. I don't want a different font for
>> text
>> and numbers in a display.
>>
>> I assume that with proportional fonts the widths of all the digit
>> characters
>> are the same. The problem is that the space character is much thinner
>> than
>> the digits, and + and - are also different widths than the digits. I
>> found
>> that for NumberPadding on the left I could sometimes use \[LetterSpace]
>> to
>> match the width of the digits, but I don't think this works for all fonts
>> or
>> font sizes. Also it leaves a slight trace of its presence, which would be
>> nice to eliminate.
>>
>> Here is a test case to experiment with:
>>
>> Module[
>> {x = 0., numformat},
>> numformat[x_] :=
>> NumberForm[N[x], {6, 3}, NumberPadding -> {"\[LetterSpace]", "0"},
>> NumberSigns -> {"-", "\[LetterSpace]"}, SignPadding -> False];
>> Panel[
>> Column[
>> {Row[{-15 <= "x" <= 15, Spacer[5],
>> Slider[Dynamic[x], {-15, 15, .001}], Spacer[5],
>> InputField[Dynamic[x], FieldSize -> {5, 1.2}]}],
>> Row[{"x:", Spacer[5], Dynamic@numformat[x], Spacer[5],
>> "in value."}]
>> }],
>> Style["Number Formatting Problem", 16],
>> BaseStyle -> {FontSize -> 16}]
>> ]
>>
>> For a FontSize of 16 the LetterSpace works well for the NumberPadding but
>> it
>> does not work well enough for the NumberSigns. If the FontSize is changed
>> to
>> 12 then it doesn't work for either. If you vary the slider you will see a
>> fair amount of jumping around.
>>
>> The basic problem here is that NumberPadding and NumberSigns take only
>> single character strings. The ideal solution would be if one could use:
>>
>> NumberPadding -> {Invisible["0"], "0"}
>> NumberSigns -> {"-", Invisible["-"]}
>>
>> but that is not possible.
>
> I think your problem is that you are trying at the wrong place.
> NumberForm is for constructing a string representation of a number, it
> doesn't care how the string is represented on screen (or paper). To do
> that there are other functions. I think the following should have the
> properties you are seeking for and should work with any font you choose
> (for some you might need to adapt the ImageSize of the Pane)
>
> Module[{x = 0., numformat},
>
> numformat[x_] :=
> NumberForm[N[x], {6, 3}, NumberPadding -> {"", "0"},
> NumberSigns -> {"-", " "}, SignPadding -> False];
> DynamicModule[{fs = 10},
> Dynamic@Panel[Column[
> {
> PopupMenu[Dynamic[fs], {10, 12, 14, 16, 18, 20, 22}],
> Row[{-15 <= "x" <= 15, Spacer[5],
> Slider[Dynamic[x], {-15, 15, .001}], Spacer[5],
> InputField[Dynamic[x], FieldSize -> {5, 1.2}]}],
> Row[{"x:", Spacer[5],
> Pane[Dynamic[
> numformat[x]
> ], ImageSize -> Dynamic[Round[{4*fs, fs}]],
> Alignment -> {Right, Baseline}],
> Spacer[5], "in value."}]
> }],
> Style["Number Formatting Problem", 16],
> BaseStyle -> {FontSize -> fs}]
> ]
> ]
>
>> Unless someone can suggest a reasonable solution to this maybe it's time
>> that WRI considered updating NumberFormat.
>
> I don't think that WRI would agree that NumberFormat has a problem...
>
> hth,
>
> albert
>
>
>