[{"data":1,"prerenderedAt":1325},["ShallowReactive",2],{"blog-ja-source-han-sans-jp-with-gpdf":3},{"id":4,"title":5,"author":6,"body":9,"date":1289,"description":1290,"draft":1291,"extension":1292,"howTo":1293,"image":1315,"meta":1316,"navigation":82,"path":1317,"seo":1318,"stem":1319,"tags":1320,"updated":1315,"__hash__":1324},"blogJa/ja/blog/010.source-han-sans-jp-with-gpdf.md","gpdf で Source Han Sans JP (源ノ角ゴシック JP) を使うには?",{"name":7,"url":8},"gpdf team","https://gpdf.dev",{"type":10,"value":11,"toc":1277},"minimark",[12,16,32,35,52,55,704,718,722,733,736,821,832,836,870,877,901,911,915,918,926,929,1084,1097,1100,1104,1107,1149,1163,1167,1170,1184,1187,1202,1205,1208,1237,1241,1244,1261,1273],[13,14,15],"h2",{"id":15},"質問を言い換えると",[17,18,19,26,27,31],"p",{},[20,21,25],"a",{"href":22,"rel":23},"https://github.com/gpdf-dev/gpdf",[24],"nofollow","gpdf"," のドキュメントで ",[28,29,30],"strong",{},"Source Han Sans JP (源ノ角ゴシック JP)"," — Adobe と Google の提携で 2014 年に公開された汎 CJK サンセリフの Adobe 側ブランド — を使いたい。GitHub のリリースタグで再現性を確保したい、Source Han を標準化してきたデザインシステムを受け継いでいる、あるいは Adobe の配布サイクルが好み。理由はどれでも構わない。ダウンロードする前に押さえておきたいのは 3 点だけ — どのファイルを取るか、Noto Sans JP との関係、そして gpdf が読める形式はどれか。",[13,33,34],{"id":34},"速答",[17,36,37,42,43,47,48,51],{},[20,38,41],{"href":39,"rel":40},"https://github.com/adobe-fonts/source-han-sans/releases",[24],"adobe-fonts/source-han-sans"," のリリースページから ",[44,45,46],"code",{},"SourceHanSansJP-Regular.ttf"," (TTF バンドル、OTF ではない) を取得し、",[44,49,50],{},"gpdf.WithFont(\"SourceHanSansJP\", bytes)"," で登録してデフォルトに設定する。Source Han Sans JP と Noto Sans JP はグリフが完全に同一なので、Adobe の運用要件に特にこだわりがなければ Noto Sans JP のほうが入手は楽。",[13,53,54],{"id":54},"動くコード",[56,57,62],"pre",{"className":58,"code":59,"language":60,"meta":61,"style":61},"language-go shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","package main\n\nimport (\n    \"log\"\n    \"os\"\n\n    \"github.com/gpdf-dev/gpdf\"\n    \"github.com/gpdf-dev/gpdf/document\"\n    \"github.com/gpdf-dev/gpdf/template\"\n)\n\nfunc main() {\n    font, err := os.ReadFile(\"SourceHanSansJP-Regular.ttf\")\n    if err != nil {\n        log.Fatal(err)\n    }\n\n    doc := gpdf.NewDocument(\n        gpdf.WithPageSize(gpdf.A4),\n        gpdf.WithMargins(document.UniformEdges(document.Mm(20))),\n        gpdf.WithFont(\"SourceHanSansJP\", font),\n        gpdf.WithDefaultFont(\"SourceHanSansJP\", 11),\n    )\n\n    page := doc.AddPage()\n    page.AutoRow(func(r *template.RowBuilder) {\n        r.Col(12, func(c *template.ColBuilder) {\n            c.Text(\"報告書\", template.FontSize(24), template.Bold())\n            c.Text(\"Source Han Sans JP — Adobe 配布の無料 CJK フォント。\")\n        })\n    })\n\n    data, err := doc.Generate()\n    if err != nil {\n        log.Fatal(err)\n    }\n    if err := os.WriteFile(\"report.pdf\", data, 0o644); err != nil {\n        log.Fatal(err)\n    }\n}\n","go","",[44,63,64,77,84,94,106,116,121,131,141,151,157,162,178,216,232,250,256,261,280,303,341,367,392,398,403,422,456,493,541,561,567,573,578,599,612,627,632,678,693,698],{"__ignoreMap":61},[65,66,69,73],"span",{"class":67,"line":68},"line",1,[65,70,72],{"class":71},"sMK4o","package",[65,74,76],{"class":75},"sBMFI"," main\n",[65,78,80],{"class":67,"line":79},2,[65,81,83],{"emptyLinePlaceholder":82},true,"\n",[65,85,87,91],{"class":67,"line":86},3,[65,88,90],{"class":89},"s7zQu","import",[65,92,93],{"class":71}," (\n",[65,95,97,100,103],{"class":67,"line":96},4,[65,98,99],{"class":71},"    \"",[65,101,102],{"class":75},"log",[65,104,105],{"class":71},"\"\n",[65,107,109,111,114],{"class":67,"line":108},5,[65,110,99],{"class":71},[65,112,113],{"class":75},"os",[65,115,105],{"class":71},[65,117,119],{"class":67,"line":118},6,[65,120,83],{"emptyLinePlaceholder":82},[65,122,124,126,129],{"class":67,"line":123},7,[65,125,99],{"class":71},[65,127,128],{"class":75},"github.com/gpdf-dev/gpdf",[65,130,105],{"class":71},[65,132,134,136,139],{"class":67,"line":133},8,[65,135,99],{"class":71},[65,137,138],{"class":75},"github.com/gpdf-dev/gpdf/document",[65,140,105],{"class":71},[65,142,144,146,149],{"class":67,"line":143},9,[65,145,99],{"class":71},[65,147,148],{"class":75},"github.com/gpdf-dev/gpdf/template",[65,150,105],{"class":71},[65,152,154],{"class":67,"line":153},10,[65,155,156],{"class":71},")\n",[65,158,160],{"class":67,"line":159},11,[65,161,83],{"emptyLinePlaceholder":82},[65,163,165,168,172,175],{"class":67,"line":164},12,[65,166,167],{"class":71},"func",[65,169,171],{"class":170},"s2Zo4"," main",[65,173,174],{"class":71},"()",[65,176,177],{"class":71}," {\n",[65,179,181,185,188,191,194,197,200,203,206,209,212,214],{"class":67,"line":180},13,[65,182,184],{"class":183},"sTEyZ","    font",[65,186,187],{"class":71},",",[65,189,190],{"class":183}," err ",[65,192,193],{"class":71},":=",[65,195,196],{"class":183}," os",[65,198,199],{"class":71},".",[65,201,202],{"class":170},"ReadFile",[65,204,205],{"class":71},"(",[65,207,208],{"class":71},"\"",[65,210,46],{"class":211},"sfazB",[65,213,208],{"class":71},[65,215,156],{"class":71},[65,217,219,222,224,227,230],{"class":67,"line":218},14,[65,220,221],{"class":89},"    if",[65,223,190],{"class":183},[65,225,226],{"class":71},"!=",[65,228,229],{"class":71}," nil",[65,231,177],{"class":71},[65,233,235,238,240,243,245,248],{"class":67,"line":234},15,[65,236,237],{"class":183},"        log",[65,239,199],{"class":71},[65,241,242],{"class":170},"Fatal",[65,244,205],{"class":71},[65,246,247],{"class":183},"err",[65,249,156],{"class":71},[65,251,253],{"class":67,"line":252},16,[65,254,255],{"class":71},"    }\n",[65,257,259],{"class":67,"line":258},17,[65,260,83],{"emptyLinePlaceholder":82},[65,262,264,267,269,272,274,277],{"class":67,"line":263},18,[65,265,266],{"class":183},"    doc ",[65,268,193],{"class":71},[65,270,271],{"class":183}," gpdf",[65,273,199],{"class":71},[65,275,276],{"class":170},"NewDocument",[65,278,279],{"class":71},"(\n",[65,281,283,286,288,291,293,295,297,300],{"class":67,"line":282},19,[65,284,285],{"class":183},"        gpdf",[65,287,199],{"class":71},[65,289,290],{"class":170},"WithPageSize",[65,292,205],{"class":71},[65,294,25],{"class":183},[65,296,199],{"class":71},[65,298,299],{"class":183},"A4",[65,301,302],{"class":71},"),\n",[65,304,306,308,310,313,315,318,320,323,325,327,329,332,334,338],{"class":67,"line":305},20,[65,307,285],{"class":183},[65,309,199],{"class":71},[65,311,312],{"class":170},"WithMargins",[65,314,205],{"class":71},[65,316,317],{"class":183},"document",[65,319,199],{"class":71},[65,321,322],{"class":170},"UniformEdges",[65,324,205],{"class":71},[65,326,317],{"class":183},[65,328,199],{"class":71},[65,330,331],{"class":170},"Mm",[65,333,205],{"class":71},[65,335,337],{"class":336},"sbssI","20",[65,339,340],{"class":71},"))),\n",[65,342,344,346,348,351,353,355,358,360,362,365],{"class":67,"line":343},21,[65,345,285],{"class":183},[65,347,199],{"class":71},[65,349,350],{"class":170},"WithFont",[65,352,205],{"class":71},[65,354,208],{"class":71},[65,356,357],{"class":211},"SourceHanSansJP",[65,359,208],{"class":71},[65,361,187],{"class":71},[65,363,364],{"class":183}," font",[65,366,302],{"class":71},[65,368,370,372,374,377,379,381,383,385,387,390],{"class":67,"line":369},22,[65,371,285],{"class":183},[65,373,199],{"class":71},[65,375,376],{"class":170},"WithDefaultFont",[65,378,205],{"class":71},[65,380,208],{"class":71},[65,382,357],{"class":211},[65,384,208],{"class":71},[65,386,187],{"class":71},[65,388,389],{"class":336}," 11",[65,391,302],{"class":71},[65,393,395],{"class":67,"line":394},23,[65,396,397],{"class":71},"    )\n",[65,399,401],{"class":67,"line":400},24,[65,402,83],{"emptyLinePlaceholder":82},[65,404,406,409,411,414,416,419],{"class":67,"line":405},25,[65,407,408],{"class":183},"    page ",[65,410,193],{"class":71},[65,412,413],{"class":183}," doc",[65,415,199],{"class":71},[65,417,418],{"class":170},"AddPage",[65,420,421],{"class":71},"()\n",[65,423,425,428,430,433,436,440,443,446,448,451,454],{"class":67,"line":424},26,[65,426,427],{"class":183},"    page",[65,429,199],{"class":71},[65,431,432],{"class":170},"AutoRow",[65,434,435],{"class":71},"(func(",[65,437,439],{"class":438},"sHdIc","r",[65,441,442],{"class":71}," *",[65,444,445],{"class":75},"template",[65,447,199],{"class":71},[65,449,450],{"class":75},"RowBuilder",[65,452,453],{"class":71},")",[65,455,177],{"class":71},[65,457,459,462,464,467,469,472,474,477,480,482,484,486,489,491],{"class":67,"line":458},27,[65,460,461],{"class":183},"        r",[65,463,199],{"class":71},[65,465,466],{"class":170},"Col",[65,468,205],{"class":71},[65,470,471],{"class":336},"12",[65,473,187],{"class":71},[65,475,476],{"class":71}," func(",[65,478,479],{"class":438},"c",[65,481,442],{"class":71},[65,483,445],{"class":75},[65,485,199],{"class":71},[65,487,488],{"class":75},"ColBuilder",[65,490,453],{"class":71},[65,492,177],{"class":71},[65,494,496,499,501,504,506,508,511,513,515,518,520,523,525,528,531,533,535,538],{"class":67,"line":495},28,[65,497,498],{"class":183},"            c",[65,500,199],{"class":71},[65,502,503],{"class":170},"Text",[65,505,205],{"class":71},[65,507,208],{"class":71},[65,509,510],{"class":211},"報告書",[65,512,208],{"class":71},[65,514,187],{"class":71},[65,516,517],{"class":183}," template",[65,519,199],{"class":71},[65,521,522],{"class":170},"FontSize",[65,524,205],{"class":71},[65,526,527],{"class":336},"24",[65,529,530],{"class":71},"),",[65,532,517],{"class":183},[65,534,199],{"class":71},[65,536,537],{"class":170},"Bold",[65,539,540],{"class":71},"())\n",[65,542,544,546,548,550,552,554,557,559],{"class":67,"line":543},29,[65,545,498],{"class":183},[65,547,199],{"class":71},[65,549,503],{"class":170},[65,551,205],{"class":71},[65,553,208],{"class":71},[65,555,556],{"class":211},"Source Han Sans JP — Adobe 配布の無料 CJK フォント。",[65,558,208],{"class":71},[65,560,156],{"class":71},[65,562,564],{"class":67,"line":563},30,[65,565,566],{"class":71},"        })\n",[65,568,570],{"class":67,"line":569},31,[65,571,572],{"class":71},"    })\n",[65,574,576],{"class":67,"line":575},32,[65,577,83],{"emptyLinePlaceholder":82},[65,579,581,584,586,588,590,592,594,597],{"class":67,"line":580},33,[65,582,583],{"class":183},"    data",[65,585,187],{"class":71},[65,587,190],{"class":183},[65,589,193],{"class":71},[65,591,413],{"class":183},[65,593,199],{"class":71},[65,595,596],{"class":170},"Generate",[65,598,421],{"class":71},[65,600,602,604,606,608,610],{"class":67,"line":601},34,[65,603,221],{"class":89},[65,605,190],{"class":183},[65,607,226],{"class":71},[65,609,229],{"class":71},[65,611,177],{"class":71},[65,613,615,617,619,621,623,625],{"class":67,"line":614},35,[65,616,237],{"class":183},[65,618,199],{"class":71},[65,620,242],{"class":170},[65,622,205],{"class":71},[65,624,247],{"class":183},[65,626,156],{"class":71},[65,628,630],{"class":67,"line":629},36,[65,631,255],{"class":71},[65,633,635,637,639,641,643,645,648,650,652,655,657,659,662,664,667,670,672,674,676],{"class":67,"line":634},37,[65,636,221],{"class":89},[65,638,190],{"class":183},[65,640,193],{"class":71},[65,642,196],{"class":183},[65,644,199],{"class":71},[65,646,647],{"class":170},"WriteFile",[65,649,205],{"class":71},[65,651,208],{"class":71},[65,653,654],{"class":211},"report.pdf",[65,656,208],{"class":71},[65,658,187],{"class":71},[65,660,661],{"class":183}," data",[65,663,187],{"class":71},[65,665,666],{"class":336}," 0o644",[65,668,669],{"class":71},");",[65,671,190],{"class":183},[65,673,226],{"class":71},[65,675,229],{"class":71},[65,677,177],{"class":71},[65,679,681,683,685,687,689,691],{"class":67,"line":680},38,[65,682,237],{"class":183},[65,684,199],{"class":71},[65,686,242],{"class":170},[65,688,205],{"class":71},[65,690,247],{"class":183},[65,692,156],{"class":71},[65,694,696],{"class":67,"line":695},39,[65,697,255],{"class":71},[65,699,701],{"class":67,"line":700},40,[65,702,703],{"class":71},"}\n",[17,705,706,707,710,711,714,715,717],{},"TTF を ",[44,708,709],{},"main.go"," の隣に置いて ",[44,712,713],{},"go run main.go","。日本語入り 1 ページの PDF が ",[44,716,654],{}," として出力される。",[13,719,721],{"id":720},"source-han-sans-jp-noto-sans-cjk-jp","Source Han Sans JP = Noto Sans CJK JP",[17,723,724,725,728,729,732],{},"最初に押さえておきたい事実は 1 つ。",[28,726,727],{},"Source Han Sans と Noto Sans CJK は同じフォント","。グリフ設計・メトリクス・文字セットは Adobe が担当し、Google が Noto ブランドで並行配布した。リリース日は両者とも 2014-07-15。アウトライン、",[44,730,731],{},"hmtx"," テーブル、JIS X 0213 / Adobe-Japan1-6 のカバレッジは 1 bit 単位で同一で、Adobe がバージョンを上げると数週間以内に Noto 側にも反映される。",[17,734,735],{},"違いはすべて配布経路とパッケージング:",[737,738,739,754],"table",{},[740,741,742],"thead",{},[743,744,745,748,751],"tr",{},[746,747],"th",{},[746,749,750],{},"Source Han Sans JP",[746,752,753],{},"Noto Sans JP",[755,756,757,769,788,799,810],"tbody",{},[743,758,759,763,766],{},[760,761,762],"td",{},"配布元",[760,764,765],{},"Adobe",[760,767,768],{},"Google",[743,770,771,774,780],{},[760,772,773],{},"一次ソース",[760,775,776],{},[20,777,41],{"href":778,"rel":779},"https://github.com/adobe-fonts/source-han-sans",[24],[760,781,782,787],{},[20,783,786],{"href":784,"rel":785},"https://notofonts.github.io",[24],"notofonts.github.io"," + Google Fonts",[743,789,790,793,796],{},[760,791,792],{},"既定フォーマット",[760,794,795],{},"OTF (CFF アウトライン)",[760,797,798],{},"TTF (static) + variable",[743,800,801,804,807],{},[760,802,803],{},"リリースモデル",[760,805,806],{},"GitHub リリースタグで手動バージョニング",[760,808,809],{},"Google Fonts CDN + git リポジトリ",[743,811,812,815,818],{},[760,813,814],{},"言語バンドル",[760,816,817],{},"言語別 TTF + 汎 CJK OTC",[760,819,820],{},"JP のみ",[17,822,823,824,827,828,831],{},"Adobe の GitHub タグを固定する運用、社内で ",[44,825,826],{},"github.com/adobe-fonts"," をミラーリング済み、あるいは別パイプラインで汎 CJK OTC も使う — こういう事情があれば Source Han Sans JP。そうでなければ TTF が直接落とせる ",[20,829,753],{"href":830},"/ja/blog/noto-sans-jp-with-gpdf"," のほうが手間が少ない。",[13,833,835],{"id":834},"なぜ-otf-ではなく-ttf-なのか","なぜ OTF ではなく TTF なのか",[17,837,838,839,842,843,846,847,850,851,850,854,850,857,859,860,850,863,866,867,869],{},"Adobe の既定配布は ",[44,840,841],{},".otf","、正確には CFF ベースの OpenType。一方 gpdf のフォントパーサは ",[44,844,845],{},"pdf/font/truetype.go"," 1 ファイルにまとまっており、扱うのは ",[44,848,849],{},"glyf"," / ",[44,852,853],{},"loca",[44,855,856],{},"cmap",[44,858,731],{}," と複合グリフ。",[44,861,862],{},"CFF ",[44,864,865],{},"CFF2"," アウトラインは読まない。CFF 系 ",[44,868,841],{}," を渡すと、レンダリング時ではなくドキュメント構築時点でパースエラーになる。",[17,871,872,873,876],{},"Adobe のリリースページは OTF と TTF の両方を公開しているので、",[28,874,875],{},"TTF バンドル"," を選ぶ。ポイントリリースで TTF が落ちていないケース用に、きれいな代替は 2 つ:",[878,879,880,887],"ol",{},[881,882,883,886],"li",{},[28,884,885],{},"Noto Sans JP に切り替える。"," Google Fonts が static TTF を直接配信しており、グリフデータは完全に同じ。変換不要、出力も同じ。",[881,888,889,892,893,896,897,900],{},[28,890,891],{},"一度変換してコミットする。"," ",[44,894,895],{},"fonttools"," の ",[44,898,899],{},"otf2ttf"," で 1 分。結果をリポジトリか社内のアーティファクトサーバに置いて、ビルドパイプラインから変換処理を追い出す。",[17,902,903,904,906,907,910],{},"ビルド時にその場で変換するのは避ける。フォント変換ツールはバージョンをまたぐと挙動が微妙に変わり、",[44,905,731],{}," テーブルがわずかに違うだけで改行位置が ",[44,908,909],{},"pip install -U"," のタイミングで動く。",[13,912,914],{"id":913},"_7-ウェイト","7 ウェイト",[17,916,917],{},"Source Han Sans JP は ExtraLight から Heavy まで 7 ウェイトを個別 TTF で配布:",[56,919,924],{"className":920,"code":922,"language":923},[921],"language-text","SourceHanSansJP-ExtraLight.ttf\nSourceHanSansJP-Light.ttf\nSourceHanSansJP-Normal.ttf\nSourceHanSansJP-Regular.ttf\nSourceHanSansJP-Medium.ttf\nSourceHanSansJP-Bold.ttf\nSourceHanSansJP-Heavy.ttf\n","text",[44,925,922],{"__ignoreMap":61},[17,927,928],{},"ほとんどの業務文書では Regular と Bold の 2 本で足りる:",[56,930,932],{"className":58,"code":931,"language":60,"meta":61,"style":61},"reg,  _ := os.ReadFile(\"SourceHanSansJP-Regular.ttf\")\nbold, _ := os.ReadFile(\"SourceHanSansJP-Bold.ttf\")\n\ndoc := gpdf.NewDocument(\n    gpdf.WithFont(\"SourceHanSansJP\", reg),\n    gpdf.WithFont(\"SourceHanSansJP-Bold\", bold),\n    gpdf.WithDefaultFont(\"SourceHanSansJP\", 11),\n)\n",[44,933,934,962,991,995,1010,1034,1058,1080],{"__ignoreMap":61},[65,935,936,939,941,944,946,948,950,952,954,956,958,960],{"class":67,"line":68},[65,937,938],{"class":183},"reg",[65,940,187],{"class":71},[65,942,943],{"class":183},"  _ ",[65,945,193],{"class":71},[65,947,196],{"class":183},[65,949,199],{"class":71},[65,951,202],{"class":170},[65,953,205],{"class":71},[65,955,208],{"class":71},[65,957,46],{"class":211},[65,959,208],{"class":71},[65,961,156],{"class":71},[65,963,964,967,969,972,974,976,978,980,982,984,987,989],{"class":67,"line":79},[65,965,966],{"class":183},"bold",[65,968,187],{"class":71},[65,970,971],{"class":183}," _ ",[65,973,193],{"class":71},[65,975,196],{"class":183},[65,977,199],{"class":71},[65,979,202],{"class":170},[65,981,205],{"class":71},[65,983,208],{"class":71},[65,985,986],{"class":211},"SourceHanSansJP-Bold.ttf",[65,988,208],{"class":71},[65,990,156],{"class":71},[65,992,993],{"class":67,"line":86},[65,994,83],{"emptyLinePlaceholder":82},[65,996,997,1000,1002,1004,1006,1008],{"class":67,"line":96},[65,998,999],{"class":183},"doc ",[65,1001,193],{"class":71},[65,1003,271],{"class":183},[65,1005,199],{"class":71},[65,1007,276],{"class":170},[65,1009,279],{"class":71},[65,1011,1012,1015,1017,1019,1021,1023,1025,1027,1029,1032],{"class":67,"line":108},[65,1013,1014],{"class":183},"    gpdf",[65,1016,199],{"class":71},[65,1018,350],{"class":170},[65,1020,205],{"class":71},[65,1022,208],{"class":71},[65,1024,357],{"class":211},[65,1026,208],{"class":71},[65,1028,187],{"class":71},[65,1030,1031],{"class":183}," reg",[65,1033,302],{"class":71},[65,1035,1036,1038,1040,1042,1044,1046,1049,1051,1053,1056],{"class":67,"line":118},[65,1037,1014],{"class":183},[65,1039,199],{"class":71},[65,1041,350],{"class":170},[65,1043,205],{"class":71},[65,1045,208],{"class":71},[65,1047,1048],{"class":211},"SourceHanSansJP-Bold",[65,1050,208],{"class":71},[65,1052,187],{"class":71},[65,1054,1055],{"class":183}," bold",[65,1057,302],{"class":71},[65,1059,1060,1062,1064,1066,1068,1070,1072,1074,1076,1078],{"class":67,"line":123},[65,1061,1014],{"class":183},[65,1063,199],{"class":71},[65,1065,376],{"class":170},[65,1067,205],{"class":71},[65,1069,208],{"class":71},[65,1071,357],{"class":211},[65,1073,208],{"class":71},[65,1075,187],{"class":71},[65,1077,389],{"class":336},[65,1079,302],{"class":71},[65,1081,1082],{"class":67,"line":133},[65,1083,156],{"class":71},[17,1085,1086,1089,1090,1093,1094,1096],{},[44,1087,1088],{},"-Bold"," サフィックスが ",[44,1091,1092],{},"template.Bold()"," とボールド TTF を結びつける規約。登録しないまま ",[44,1095,1092],{}," を使うと、Regular グリフに 0.4 pt のストロークを重ねた合成ボールドにフォールバックする。見出し程度なら通用するが、大きな級数では本物のボールドアウトラインに比べて明らかに痩せて見える。",[17,1098,1099],{},"CJK フォントはイタリック版を出さないのが定石で、Source Han Sans JP も例外ではない。日本語の強調にイタリックが欲しい場面は、ウェイトか色に振り替えるほうが自然。漢字に斜体変形をかけると強調ではなく破綻して見える。",[13,1101,1103],{"id":1102},"pan-cjk-か-jp-単体か-superotc-か","Pan-CJK か JP 単体か SuperOTC か",[17,1105,1106],{},"Adobe は Source Han Sans を複数の粒度で配布している。Go の PDF 生成では使い分けが重要:",[1108,1109,1110,1123,1133],"ul",{},[881,1111,1112,1115,1116,1119,1120,1122],{},[28,1113,1114],{},"SourceHanSans.ttc"," (Super OTC) — CJK 全言語を 1 つの 20 MB 超の TrueType Collection に収めたファイル。gpdf は ",[44,1117,1118],{},".ttc"," の内部フェースインデックスを解決しないため、先に ",[44,1121,895],{}," で JP フェースを切り出して TTF として渡す必要がある。通常は選ばない。",[881,1124,1125,1128,1129,1132],{},[28,1126,1127],{},"地域別 OTF"," (例: ",[44,1130,1131],{},"SourceHanSans-Regular.otf",") — CJK 言語統合、CFF アウトライン。gpdf では読めない。",[881,1134,1135,1138,1139,1141,1142,1144,1145,1148],{},[28,1136,1137],{},"言語別 TTF"," (",[44,1140,46],{},") — JP 単体、",[44,1143,849],{}," アウトライン。",[28,1146,1147],{},"これを選ぶ","。",[17,1150,1151,1152,1154,1155,1158,1159,1162],{},"1 ページに日本語と韓国語 / 中国語が混在する場合は、汎 CJK OTF に頼らず言語別ファミリを並べて登録する: ",[44,1153,357],{}," と ",[44,1156,1157],{},"SourceHanSansKR"," を登録し、スクリプトが切り替わる箇所で ",[44,1160,1161],{},"template.FontFamily"," を明示する。汎 CJK OTF は漢字を Han unification で 1 つの形に寄せるため、日本語本文の中で「これは日本語の漢字のはず」と読者が感じる文字が中国語の字形で出てしまう事故が起きる。",[13,1164,1166],{"id":1165},"noto-ではなく-source-han-を選ぶべき場面","Noto ではなく Source Han を選ぶべき場面",[17,1168,1169],{},"アウトラインは同じ、違うのは配布経路。Source Han Sans JP を選ぶと自然なのは:",[1108,1171,1172,1175,1181],{},[881,1173,1174],{},"Adobe の GitHub リリースタグにフォントを固定する運用を取りたい (再現性・監査性)",[881,1176,1177,1178,1180],{},"社内で ",[44,1179,826],{}," をすでにミラーしている (厳しいアーティファクトポリシーのある企業で多い)",[881,1182,1183],{},"汎 CJK OTC バンドルがパイプラインの別工程でも役立つ (DTP 連携、ブランドシステムが Adobe 名で統一されている等)",[17,1185,1186],{},"逆に Noto Sans JP が正解なのは:",[1108,1188,1189,1196,1199],{},[881,1190,1191,1192,1195],{},"TTF を最短経路で入手したい (",[44,1193,1194],{},"fonts.google.com/noto/specimen/Noto+Sans+JP"," → zip → 完了)",[881,1197,1198],{},"OTF→TTF 変換をビルドに持ち込みたくない",[881,1200,1201],{},"すでに他の Google Fonts を既存ワークフローで取得している",[17,1203,1204],{},"レンダリング結果はどちらでも同じ。判断軸は運用上のもの — ファイルをどこから取るか、どうバージョニングするか、運用チームがどちらに慣れているか — で、美的なものではない。",[13,1206,1207],{"id":1207},"関連記事",[1108,1209,1210,1216,1223,1230],{},[881,1211,1212,1215],{},[20,1213,1214],{"href":830},"Noto Sans JP を gpdf で使うには?"," — 同じグリフ、TTF でそのまま配布されている選択肢",[881,1217,1218,1222],{},[20,1219,1221],{"href":1220},"/ja/blog/embed-japanese-font","gpdf で日本語フォントを埋め込むには?"," — CJK 全般の一般的な埋め込みレシピ",[881,1224,1225,1229],{},[20,1226,1228],{"href":1227},"/ja/blog/ipaex-gothic-gpdf","gpdf で IPAex ゴシックを使うには?"," — IPA ライセンスの選択肢 (官公庁提出向け)",[881,1231,1232,1236],{},[20,1233,1235],{"href":1234},"/ja/blog/tofu-boxes-japanese","gpdf で日本語が豆腐文字になる原因と直し方"," — グリフが出ないときのトラブルシュート",[13,1238,1240],{"id":1239},"gpdf-を使ってみる","gpdf を使ってみる",[17,1242,1243],{},"gpdf は Go の PDF 生成ライブラリ。MIT、外部依存ゼロ、ネイティブ CJK 対応。",[56,1245,1249],{"className":1246,"code":1247,"language":1248,"meta":61,"style":61},"language-bash shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","go get github.com/gpdf-dev/gpdf\n","bash",[44,1250,1251],{"__ignoreMap":61},[65,1252,1253,1255,1258],{"class":67,"line":68},[65,1254,60],{"class":75},[65,1256,1257],{"class":211}," get",[65,1259,1260],{"class":211}," github.com/gpdf-dev/gpdf\n",[17,1262,1263,1267,1268],{},[20,1264,1266],{"href":22,"rel":1265},[24],"⭐ GitHub でスター"," · ",[20,1269,1272],{"href":1270,"rel":1271},"https://gpdf.dev/ja/docs/quickstart",[24],"ドキュメントを読む",[1274,1275,1276],"style",{},"html pre.shiki code .sMK4o, html code.shiki .sMK4o{--shiki-light:#39ADB5;--shiki-default:#89DDFF;--shiki-dark:#89DDFF}html pre.shiki code .sBMFI, html code.shiki .sBMFI{--shiki-light:#E2931D;--shiki-default:#FFCB6B;--shiki-dark:#FFCB6B}html pre.shiki code .s7zQu, html code.shiki .s7zQu{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#89DDFF;--shiki-default-font-style:italic;--shiki-dark:#89DDFF;--shiki-dark-font-style:italic}html pre.shiki code .s2Zo4, html code.shiki .s2Zo4{--shiki-light:#6182B8;--shiki-default:#82AAFF;--shiki-dark:#82AAFF}html pre.shiki code .sTEyZ, html code.shiki .sTEyZ{--shiki-light:#90A4AE;--shiki-default:#EEFFFF;--shiki-dark:#BABED8}html pre.shiki code .sfazB, html code.shiki .sfazB{--shiki-light:#91B859;--shiki-default:#C3E88D;--shiki-dark:#C3E88D}html pre.shiki code .sbssI, html code.shiki .sbssI{--shiki-light:#F76D47;--shiki-default:#F78C6C;--shiki-dark:#F78C6C}html pre.shiki code .sHdIc, html code.shiki .sHdIc{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#EEFFFF;--shiki-default-font-style:italic;--shiki-dark:#BABED8;--shiki-dark-font-style:italic}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}",{"title":61,"searchDepth":79,"depth":79,"links":1278},[1279,1280,1281,1282,1283,1284,1285,1286,1287,1288],{"id":15,"depth":79,"text":15},{"id":34,"depth":79,"text":34},{"id":54,"depth":79,"text":54},{"id":720,"depth":79,"text":721},{"id":834,"depth":79,"text":835},{"id":913,"depth":79,"text":914},{"id":1102,"depth":79,"text":1103},{"id":1165,"depth":79,"text":1166},{"id":1207,"depth":79,"text":1207},{"id":1239,"depth":79,"text":1240},"2026-04-19","Adobe の GitHub リリースから TTF 版 Source Han Sans JP を取得して gpdf.WithFont で登録する。Noto Sans JP と同じグリフ、7 ウェイト、SIL OFL。",false,"md",{"name":1294,"totalTime":1295,"tools":1296,"steps":1299},"gpdf ドキュメントで Source Han Sans JP (源ノ角ゴシック JP) をデフォルトフォントに設定する","PT15M",[1297,1298],"Go 1.22+","SourceHanSansJP-Regular.ttf (adobe-fonts/source-han-sans 配布)",[1300,1303,1306,1309,1312],{"name":1301,"text":1302},"Adobe の GitHub リリースから TTF 版を入手する","github.com/adobe-fonts/source-han-sans/releases を開き、最新リリースから TTF バンドル (OTF / SuperOTC ではなく) をダウンロードして SourceHanSansJP-Regular.ttf を取り出す。gpdf は TrueType パーサのみで CFF 系 OpenType は読めない。",{"name":1304,"text":1305},"起動時にバイト列を読み込む","os.ReadFile(\"SourceHanSansJP-Regular.ttf\") か //go:embed を使う。CI 再現性のため、ビルド時にダウンロードせず Adobe のリリースタグを固定してリポジトリに含める運用が安全。",{"name":1307,"text":1308},"ドキュメント生成時に登録する","gpdf.WithFont(\"SourceHanSansJP\", fontBytes) と gpdf.WithDefaultFont(\"SourceHanSansJP\", 11) を gpdf.NewDocument に渡す。AddUTF8Font もファイルパスも不要。",{"name":1310,"text":1311},"必要に応じて他ウェイトも登録する","Source Han Sans JP は ExtraLight 〜 Heavy の 7 ウェイトを個別 TTF として配布。-Bold サフィックス付きで登録しておくと template.Bold() が本物のボールドアウトラインを使うようになる。",{"name":1313,"text":1314},"OFL.txt を配布物に同梱する","SIL OFL 1.1 はフォントバイナリの配布先にライセンス全文の同梱を要求する。//go:embed する場合は OFL.txt も LICENSES/ に含めて NOTICE から参照する。",null,{},"/ja/blog/source-han-sans-jp-with-gpdf",{"title":5,"description":1290},"ja/blog/010.source-han-sans-jp-with-gpdf",[1321,1322,1323],"recipe","cjk","tutorial","ARN91OiCQazALeR25_a6EjgTC3En5Sc7vh7sZKr3LFg",1776537634944]