Class pv.Mark
Represents a data-driven graphical mark. The Mark class is the base class for all graphical marks in Protovis; it does not provide any specific rendering functionality, but together with Panel establishes the core framework.
Concrete mark types include familiar visual elements such as bars, lines and labels. Although a bar mark may be used to construct a bar chart, marks know nothing about charts; it is only through their specification and composition that charts are produced. These building blocks permit many combinatorial possibilities.
Marks are associated with data: a mark is generated once per associated datum, mapping the datum to visual properties such as position and color. Thus, a single mark specification represents a set of visual elements that share the same data and visual encoding. The type of mark defines the names of properties and their meaning. A property may be static, ignoring the associated datum and returning a constant; or, it may be dynamic, derived from the associated datum or index. Such dynamic encodings can be specified succinctly using anonymous functions. Special properties called event handlers can be registered to add interactivity.
Protovis uses inheritance to simplify the specification of related marks: a new mark can be derived from an existing mark, inheriting its properties. The new mark can then override properties to specify new behavior, potentially in terms of the old behavior. In this way, the old mark serves as the prototype for the new mark. Most mark types share the same basic properties for consistency and to facilitate inheritance.
The prioritization of redundant properties is as follows:
- If the width property is not specified (i.e., null), its value is the width of the parent panel, minus this mark's left and right margins; the left and right margins are zero if not specified.
- Otherwise, if the right margin is not specified, its value is the width of the parent panel, minus this mark's width and left margin; the left margin is zero if not specified.
- Otherwise, if the left property is not specified, its value is the width of the parent panel, minus this mark's width and the right margin.
While most properties are variable, some mark types, such as lines and areas, generate a single visual element rather than a distinct visual element per datum. With these marks, some properties may be fixed. Fixed properties can vary per mark, but not per datum! These properties are evaluated solely for the first (0-index) datum, and typically are specified as a constant. However, it is valid to use a function if the property varies between panels or is dynamically generated.
See also the Protovis guide.
Defined in: Mark.js.
Constructor Attributes | Constructor Name and Description |
---|---|
pv.Mark()
Constructs a new mark with default properties.
|
Field Attributes | Field Name and Description |
---|---|
The bottom margin; the distance, in pixels, between the bottom edge of the
enclosing panel and the bottom edge of this mark.
|
|
The child index.
|
|
The cursor property; corresponds to the CSS cursor property.
|
|
The data property; an array of objects.
|
|
Default properties for all mark types.
|
|
The events property; corresponds to the SVG pointer-events property,
specifying how the mark should participate in mouse events.
|
|
The mark index.
|
|
The left margin; the distance, in pixels, between the left edge of the
enclosing panel and the left edge of this mark.
|
|
The enclosing parent panel.
|
|
The mark prototype, possibly undefined, from which to inherit property
functions.
|
|
The reverse property; a boolean determining whether marks are ordered from
front-to-back or back-to-front.
|
|
The right margin; the distance, in pixels, between the right edge of the
enclosing panel and the right edge of this mark.
|
|
The root parent panel.
|
|
The current scale factor, based on any enclosing transforms.
|
|
The title property; corresponds to the HTML/SVG title property, allowing the
general of simple plain text tooltips.
|
|
The top margin; the distance, in pixels, between the top edge of the
enclosing panel and the top edge of this mark.
|
|
The mark type; a lower camelCase name.
|
|
The visible property; a boolean determining whether or not the mark instance
is visible.
|
Method Attributes | Method Name and Description |
---|---|
add(type)
Adds a new mark of the specified type to the enclosing parent panel, whilst
simultaneously setting the prototype of the new mark to be this mark.
|
|
anchor(name)
Returns an anchor with the specified name.
|
|
Returns the anchor target of this mark, if it is derived from an anchor;
otherwise returns null.
|
|
def(name, v)
Defines a custom property on this mark.
|
|
event(type, handler)
Registers an event handler for the specified event type with this mark.
|
|
extend(proto)
Sets the prototype of this mark to the specified mark.
|
|
margin(n)
Alias for setting the left, right, top and bottom properties simultaneously.
|
|
mouse()
Returns the current location of the mouse (cursor) relative to this mark's
parent.
|
|
render()
Renders this mark, including recursively rendering all child marks if this is
a panel.
|
- See:
- CSS2 cursor
m.data([1, 2, 3, 4, 5]);However, it is perfectly acceptable to define the data property as a function. This function might compute the data dynamically, allowing different data to be used per enclosing panel. For instance, in the stacked area graph example (see #scene), the data function on the area mark dereferences each series.
"painted": The given mark may receive events when the mouse is over a "painted" area. The painted areas are the interior (i.e., fill) of the mark if a 'fillStyle' is specified, and the perimeter (i.e., stroke) of the mark if a 'strokeStyle' is specified.
"all": The given mark may receive events when the mouse is over either the interior (i.e., fill) or the perimeter (i.e., stroke) of the mark, regardless of the specified fillStyle and strokeStyle.
"none": The given mark may not receive events.
dot.radius(function() 10 / this.scale)Note that the stroke width and font size are defined irrespective of scale (i.e., in screen space) already. Also note that when a transform is applied to a panel, the scale affects only the child marks, not the panel itself.
- See:
- pv.Panel#transform
- Parameters:
- {function} type
- the type of mark to add; a constructor, such as pv.Bar.
- Returns:
- {pv.Mark} the new mark.
- See:
- #extend
- top
- left
- center
- bottom
- right
To facilitate stacking, anchors are defined in terms of their opposite edge. For example, the top anchor defines the bottom property, such that the mark extends upwards; the bottom anchor instead defines the top property, such that the mark extends downwards. See also pv.Layout.Stack.
While anchor names are typically constants, the anchor name is a true property, which means you can specify a function to compute the anchor name dynamically. See the pv.Anchor#name property for details.
- Parameters:
- {string} name
- the anchor name; either a string or a property function.
- Returns:
- {pv.Anchor} the new anchor.
bar.anchor("top").add(pv.Label);then property functions on the label can refer to the bar via the anchorTarget method. This method is also useful for mark types defining properties on custom anchors.
- Returns:
- {pv.Mark} the anchor target of this mark; possibly null.
WARNING We plan on changing this feature in a future release to define standard properties, as opposed to fixed properties that behave idiosyncratically within event handlers. Furthermore, we recommend storing state in an external data structure, rather than tying it to the visualization specification as with defs.
- Parameters:
- {string} name
- the name of the local variable.
- {function} v Optional
- an optional initializer; may be a constant or a function.
m.event("click", function() this.fillStyle("red"));Alternatively, the external data can be manipulated and the visualization redrawn:
m.event("click", function(d) { data = all.filter(function(k) k.name == d); vis.render(); });The return value of the event handler determines which mark gets re-rendered. Use defs (#def) to set temporary state from event handlers.
The complete set of event types is defined by SVG; see the reference below. The set of supported event types is:
- click
- mousedown
- mouseup
- mouseover
- mousemove
- mouseout
TODO In the current implementation, event handlers are not inherited from prototype marks. They must be defined explicitly on each interactive mark. In addition, only one event handler for a given event type can be defined; when specifying multiple event handlers for the same type, only the last one will be used.
- Parameters:
- {string} type
- the event type.
- {function} handler
- the event handler.
- Returns:
- {pv.Mark} this.
- See:
- SVG events
- Parameters:
- {pv.Mark} proto
- the new prototype.
- Returns:
- {pv.Mark} this mark.
- See:
- #add
- Parameters:
- n
- Returns:
- {pv.Mark} this.
- Returns:
- {pv.Vector} the mouse location.
If an enclosing panel has an index property set (as is the case inside in an event handler), then only instances of this mark inside the given instance of the panel will be rendered; otherwise, all visible instances of the mark will be rendered.