Graph:...y::Node(3pm)

πŸ“¦
version 0.76 Β· 4 versions
, in debian bookworm, debian trixie, ubuntu noble, ubuntu resolute, ubuntu stonking

πŸ’– Graph::Easy::Node β€” the 3pm manual, but make it cute πŸ’–

Okay so real talk: this is the user-contributed Perl documentation for Graph::Easy::Node, and it is lowkey iconic. Grab a snack, bestie, we're getting into it. πŸ“


🌸 NAME 🌸

Graph::Easy::Node β€” it represents a node in a Graph::Easy graph. That's the whole vibe. A node. In a graph. Slay. πŸ‘‘


✨ SYNOPSIS ✨

use Graph::Easy::Node;

my $bonn = Graph::Easy::Node->new('Bonn');

$bonn->set_attribute('border', 'solid 1px black');

my $berlin = Graph::Easy::Node->new( name => 'Berlin' );

Like… look at that. Two little cities. Living their best lives. πŸ™οΈβœ¨


πŸ’œ DESCRIPTION πŸ’œ

A Graph::Easy::Node is a node in a simple graph. Every node has contents (which is a text, an image, or another graph β€” yes, graphs in graphs, it's giving inception πŸŒ€), plus a dimension and an origin.

The origin is typically figured out by a graph layouter module like Graph::Easy. So like, the node doesn't decide where it stands in the world, the layouter does. Very "the algorithm chose my fate" energy. 😌


πŸŽ€ METHODS πŸŽ€

So Graph::Easy::Node already gets all the methods from its base class Graph::Easy::Base, and on top of that it has the following methods. Let's go one by one, no skipping, periodt. πŸ’…

πŸ¦‹ new()

my $node = Graph::Easy::Node->new( name => 'node name' );
my $node = Graph::Easy::Node->new( 'node name' );

Makes you a brand new node, fresh out the box. ✨

But bestie, listen: if you want to add the node to a Graph::Easy object, do it like this instead:

my $node = $graph->add_node('Node name');

Then you can hit it with $node->set_attribute(); or $node->set_attributes(); to set your new node's attributes. Easy. 🫢

🌈 as_ascii()

my $ascii = $node->as_ascii();

Returns the node as a little box drawn in ASCII art, as a string. It's giving retro-terminal-chic. πŸ–₯️

🌸 as_txt()

my $txt = $node->as_txt();

Returns the node in simple txt format, attributes included. No details left behind. πŸ’–

⭐ as_svg()

my $svg = $node->as_svg();

Returns the node as a Scalable Vector Graphic. The actual code for this routine lives in Graph::Easy::As_svg.pm. Scalable! Vector! Graphic! Iconic. 🎨

πŸ’« as_graphviz()

Mostly for internal use β€” use at your own risk. πŸ™ˆ
my $txt = $node->as_graphviz();

Returns the node as graphviz-compatible text, which you can feed to dot etc. to create images. Yum. 🍽️

Also, heads up: you need to load Graph::Easy::As_graphviz first before you can call this method. No loading, no calling. That's the rule. βœ‹

🧚 as_graphviz_txt()

Again, mostly for internal use β€” use at your own risk. πŸ™ˆ
my $txt = $node->as_graphviz_txt();

Returns only the node itself (no attributes) as a graphviz representation. Just the node, unbothered, moisturized, in its lane. πŸ’…

And same deal: you need to load Graph::Easy::As_graphviz first before calling this one too.

πŸŽ€ as_pure_txt()

my $txt = $node->as_pure_txt();

Returns the node in simple txt format β€” but this time without the attributes. Stripped down. Minimalist. Clean girl aesthetic. 🧼

πŸ’œ text_styles_as_css()

my $styles = $graph->text_styles_as_css();      # or $edge->...() etc.

Returns the text styles as a chunk of CSS styling that you can embed into a style="" parameter. Yes, $edge->...() works too, it's not just graphs. 😌

πŸ¦‹ as_html()

my $html = $node->as_html();

Returns the node as HTML code. Web-ready. 🌐

✨ attribute(), get_attribute()

$node->attribute('border-style');

Returns the respective attribute of the node, or undef if it was never set. And if there's a default attribute for all nodes in the specific class this node belongs to, then that default gets returned instead. Inheritance, but make it fashion. πŸ‘‘

🌸 get_attributes()

my $att = $object->get_attributes();

Returns all effective attributes on this object (graph/node/group/edge) as an anonymous hash ref. It respects inheritance and default values. Very thorough of it. πŸ’…

Ngl, this does not include custom attributes. Just so you know.

See also get_custom_attributes and raw_attributes(). πŸ“š

πŸŽ€ get_custom_attributes()

my $att = $object->get_custom_attributes();

Returns all the custom attributes on this object (graph/node/group/edge) as an anonymous hash ref. These are the special ones. 🌟

⭐ custom_attributes()

my $att = $object->custom_attributes();

custom_attributes() is an alias for get_custom_attributes. Same energy, shorter name. 😌

πŸ¦‹ raw_attributes()

my $att = $object->get_attributes();

Returns all set attributes on this object (graph/node/group/edge) as an anonymous hash ref. It respects inheritance, but it does not include default values for attributes that were never set. So it's the raw tea. 🍡

See also get_attributes(). πŸ“š

πŸ’« default_attribute()

my $def = $graph->default_attribute($class, 'fill');

Returns the default value for the given attribute in the class of the object.

The default attribute is the value that gets used when the attribute is unset on the object itself AND unset on the class. The backup backup. πŸ›Ÿ

To find out what attribute is on the class, use the three-arg form of attribute on the graph:

my $g = Graph::Easy->new();
my $node = $g->add_node('Berlin');

print $node->attribute('fill'), "\n";           # print "white"
print $node->default_attribute('fill'), "\n";   # print "white"
print $g->attribute('node','fill'), "\n";       # print "white"

$g->set_attribute('node','fill','red');         # class is "red"
$node->set_attribute('fill','green');           # this object is "green"

print $node->attribute('fill'), "\n";           # print "green"
print $node->default_attribute('fill'), "\n";   # print "white"
print $g->attribute('node','fill'), "\n";       # print "red"

See how the object wins, and the default stays defaulty? The way that works. πŸ˜­πŸ’–

See also raw_attribute(). πŸ“š

🌈 attributes_as_txt

my $txt = $node->attributes_as_txt();

Returns the attributes of this node as a text description. This is used by the $graph->as_txt() code, and ngl there should be no reason to use this function on your own. It's an internal thing. Stay out of its business. πŸ™ˆ

πŸŽ€ set_attribute()

$node->set_attribute('border-style', 'none');

Sets the specified attribute of this (and only this!) node to the specified value. Emphasis on only this. Don't be out here changing your neighbors. βœ‹

πŸ¦‹ del_attribute()

$node->del_attribute('border-style');

Deletes the specified attribute of this (and only this!) node. Gone. Poof. πŸ’¨

✨ set_attributes()

$node->set_attributes( $hash );

Sets all the attributes specified in $hash as key => value pairs, on this (and only this!) node. Bulk setting, because we're efficient. πŸ’…

πŸ’œ border_attribute()

my $border = $node->border_attribute();

Assembles the border-width, border-color and border-style attributes into one string like solid 1px red. Three-in-one, it's giving combo meal. πŸ”

⭐ color_attribute()

# returns f.i. #ff0000
my $color = $node->get_color_attribute( 'fill' );

Just like get_attribute(), except only for colors, and it returns them as hex using the current colorscheme. Hex girl autumn. πŸ‚

🌸 get_color_attribute()

Is an alias for color_attribute(). Same method, different name, no cap. πŸ’…

πŸ¦‹ raw_attribute(), get_raw_attribute()

my $value = $object->raw_attribute( $name );

Returns the value of attribute $name from the object this method was called on (graph, node, edge, group etc.). If the attribute is not set on the object itself, it returns undef.

This method respects inheritance, so an attribute value of 'inherit' on an object makes the method return the inherited value:

my $g = Graph::Easy->new();
my $n = $g->add_node('A');

$g->set_attribute('color','red');

print $n->raw_attribute('color');               # undef
$n->set_attribute('color','inherit');
print $n->raw_attribute('color');               # 'red'

See? It went and picked up 'red' from the parent. Main character inheriting the family colorway. πŸ‘‘

See also attribute(). πŸ“š

πŸŽ€ raw_color_attribute()

# returns f.i. #ff0000
my $color = $graph->raw_color_attribute('color' );

Just like raw_attribute(), except only for colors, and it returns them as hex using the current colorscheme.

If the attribute is not set on the object, it returns undef. Simple as that. 😌

πŸ’« text_styles()

my $styles = $node->text_styles();
if ($styles->{'italic'})
  {
  print 'is italic\n';
  }

Returns a hash with the given text-style properties, aka 'underline', 'bold' etc. Yes bestie, we can tell if it's italic. πŸ’…

🧚 find_grandparent()

my $grandpa = $node->find_grandparent();

For a node that has no origin (meaning it's not relative to another one), this returns $node itself. For every other node, it follows the chain of origin back until it finds a node without a parent, and returns that node. So it's out here tracing the whole family tree. 🌳

This code assumes there are no loops, which origin() prevents from happening. No circular family drama allowed. 🚫

⭐ name()

my $name = $node->name();

Returns the name of the node. In a graph, each node has a unique name, and unless a node label is set, that name is what gets displayed when the graph is rendered. So the name is kind of a big deal. ✨

🌸 label()

my $label = $node->label();
my $label = $node->label(1);            # raw

Returns the label of the node. If no label was set, it returns the name of the node. Backup plan, love that for it. πŸ’–

If the optional parameter is true, the label gets returned 'raw', which means any potential escape of the form \N, \E, \G, \T or \H will not be left alone and not be replaced. So it stays exactly as written, no touchy. πŸ™…

πŸ¦‹ background()

my $bg = $node->background();

Returns the background color. This method honours group membership and inheritance, because it's respectful like that. 🫢

πŸ’œ quoted_comment()

my $cmt = $node->comment();

The comment of this object, quoted so it's suitable to be embedded into HTML/SVG. If this object doesn't have a comment set, it returns the empty string. No comment, no problem. 😌

πŸŽ€ title()

my $title = $node->title();
my $title = $node->title(1);            # raw

Returns a potential title you can use for mouse-over effects. If no title was set (or autogenerated), it returns an empty string. Nothing to hover over, bestie. πŸ–±οΈ

If the optional parameter is true, the title gets returned 'raw', so any potential escape of the form \N, \E, \G, \T or \H is left alone and not replaced. Untouched, as requested. πŸ™ˆ

my $link = $node->link();
my $link = $node->link(1);              # raw

Returns the URL, built from the linkbase and link (or autolink) attributes. If the node has no link associated with it, it returns an empty string. No link, no clicks. πŸ”—

If the optional parameter is true, the link gets returned 'raw', so any potential escape of the form \N, \E, \G, \T or \H will not be left alone and not be replaced. Exact copy, no editing. πŸ’…

⭐ dimensions()

my ($w,$h) = $node->dimensions();

Returns the dimensions of the node/cell, derived from the label (or name), measured in characters. It assumes the label/name has literal '\n' replaced by "\n". So like, it's expecting you already did that swap. 😌

πŸ’« size()

my ($cx,$cy) = $node->size();

Returns the node size in cells. Cells! Not characters! Don't get it twisted. πŸ“

🧚 contents()

my $contents = $node->contents();

For nested nodes, returns the contents of the node. Yes, nested nodes are a thing. It's giving turducken but for graphs. πŸ¦ƒ

🌸 width()

my $width = $node->width();

Returns the width of the node. This is a unitless number, so don't go putting px on it. 🚫

πŸŽ€ height()

my $height = $node->height();

Returns the height of the node. Also a unitless number. Matchy matchy. πŸ“

πŸ¦‹ columns()

my $cols = $node->columns();

Returns the number of columns (in cells) that this node occupies. How much horizontal real estate it's claiming. πŸ™οΈ

πŸ’œ rows()

my $cols = $node->rows();

Returns the number of rows (in cells) that this node occupies. And that's the vertical claim. πŸ“Š

⭐ is_multicelled()

if ($node->is_multicelled())
  {
  ...
  }

Returns true if the node consists of more than one cell. Big node energy. πŸ’ͺ

See als rows() and cols(). πŸ“š

🌈 is_anon()

if ($node->is_anon())
  {
  ...
  }

Returns true if the node is an anonymous node. For Graph::Easy::Node objects it's false, and for Graph::Easy::Node::Anon objects it's true. So like, the anon ones are the ones out here with no name. Respect their privacy. πŸ™ˆ

πŸŽ€ pos()

my ($x,$y) = $node->pos();

this one literally just hands back the position of the node. Initially it's undef, and it gets set from Graph::Easy::layout(). Only valid during the layout phase, bestie β€” so don't be out here trusting it once the layout party's over. 🫢

offset() ✨

my ($dx,$dy) = $node->offset();

Gives you the position of the node relative to the origin. And if the origin node was never set? You get "(0,0)" back. Default behaviour ate, no crumbs. πŸ’…

x() 🌸

my $x = $node->x();

Returns the X position of the node. Initially it's undef, and it gets set from Graph::Easy::layout(). Only valid during the layout phase, fr fr.

y() 🌸

my $y = $node->y();

Returns the Y position of the node. Initially undef, set from Graph::Easy::layout(). Only valid during the layout phase. It's giving twin flame energy with x(), lowkey.

id() πŸŽ€

my $id = $node->id();

Returns the node's unique, internal ID number. That's it. That's the whole vibe. One number, iconic.

connections() πŸ”₯

my $cnt = $node->connections();

Returns the count of incoming and outgoing connections of this node. And here's the plot twist: self-loops count as two connections. So in this example right here, node "N" has four connections but only three edges:

                    +--+
                    v  |
        +---+     +------+     +---+
        | 1 | --> |  N   | --> | 2 |
        +---+     +------+     +---+

See also edges(). πŸ¦‹

edges() 🌈

my $edges = $node->edges();

Returns a list of all the edges (as Graph::Easy::Edge objects) at this node, in no particular order. So like, don't assume an ordering, bestie, that's not what she promised you.

predecessors() πŸ‘‘

my @pre = $node->predecessors();

Returns all nodes (as objects) that link to us. The ones who showed up for us first. πŸ’–

has_predecessors() βœ…

if ($node->has_predecessors())
  {
  ...
  }

Returns true if the node has one or more predecessors. And heads up: it will also return true for nodes with selfloops, because a node can absolutely be its own predecessor. Main character behaviour, honestly.

successors() πŸš€

my @suc = $node->successors();

Returns all nodes (as objects) that we are linking to. The ones we're pointing at. Periodt.

sorted_successors() πŸ”’

my @suc = $node->sorted_successors();

Returns the successors of the node sorted by their chain value (so, successors with more successors come first). It's a whole ranking system, and honestly? Deserved.

has_as_successor() 🫢

if ($node->has_as_successor($other))
  {
  ...
  }

Returns true if $other (a node or a group) is a successor of node β€” meaning there's an edge leading from node to $other. So like, yes, a group can be the successor. Inclusive king.

has_as_predecessor() 🫢

if ($node->has_as_predecessor($other))
  {
  ...
  }

Returns true if the node has $other (a group or a node) as predecessor β€” meaning there's an edge leading from $other to node. The mirror image of the one above. Symmetry slay.

edges_to() ➑️

my @edges = $node->edges_to($other_node);

Returns all the edges (as objects) that start at $node and go to $other_node.

shared_edges() 🀝

my @edges = $node->shared_edges();

Returns a list of all edges starting/ending at this node that share a port with another edge. Besties sharing a doorway. πŸšͺ✨

nodes_sharing_start() 🎬

my @nodes = $node->nodes_sharing_start($side, $port);

Returns a list of unique nodes that share a start point with an edge from this node, on the specified side (absolute) and port number.

nodes_sharing_end() 🏁

my @nodes = $node->nodes_sharing_end($side, $port);

Returns a list of unique nodes that share an end point with an edge from this node, on the specified side (absolute) and port number.

edges_at_port() πŸšͺ

my @edges = $node->edges_to('start', 'south', '0');

Returns all the edge objects that share the same "start" or "end" port at the specified side and port number. Now listen carefully bestie, there are rules:

  • The side must be one of "south", "north", "west" or "east". No free-styling.
  • The port number must be positive.

incoming() πŸ“₯

my @edges = $node->incoming();

Returns all edges that end at this node. The ones sliding into the DMs.

outgoing() πŸ“€

my @edges = $node->outgoing();

Returns all edges that start at this node. The ones she's sending out into the world.

add_to_group() πŸ‘―

$node->add_to_group( $group );

Puts the node into this group. Welcome to the group chat, you're in it now, no take-backs. πŸ’œ

group() πŸŽͺ

my $group = $node->group();

Returns the group this node belongs to, or undef if she's a lone wolf. No group, no problem.

parent() 🌳

my $parent = $node->parent();

Returns the parent object of the node β€” which is either the group the node belongs to, or the graph. Whichever one is actually holding her.

origin() 🧭

my $origin_node = $node->origin();

Returns the node this node is relative to, or undef otherwise. Your anchor, your home base, your origin story. 🌟

relative_to() πŸ“

$node->relative_to($parent, $dx, $dy);

Sets itself relative to $parent with the offset "$dx,$dy". That's the whole thing. Coordinates with commitment issues? No, coordinates with a reference point. ✨

shape() πŸ”·

my $shape = $node->shape();

Returns the shape of the node as a string, defaulting to 'rect'. Rectangle by default because she's simple like that (derogatory? no, affectionate).

angle() πŸ“

my $angle = $self->rotation();

Returns the node's rotation, based on the "rotate" attribute β€” and in case that's relative, on the node's flow. So the angle is literally just vibes computed from other vibes. 😭

flow() 🌊

my $flow = $node->flow();

Returns the outgoing flow for this node as an absolute direction in degrees.

The value gets computed from the incoming flow (or the general flow as the default) plus the flow attribute of this node. So it's a whole collaborative effort, ngl.

_extra_params() πŸ› οΈ

my $extra_params = $node->_extra_params();

The return value of that method gets added as extra params to the HTML tag for a node when as_html() is called. By default it returns the empty string, and it can be overridden in subclasses. See also use_class(). πŸ’…

An overridden method should return a text with a leading space, or the empty string. Do not forget the leading space, bestie, I'm begging.

Example:

package Graph::Easy::MyNode;
use base qw/Graph::Easy::Node/;

sub _extra_params
  {
  my $self = shift;

  ' ' . 'onmouseover="alert(\'' . $self->name() . '\');"';
  }

1;

✨ EXPORT ✨

None by default. Yeah. Nothing. Empty-handed, but make it fashion. πŸ’…


🌈 SEE ALSO 🌈

  • Graph::Easy.

πŸ’– AUTHOR πŸ’–

Copyright (C) 2004 - 2007 by Tels <http://bloodgate.com>.

See the LICENSE file for more details.


and that's the whole page, bestie!! πŸŽ€ go forth and build ur graphs, this was perl v5.36.0, dated 2022-11-20, straight out of the Graph::Easy::Node(3pm) era β€” iconic, historic, obsessed. πŸ’œπŸ¦‹βœ¨