Graduated Panels
The "Graduated" Panel, Panel.Graduated, draws regular tick marks and/or text labels along the stroke of the main child Shape. Graduated Panels can be considered scales showing a range of values.
For examples of Graduated Panels see the Timeline, Thermometer, Instrument Gauge, and Rulered Diagram samples.
Simple Graduated Panels
Similar to Auto and Spot Panels, Graduated Panels should have two or more elements in them. Elements must be either Shapes or TextBlocks. The main Shape element may be declared by setting GraphObject.isPanelMain to true; but no such setting is needed if it is the very first element of the panel. Shapes and TextBlocks, other than the main Shape, basically act as templates for the drawing of each tick mark and label.
Tick mark Shapes within a Graduated Panel should have a measured size, either by setting a GraphObject.desiredSize (or width and
height properties), or by setting its Shape.geometry. For basic tick marks drawn normal to the main Shape's path, it is easiest to use a
simple vertical line geometry string: M0 0 V10. The height of the geometry will determine the length of the tick mark.
Any shape, including custom geometries, can be used as the main Shape or as a tick mark Shape of a Graduated Panel.
Graduated Panels can also be labeled with TextBlocks denoting the values along the scale. Often, these will be offset from the main stroke using GraphObject.segmentOffset, as one would with Link labels, so that the text does not overlap the main stroke. More detail on placing labels is in the "Appearance" section below.
Graduated Panel properties
There are a number of properties that govern the appearance of tick marks and labels.
Tick mark values
The graduated values of a Graduated Panel will range on a linear scale from the start of the main shape's stroke to the end of the stroke. The values and frequency of tick marks and labels are governed by a few properties:
- Panel.graduatedMin - the minimum value represented on the scale, at the beginning of the stroke of the main shape
- Panel.graduatedMax - the maximum value represented on the scale, at the end of the main shape
- Panel.graduatedTickBase - the value of the "origin" tick mark, the first tick mark if it is the same as graduatedMin
- Panel.graduatedTickUnit - tick marks are positioned at multiples of the graduatedTickUnit added to the graduatedTickBase
- Shape.interval/TextBlock.interval - a multiple of the graduatedTickUnit at which to draw a tick or label
Graduated Panels can have multiple Shapes as tick marks and multiple TextBlocks as labels, with the interval property controlling at what multiples of the
graduatedTickUnit they are drawn. In many of the examples below, larger ticks are drawn at intervals of 4; some have an interval of 5.
A graduatedMin of 0, graduatedMax of 77, graduatedTickBase of 0,
graduatedTickUnit of 2.5, and intervals of 4 result in a scale that might appear as:
Try changing some values. For example, try changing graduatedMin to -23.
The range from the min to the max value (Panel.graduatedRange) has increased from 77 to 100, so the tick marks are closer to each other for the same
length main path.
If you change graduatedTickBase to 1.2, the "origin" for the scale would shifted slightly,
even though the end values remain the same. There will always be a tick mark at the
graduatedTickBase
if that value is within the range of the graduated scale.
Making these edits and doubling the graduatedTickUnit to 5 results in:
Doubling the tick unit halves the number of ticks for the same length path, but again the end values are unchanged.
Changing graduatedTickBase back to 0 and the intervals to 5 results in:
You can have more than one label. For example, small text that is more frequent than larger text:
Notice that the infrequent label, the 100s, overpowers the more frequent label (the 50s). You won't have two labels in one spot.
Tick mark appearance
The appearance of tick marks relative to the main shape path is controlled by a few properties:
- Shape.graduatedStart/TextBlock.graduatedStart - the fractional distance along the main stroke at which drawing this tick or label may begin
- Shape.graduatedEnd/TextBlock.graduatedEnd - the fractional distance along the main stroke beyond which it will not draw this tick or label
- GraphObject.alignmentFocus - the spot on the tick or label to align with the calculated path points, defaulting to the top center
- GraphObject.segmentOffset - how much to offset a TextBlock label from the main stroke -- the Y value specifies distance from the path
- GraphObject.segmentOrientation - how to rotate a TextBlock label relative to the main stroke
Only TextBlock labels should set the GraphObject.segmentOffset or GraphObject.segmentOrientation. They have no impact on the main shape or tick shapes. These GraphObject properties are also commonly used to place Link labels, as seen in the learn page on Link labels, and are used by Graduated Panels in a similar manner.
Setting graduatedStart and/or graduatedEnd allows for drawing ticks only along part of the main stroke:
In this case, tick marks are now only drawn in the middle half of the main shape.
Setting alignmentFocus to go.Spot.Bottom will cause the ticks to have their bottoms aligned to the main stroke:
Setting alignmentFocus to go.Spot.Center will cause the ticks to be centered across the path:
Note the gap in the geometry of the shape.
Setting segmentOffset for labels can make them more readable near tick marks:
Setting segmentOrientation for labels can alter the angle at which they are drawn relative to the main stroke,
but note that in the below example, the top-center point of each label is exactly at the point along the path for that value.
For this reason, you'll want to also add an alignmentFocus and segmentOffset to make it look nice.
For vertical lines it's not necessary to rotate the text.
Also, the scale follows the stroke's direction: a geometry running down
(V400, a vertical line to the y-value 400) reads top-to-bottom, while one running up (V-400, since negative Y is higher on the page) reads
bottom-to-top.
The properties segmentOrientation, alignmentFocus and segmentOffset behave similarly to Link labels, in that they respond to the direction of the main stroke. For example, let us turn the main shape so that it
goes diagonally down from the top-left to the bottom-right.
Now let us try a curve:
Here's another commonplace configuration:
Lastly, any angle specified on a label will be respected if orientation is one of Orientation.None, Orientation.Along, or Orientation.Upright. In the case of Along and Upright, the angle will be added to the slope of the main path at the point of the TextBlock.
With None, the labels are always 45 degrees. With Along, the labels are always 45 degrees more than the slope. With Upright, the labels are always 45 degrees more than the slope, then rotated upright if necessary.
Functional appearance properties
There are also some functional properties allowing for further customization of the appearance of ticks and labels.
- Shape.graduatedSkip/TextBlock.graduatedSkip - an optional function which returns true for values that should be skipped while drawing a particular tick or label
- TextBlock.graduatedFunction - an optional function which converts a value to a string to be displayed at that value -- if not defined, the default returns the value rounded to at most two decimals
Setting graduatedSkip allows for skipping ticks where the supplied function returns true:
Setting graduatedFunction allows for changing the way labels are displayed:
Graduated value computations
There are two methods for converting between values and positions on a graduated path:
- Panel.graduatedPointForValue — given a value between graduatedMin and graduatedMax, returns its Point on the main shape (in panel coordinates).
- Panel.graduatedValueForPoint — given a Point, returns the nearest value along the main shape.
The two gauges below each use one. On the left, a move() loop calls
graduatedPointForValue to move the red marker along the arc every 10ms. On the right, you can drag the marker: a
Part.dragComputation gives the drag point to graduatedValueForPoint to find the nearest value, then back through
graduatedPointForValue, to keep the marker on the nearest point on the graduated panel.
For demonstration the markers are separate Parts from their gauges. A real gauge would make the marker part of the gauge itself as an indicator of a value, optionally draggable. See more at Instrument Controls: Gauges and Meters.
Other considerations
By default, only the main shape of a Graduated Panel can be used to pick the panel. As with Grid Panels, a Graduated Panel should have a non-null
background if the entire panel needs to be pickable (set to transparent if you want it to be pickable without a visible background). You cannot set or bind the Panel.itemArray of a Graduated Panel. You can set and bind
properties on tick Shapes and TextBlock labels as you can with any other GraphObject properties.
Events on the tick Shapes and TextBlock labels will be ignored. Rotating the main shape will not rotate the ticks, just as rotating a Spot Panel's main element won't rotate its children. Rotation should generally be done at the Panel level. Another similarity to Spot Panels is that resizing of a Graduated Panel should generally be done on the main shape. TextBlock labels cannot be edited.