Specifying Unicode values and colors easier with PROC SGPLOT and GTL

Many users of ODS Graphics will be excited to learn that, beginning with SAS® 9.4 TS1M3, SG procedures are able to recognize formatted values that contain Unicode values. One benefit of this is that it allows you to include, without using annotation, special symbols such as greater-than-or-equal-to signs or Greek characters in your axis tick-mark values. You have also asked for syntax which can more easily assign colors to your graphs without having to define a style using PROC TEMPLATE. In this blog, we take a closer look at syntax that you can use to accomplish both of these tasks for PROC SGPLOT. We'll also discuss syntax that produces similar results with the Graph Template Language (GTL).

Recognizing Formatted Values That Contain Unicode

For example purposes, I want to produce a box plot that looks at the levels of cholesterol across patient ages. My program, below, uses a data set called sashelp.heart, which contains values for each patient’s age at the start.

proc sort data=sashelp.heart out=heart;
by ageatstart;
run;
proc sgplot data=heart ;
Title1 "Cholesterol Level by Age Range";
vbox cholesterol / category=AgeAtStart ;
run;

By default, when I submit the program, I get a box for each value of AgeAtStart that is in the data set sashelp.heart.

Wow, that’s a lot of boxes. This chart is crowded and hard to read.

Now, let’s group the boxes into age ranges using a format I created called AGEFMT. Each formatted value should display the lower and upper ages of the range separated by a greater-than-or-equal-to sign. Note that to display the greater-than-or-equal-to sign, I need to use the Unicode value 2264. And because ODS Graphics does not recognize the escapechar, I use (*ESC*) in my format definition.

proc format;
value agefmt
20-30 = "20 (*ESC*){unicode '2264'x} 30"
30-40 = "30 (*ESC*){unicode '2264'x} 40"
40-50 = "40 (*ESC*){unicode '2264'x} 50"
50-60 = "50 (*ESC*){unicode '2264'x} 60"
60-70 = "60 (*ESC*){unicode '2264'x} 70"
;
run;
proc sgplot data=heart ;
Title1 "Cholesterol Level by Age Range";
vbox cholesterol / category=AgeAtStart ;
format ageatstart agefmt.;
run;

If I use SAS 9.4 TS1M2 or earlier to submit my program, the results look like the following. Notice that the Unicode values in the PROC FORMAT do not resolve in the output produced by PROC SGPLOT like they do for the Base SAS® procedures. Prior to SAS 9.4 TS1M3, I would need to use annotation in order to display axis values that contain Unicode values. (Sample 48123 illustrates the syntax.)

Fortunately, these issues disappear with SAS 9.4 TS1M3. When I submit my modified program, my results look much better:

An Easier Way to Assign Colors to Your Graphs

I want each box to be a different color, so I will add the option GROUP=AgeAtStart to my VBOX statement.

proc format;
value agefmt
20-30 = "20 (*ESC*){unicode '2264'x} 30"
30-40 = "30 (*ESC*){unicode '2264'x} 40"
40-50 = "40 (*ESC*){unicode '2264'x} 50"
50-60 = "50 (*ESC*){unicode '2264'x} 60"
60-70 = "60 (*ESC*){unicode '2264'x} 70"
;
run;

proc sgplot data=heart ;
Title1 "Cholesterol Level by Age Range";
vbox cholesterol / category=AgeAtStart group=AgeAtStart ;
format ageatstart agefmt.;
run;

In addition to each box being represented with a different color, a default legend is also displayed.

I am going to suppress the legend by adding the option NOAUTOLEGEND to the PROC SGPLOT statement. I also want to change the default colors for the boxes. Prior to SAS 9.4 TS1M0, I would have had to do this through an attribute map definition or a style definition like this one:

proc template;
define style colors;
parent=styles.htmlblue;
class graphdata1 / color=red;
class graphdata2 / color=green;
class graphdata3 / color=purple;
class graphdata4 / color=orange;
class graphdata5 / color=cyan;
end;

Beginning in SAS 9.4 TS1M0, I assign the colors with the DATACOLORS option in the STYLEATTRS statement in PROC SGPLOT. In addition to changing the fill color of the boxes, I change the color of my graph background and the plot wall area with the BACKCOLOR and WALLCOLOR options, respectively, in the STYLEATTRS statement. Here is the final code:

proc format;
value agefmt
20-30 = "20 (*ESC*){unicode '2264'x} 30"
30-40 = "30 (*ESC*){unicode '2264'x} 40"
40-50 = "40 (*ESC*){unicode '2264'x} 50"
50-60 = "50 (*ESC*){unicode '2264'x} 60"
60-70 = "60 (*ESC*){unicode '2264'x} 70"
;
run;
proc sgplot data=sashelp.heart noautolegend;
Title1 "Cholesterol Level by Age Range";
styleattrs datacolors=(red green purple orange cyan) backcolor=vpav wallcolor=pwh;
vbox cholesterol / category=AgeAtStart group=ageatstart ;
format ageatstart agefmt.;
run;

This is the final graphics output:

Using GTL to Create the Same Graph

The syntax below creates this graph using GTL. The color-fill assignments are made using the DATACOLORS option in the BEGINGRAPH statement. The BACKGROUNDCOLOR option in the BEGINGRAPH statement specifies the background color, and the WALLCOLOR option in the LAYOUT OVERLAY statement defines the color of the axis wall.

proc template;
define statgraph boxes;
begingraph / datacolors=(red green purple orange cyan) backgroundcolor=vpav;
layout overlay / wallcolor=pwh;
boxplot x=AgeAtStart y=cholesterol / group=AgeAtStart;
endlayout;
endgraph;
end;

proc sgrender data=sashelp.heart template=boxes;
Title1 "Cholesterol Level by Age Range";
format AgeAtStart agefmt.;
run;

Specifying Unicode values and colors easier with PROC SGPLOT and GTL was published on SAS Users.