本文へスキップ
からだにいいもの

Rのトピックスを中心に『まだ、まだ、知らない、役に立つ情報?』を発信します。

Rで解析:手描き風グラフを描画する「xkcd」パッケージ

発表資料や記事に図を添えるとき、整いすぎたグラフがかえって堅い印象を与え、読み手の関心を引きにくい場合があります。本パッケージは、「ggplot2」パッケージと同様の操作で、Webコミック「xkcd」を思わせる手描き風グラフのプロットが可能です。また、収録されている専用フォントを利用したテーマを適用することもできます。本パッケージにより、図の印象を和らげ、要点を伝える資料の作成が可能だと考えます。

パッケージバージョンは0.1.1。Windows 11 x64 (build 26200)のR version 4.6.1で確認しています。

パッケージのインストール

下記コマンドを実行してください。

# パッケージのインストール
install.packages("xkcd")

# パッケージの読み込み
# ggplot2は同時に読み込まれます
library("xkcd")

手描き風の書体を利用するには、別途「xkcd」フォントをシステムにインストールします。フォントが見つからない場合は警告が表示され、既定の書体でプロットされます。下記、作業で「xkcd」フォントをシステムにインストールが可能です。

# xkcdフォントを作業フォルダにダウンロード
download.file(
  "https://toledoem.github.io/img/xkcd.ttf",
  destfile = "xkcd.ttf",
  mode = "wb"
)

# フォントを開き、xkcdフォントをドラッグ&ドロップしてインストール
shell.exec("C:/Windows/Fonts")

インストール後、Rを再起動し、下記コマンドの実行で利用可能です。

# 「extrafont」パッケージの読み込み
library("extrafont")

# インポート
font_import(
  paths = file.path(Sys.getenv("LOCALAPPDATA"),
                    "Microsoft", "Windows", "Fonts"),
  pattern = "xkcd",
  prompt = FALSE
)

# 読み込み
loadfonts(device = "win")
Registering font with R using windowsFonts(): xkcd
スポンサーリンク

コマンド例

詳細はコメント、パッケージのヘルプを確認してください。

本パッケージのプロットは、線に乱数由来の揺らぎを加えたうえでベジエ曲線により平滑化する仕組みです。実行のたびに形が変わるため、同じ図を再現したい場合はset.seedコマンドを用いるか、後述のseed引数を指定します。

手描き風の軸のプロット:xkcdaxisコマンド

X軸とY軸を手描き風の線でプロットします。戻り値には座標系の設定とtheme_xkcdコマンドによるテーマが含まれるため、別途テーマを追加する必要はありません。

オプション意味初期値
xrangeX軸の範囲なし
yrangeY軸の範囲なし
geom_xkcdpathコマンドに渡すその他の引数なし
# 架空の週別読書ページ数データを作成
dokusho <- data.frame(shu = 1:8,
                      pages = c(42, 65, 58, 90, 120, 105, 138, 160))

# X軸の範囲を取得
xhani <- range(dokusho$shu)

# Y軸の範囲を取得
yhani <- range(dokusho$pages)

# 揺らぎを再現できるように乱数の種を固定
set.seed(1234)

# 散布図に手描き風の軸を適用したプロット
ggplot() +
  geom_point(aes(x = shu, y = pages), data = dokusho) +
  xkcdaxis(xhani, yhani)

手描き風の長方形のプロット:xkcdrectコマンド

四辺の境界線に揺らぎを加えた長方形をプロットします。xmin、xmax、ymin、ymaxの4つの設定が必須です。塗りつぶし色と境界線は、fill、colour、linewidthで指定します。

オプション意味初期値
dataこのレイヤーで使用するデータセットNULL
statこのレイヤーで適用する統計変換“identity”
position位置の調整方法“identity”
layerコマンドに渡すその他の引数なし
borderxjitteramount境界線の水平方向の揺らぎ量0.005
borderyjitteramount境界線の垂直方向の揺らぎ量0.005
wobble2つの揺らぎ量に乗じる倍率、0で直線になる1
seed境界線の揺らぎを再現するための整数NULL
na.rmFALSEで欠損値を警告とともに除去するかの指定FALSE
show.legend凡例を表示するかの指定NA
inherit.aesプロットからaesを継承するかの指定TRUE
# 架空の年度別入部者数データを作成
bukatsu <- data.frame(nendo = 2021:2025,
                      ninzu = c(18, 24, 21, 30, 35))

# X軸の範囲を取得
xhani <- range(bukatsu$nendo)

# Y軸の範囲を取得
yhani <- range(bukatsu$ninzu)

# 手描き風の長方形と点を重ねたプロットを作成
# 揺らぎはseedで固定し、効果をわかりやすくするためwobbleで揺れ幅を1.5倍に設定
ggplot() +
  xkcdrect(aes(xmin = nendo - 0.3,
               xmax = nendo + 0.3,
               ymin = ninzu - 2,
               ymax = ninzu + 2),
           data = bukatsu,
           fill = "lightblue",
           colour = "black",
           linewidth = 1.2,
           wobble = 1.5,
           seed = 20250820) +
  geom_point(aes(x = nendo, y = ninzu), data = bukatsu) +
  xkcdaxis(xhani, yhani)

手描き風の線分と円のプロット:geom_xkcdpathコマンド

揺らぎを加えて平滑化した線分または円をプロットします。xとyに加えてxendとyendを与えると線分、diameterを与えると円としてプロットされます。colour、alpha、linewidth、linetypeの各aesにも対応しています。

オプション意味初期値
dataデータフレームNULL
stat適用する統計変換“identity”
position位置の調整方法“identity”
layerコマンドに渡すその他の引数なし
xjitteramount線分の水平方向の揺らぎ量、単位はデータの値0.01
yjitteramount線分の垂直方向の揺らぎ量、単位はデータの値0.01
wobble2つの揺らぎ量に乗じる倍率、0で直線になる1
seed揺らぎを再現するための整数NULL
maskTRUEで線の下に太い白色の線を重ねるかの指定TRUE
show.legend凡例を表示するかの指定NA
inherit.aesプロットからaesを継承するかの指定TRUE
# 架空の観測点をつなぐ線分の始点と終点データを作成
keiro <- data.frame(x = c(1, 2, 3, 4),
                    y = c(2, 4, 3, 5),
                    xend = c(2, 3, 4, 5),
                    yend = c(4, 3, 5, 4))

# 手描き風の線分をプロット
ggplot() +
  geom_xkcdpath(aes(x = x, y = y, xend = xend, yend = yend),
                data = keiro,
                wobble = 3,
                seed = 777)

diameterを設定すると円がプロットされます。

# 架空の3つの円の中心座標と直径データを作成
maru <- data.frame(x = c(1, 2.5, 4),
                   y = c(1, 2, 1.2),
                   diameter = c(1, 1.6, 0.8))

# 手描き風の円をプロット
# coord_fixedで縦横比を1に固定
ggplot() +
  geom_xkcdpath(aes(x = x, y = y, diameter = diameter),
                data = maru,
                seed = 201) +
  coord_fixed()

棒人間のプロット:xkcdmanコマンド

データのごとに1体の棒人間をプロットします。頭部の中心座標を表すxとy、全体の大きさを表すscale、X軸とY軸の縮尺比を表すratioxy、そして8か所の角度をラジアンで指定することが必要です。

オプション意味初期値
dataこのレイヤーで使用するデータセットなし
seed棒人間の揺らぎを再現するための整数NULL
geom_xkcdpathコマンドに渡すその他の引数なし

角度を指定するオプションは、背骨のangleofspine、右上腕のanglerighthumerus、左上腕のanglelefthumerus、右前腕のanglerightradius、左前腕のangleleftradius、右脚のanglerightleg、左脚のangleleftleg、首のangleofneckの8種類です。

# 架空の年度別ボランティア登録者数データを作成
touroku <- data.frame(nendo = 2020:2024,
                      ninzu = c(120, 148, 165, 190, 232))

# X軸の範囲を取得
xhani <- range(touroku$nendo)

# Y軸の範囲を取得
yhani <- range(touroku$ninzu)

# 棒人間がゆがまないようにX軸とY軸の縮尺比を算出
hiritsu <- diff(xhani) / diff(yhani)

# 2体の棒人間の位置と各関節の角度データを作成
ningen <- data.frame(x = c(2021, 2023),
                     y = c(215, 150),
                     scale = 15,
                     ratioxy = hiritsu,
                     angleofspine = -pi / 2,
                     anglerighthumerus = c(-pi / 6, -pi / 3),
                     anglelefthumerus = c(-pi / 2 - pi / 6, -pi / 2 - pi / 6),
                     anglerightradius = c(pi / 5, -pi / 5),
                     angleleftradius = c(pi / 5, -pi / 5),
                     anglerightleg = 3 * pi / 2 - pi / 12,
                     angleleftleg = 3 * pi / 2 + pi / 12,
                     angleofneck = -pi / 2)

# 棒人間のプロットに用いる対応付けを作成
taiou <- aes(x = x, y = y, scale = scale, ratioxy = ratioxy,
             angleofspine = angleofspine,
             anglerighthumerus = anglerighthumerus,
             anglelefthumerus = anglelefthumerus,
             anglerightradius = anglerightradius,
             angleleftradius = angleleftradius,
             anglerightleg = anglerightleg,
             angleleftleg = angleleftleg,
             angleofneck = angleofneck)

# 折れ線、手描き風の軸、棒人間を重ねたプロットを作成
ggplot() +
  geom_line(aes(x = nendo, y = ninzu), data = touroku) +
  xkcdaxis(xhani, yhani) +
  xkcdman(taiou, ningen, seed = 100)

XKCDスタイルのテーマ設定:theme_xkcdコマンド

グリッド線や背景を取り除き、xkcdフォントを適用したテーマになります。xkcdフォントが見つからない場合は警告が表示され、既定の書体でプロットされます。

# 架空の月別ラジオ体操参加者数データを作成
taisou <- data.frame(tsuki = 1:6,
                     sanka = c(12, 15, 22, 28, 26, 34))

# 折れ線と点のプロットにXKCDスタイルのテーマを適用
ggplot(taisou, aes(x = tsuki, y = sanka)) +
  geom_line() +
  geom_point() +
  theme_xkcd()

この記事が誰かの役に立ちますように。

スポンサーリンク
価格および配送状況は変更される場合があります。購入時は商品ページをご確認ください。
当サイトに表示されている商品情報はAmazonから提供されたものであり、更新または削除される場合があります。
karada-goodはAmazonアソシエイトとして、適格販売により収入を得ています。