LoginSignup
0
0

WSLとVSCodeを用いて高速で快適なLaTeX環境をインストールしたい

Last updated at Posted at 2024-05-23

はじめに

LaTeXを一度でも使ったことのある人なら分かってくれると思うのですが、コンパイルが遅い。遅すぎる。pdf化のコマンドを打ってから実際にpdfができるまでに1分とかかかる場合もある。さすがにやってられん。
これをどうにかする方法はネット上にはあるにはあるのですが、困ったことに初心者がまず最初に見つける記事は大抵Windows上でLuaLaTeXを使うという遅すぎるものなので、これは良くない。

というわけで、なるべく早くpdf化できるような環境構築の方法をまとめました。

本記事ではupLaTeXの実行環境を構築することを目指します(Luaは遅い)
また、本記事内容はgithubにも公開しています

参考文献

本記事はただしい高速LaTeX論の内容を大いに参考にさせていただきました。

また、VSCode で和文を編集するときのオススメ設定TeX wikiの内容も参考にさせていただきました。

WSLおよびUbuntuのインストール

Windows上でLaTeXを実行するよりも、Linux仮想環境上でやった方が
早いのでWSLを使います

前提条件

Windowsのバージョンは、Windows 10 バージョン2004 以上または Windows 11 であることが必要です。それ以前のバージョンの場合は手動インストールを参照してください

WSLのインストール

PowerShellまたはコマンドプロンプト(以下ターミナル)を管理者権限で起動し、次のように入力して実行(エンターキーを押す)してください

powershell
WSL --install

このコマンドを実行すると、自動的にLinuxのUbuntuディストリビューションをインストールしてくれます(別のディストリビューションがいいという人は勝手にやってください)

少し待つと次のように表示されるはずです

powershell
要求された操作は正常に終了しました。変更を有効にするには、システムを再起動する必要があります

その後パソコンを再起動(シャットダウンではなく再起動!)してください

再びターミナルを起動して、正常にインストールされているか確かめてみましょう。Windowsのターミナル上で次のコマンドを実行してください

powershell
wsl -l -v

すると次のように出力されれば正常です

powershell
$ wsl -l -v
  NAME            STATE           VERSION
* Ubuntu          Stopped         2

ちなみに、StoppedではなくRunningと表示される場合、どこかでこのUbuntuが起動していることを意味しています

Ubuntuを起動

WSLでUbuntuを起動する方法は複数あります。
一つはターミナル上で

powershell
wsl

のコマンドを実行することです。するとUbuntuが立ち上がります

別の方法として、次の画像の青い丸で囲んだ場所にあるマークを押して、「Ubuntu」をクリックする方法もあります。筆者は諸事情により複数のディストリビューション(AzureとかUbuntu-20.04とか)を入れていますが、気にしないでください
ターミナル.png

初回起動時は次のように表示するはずです。完了するまで数分程度かかります(2回目以降はすぐ起動します)

Ubuntu
Installing, this may take a few minutes...

しばらくして次のように表示されたら、ユーザー名とパスワードを登録しましょう。パスワードは打ち込んでも表示されません(セキュリティのため)が、ちゃんと打てているので気にせず入力してください

Ubuntu
Enter new UNIX username:

successfulみたいなことが表示されれば完了です

ついでに、Ubuntuのアップデート・アップグレートをしておきましょう。Ubuntu上で次のコマンドを実行してください

Ubuntu
sudo apt -y update && sudo apt -y upgrade

パスワードが求められるはずですので、さっき登録したパスワードを入力してください

ちなみに、sudoは管理者権限で実行、という意味です。これくらいは覚えておきましょう。

Ubuntuのアンインストール(必要になったときに行ってください)

WSLの良いところは、壊してしまっても一からやり直せばよいところです(WSLはWindowsに影響を及ぼすこともできるので、なんでもやっていいわけではない)

万一Ubuntuが動かなくなったときはアンインストールしてもう一度最初からやり直しましょう。WSL自体は有効のままなので再起動の必要もありません

Windowsのターミナル上で次のコマンドを実行(Ubuntu上ではありません)

powershell
wsl --unregister Ubuntu

この操作を正しく終了しました。と出力されれば完了です。もちろんUbuntuに入れたデータはすべて消えますので、保存しておきたいデータはどこかに移しておきましょう

終わったら再び

powershell
wsl --install

を実行。今度はすぐにUbuntuが起動するので、上記にある「Ubuntuを起動」の内容を行ってください

LaTeXのインストール

TeX wikiをよめば誰でもできます。というか、面倒なのでここではTeX Wikiの内容をさらに端折って書きます。困ったらwikiを見ましょう

LaTeXのインストールには1,2時間はかかります(マシンスペックによってはそれ以上)余裕のあるときにやりましょう

決まり事

ここまでではしませんでしたが、ここからはUbuntuやターミナルにコマンドを入力するときは次のように書くことにします。コピペで実行するときは$マークを消すことに注意してください

$ hogehoge

こんな風に書いてあったらhogehogeと入力して実行してください。

一方で、

hogehoge

のように書いてある場合、これは入力する内容ではなく、何かコマンドを実行した後に勝手に表示される内容を指します。たとえば、

$ hoge1
hogehoge

のように書いてあれば、あなたがhoge1というコマンドを実行することでhogehogeと表示されるはず、ということを意味します。
(ちなみに、hogeは何の意味もないです。しいて言えば日本人プログラマーの鳴き声です)

TeX Liveのインストール

前回Ubuntuをインストールしたはずですので、Ubuntuを起動してください。起動出来たら次のコマンドを実行しましょう

Ubuntu
$ wget http://mirror.ctan.org/systems/texlive/tlnet/install-tl-unx.tar.gz

これはinstall-tl-unx.tar.gzという圧縮フォルダをダウンロードするコマンドです。完了したらこれを展開しましょう。次のコマンドを実行します。

Ubuntu
$ tar xvf install-tl-unx.tar.gz

展開したインストーラーのディレクトリに移動するために次のコマンドを実行します。ちなみに*は任意文字列を意味するので、このコマンドは2020年代のうちは使えるわけですね。2030年になったら動かなくなるはず

Ubuntu
$ cd install-tl-2*

さて、あなたは今から2時間このPCを起動したまま放置できる環境にいますか?いないならここでいったん中断してください。LaTeXのインストールには2時間近くかかる場合があります。いいですね?
あと、PCを放置してると自動でシャットダウンやスリープしてしまう恐れがあります。Windowsの設定を開き、「システム>電源とバッテリー>画面とスリープ」から、パソコンがスリープ状態にならないように設定して下さい。あと、充電切れを避けるためにコンセントにつないでおきましょう

いいですね?ではインストールしましょう。次のコマンドを実行します。

Ubuntu
$ sudo ./install-tl -no-gui -repository http://mirror.ctan.org/systems/texlive/tlnet/

すると次のように表示されるはずです。

Ubuntu
Actions:
 <I> start installation to hard disk
 <H> help
 <Q> quit
Enter command: 
```:Ubuntu
```I```と入力すればインストールが開始します。

1,2時間が経過してインストールが完了したら、次のコマンドを実行します。
```:Ubuntu
$ sudo /usr/local/texlive/????/bin/*/tlmgr path add

最後に一応アップデートをしておきましょう。今後も、パッケージを追加した場合はアップデートをしてください。

Ubuntu
$ sudo tlmgr update --self --all

これで完了です。

VSCodeのインストールおよび準備

ここではVSCodeのインストールと拡張機能のインストール、WSL用のショートカット作成を行います

インストール

VSCodeのインストールはWindows上で行います。

VSCodeのダウンロードページに飛んだら、Windows用インストーラーをダウンロードしてください。

ダウンロードできたら、そのインストーラーを実行すれば完了です。

デスクトップにショートカットを作成しておくと、あとでWSLのショートカットを作成するのが楽です。

これ以上詳しく書くほどのことじゃないので、どうしてもわからん、という人は明治大の解説ページでも見るかググるかしてください

拡張機能

extensions.png
拡張機能のインストール方法について説明します

上画像のように、

1.四角形4つのマークをクリック

2.インストールしたい拡張機能を検索

3.インストールをクリック

とするだけです。

インストールすべき拡張機能は、

  • Japanese Language Pack for Visual Studio Code (japanと検索した一番上)
  • LaTeX Workshop (latex workshopと検索した一番上)
  • WSL (WSLと検索した一番上)
    の3つです(日本語化はなくてもいいけど)

できたらVSCodeを再起動してください。

WSLに接続

拡張機能を入れて再起動したら、左下に青い><みたいなマークの場所があるはずです。それをクリックして、「WSLへの接続」をクリックするとWSLに接続できます。ターミナルよりこっちの方が視覚的で楽ですね!

WSL上だと一部拡張機能がインストールされてない場合があります。もう一度
1.四角形4つのマークをクリック
すると、「LOCAL-インストール済み」のところにある拡張機能に、なにやら青い『WSL:Ubuntuにインストールする』というボタンが表示されています。これをクリックすればWSL上でも拡張機能が使えるようになります

WSLショートカット

VSCodeをインストールするときにショートカットを作成していれば、次のアイコンのショートカットがデスクトップにできているはずです
VSCodeicon.png

これをコピー&貼り付け(ctrl+c, ctrl+v)すれば複製できます。コピーした方を右クリック→プロパティを開き、リンク先の末尾に

 --remote wsl+Ubuntu /home/ユーザー名

を加え、『OK』をクリックします。ただし、『ユーザー名』はUbuntuインストール時に設定したユーザー名です。

これでWSLをすぐ開けるようになります

latexmkrcの設定

この内容はただしい高速LaTeX論を参照しています。このページを読めばまあ大体大丈夫ではある

.latexmkrcを作成

ホームディレクトリ(コマンドcd ~で移動する場所)に.latexmkrcというファイルを作成します。
せっかくなのでVSCodeを使うとしましょう。
makefile.png

前回つくったVSCodeのWSLショートカットを起動し(普通にWSLに接続しても同じ)、左のアクセサリーバー上から2番目にあるエクスプローラーを開きますと、上の画像のような画面になるはずです。筆者はUbuntuのユーザー名をutaojiにしているのでホームディレクトリ名がutaojiになってます。

赤い丸で囲われたボタンをクリックするとファイル作成ができます(その右はフォルダ作成)

ファイル名は.latexmkrcにしてください。(頭文字にピリオドがあることに注意)

ファイルの中身は、ただしい高速LaTeX論を参考にしてください

.latexmkrcの中身
.latexmkrc
# カレントディレクトリ変更
$do_cd = 1;

# fmtlatexの呼び出し
$pdf_mode = 3;
$latex = 'internal fmtlatex uplatex %Z %Y %A %S %R -synctex=1 -file-line-error -halt-on-error %O';
$dvipdf = 'dvipdfmx %O -o %D %S';
$max_repeat = 5;

# 作業パス
my $comdir=$ENV{HOME};
my $comname=".latexmk";
my $pwd=`pwd`;
chomp $pwd;

# fmtlatex メインルーチン
{
    # 拡張子を登録
    $clean_ext="$clean_ext fmt";
    my $initial = 1;

    sub fmtlatex {
        # 引数読込
        my ($engine, $outpath, $auxpath, $basename, $texname, $jobname, @args) = @_;
        my $options = join(' ', @args);

        # 初回実行時
        if ($initial == 1){
            $initial = 0;
            # フォーマット生成フラグ
            my $flag = 0;
            print "fmtlatex: checking if the preamble changed...\n";
            if (&check_preamble_change($auxpath,$jobname,$texname) == 0){
                print "fmtlatex: the preamble is not changed.\n";
                print "fmtlatex: checking if the common fmt file is owned...\n";
                if (&check_com_owned("$pwd/$texname") == 0){
                    print "fmtlatex: the common fmt file is not owned.\n";
                    $flag = 1;
                }else{
                    print "fmtlatex: the common fmt file is owned.\n";
                }
            }else{
                print "fmtlatex: the preamble is changed.\n";
                $flag = 1;
            }
            if ($flag == 1){
                print "rewriting the common fmt file in ini mode...\n";
                # フォーマット生成
                my $iniret=Run_subst("$engine -ini $options -output-directory=\"$comdir\" -jobname=\"$comname\" \\\&$engine mylatexformat.ltx $texname");
                if($iniret == 0){
                    print "fmtlatex: the common fmt file rewrited. saving preamble...\n";
                    &memorize_preamble_change($auxpath,$jobname);
                    &hold_com("$pwd/$texname");
                }else{
                    print "fmtlatex: failed to rewrite the common fmt file.\n";
                    &forget_preamble_change($auxpath,$jobname);
                    &throw_com("$pwd/$texname");
                    return $iniret;
                }
            }else{
                print "keep the common fmt file.\n";
                &forget_preamble_change($auxpath,$jobname);
            }
        }
        print "fmtlatex: the common fmt file is ready, so running normal latex... \n";
        # 通常のタイプセット
        my $finalres = Run_subst("$engine -fmt \"$comdir/$comname\" $options $texname");
        return $finalres;
    }
}

# 共有フォーマットファイルの確認・確保・破棄
{
    # 確認
    sub check_com_owned(){
        my $path=$_[0];
        open(my $fh, "<", "$comdir/$comname.info");
        my $holder=<$fh>;
        close($fh);
        if($path eq $holder){
            return 1;
        }else{
            return 0;
        }
    }
    # 確保
    sub hold_com(){
        my $path=$_[0];
        open(my $fh, ">", "$comdir/$comname.info");
        print $fh "$path";
        close($fh);
    }
    # 破棄(生成失敗時用)
    sub throw_com(){
        open(my $fh, ">", "$comdir/$comname.info");
        print $fh "";
        close($fh);
    }
}

# プリアンブル差分検知
{
    my $prea_ext = "prea";
    $clean_ext="$clean_ext $prea_ext";

    # プリアンブル抽出用のコマンド
    # \endofdumpまたは\begin{document}まで読み出して保存
    my $gethead = "awk '!/%.*/{if (p) print}BEGIN{p=1}/\\\\endofdump/{p=0}/\\\\begin\\{document\\}/{p=0}'";
    my $comphead = "sed -e 's/ *\$//g' -e 's/%.*\$//g'";

    sub check_preamble_change{
        print "check_preamble_change\n";
        my ($auxpath, $basename, $texname) = @_;
        my $preapath="$auxpath$basename.$prea_ext";
        # プリアンブル部の一時ファイルをクリア
        system("echo \"\" > \"$preapath.tmp\"");
        system("echo \"\" > \"$preapath.tmp\"");

        my $chain_flag=1;
        # subfilesによるプリアンブル依存が終わるまで続ける
        do{
            system("$gethead \"$texname\"|$comphead >> \"$preapath.tmp\"");
            system("echo \"\" >> \"$preapath.tmp\"");

            # subfilesの利用を検出
            # 第1行が\documentclass[親ファイルパス]{subfiles}であればsubfiles使用とする
            my $mastername = `head -n 1 "$texname"`;
            if ($mastername =~ /^ *\\documentclass\[.*\]\{subfiles\} *$/){
                $mastername =~ s/^ *\\documentclass\[//g;
                $mastername =~ s/\]\{subfiles\} *$//g;
            }else{
                $mastername = "";
            }
            chomp($mastername);
            # $masternameはsubfilesを利用していれば拡張子なしの親ファイルパスが入っている
            if ($mastername ne ""){
                $texname = "$mastername.tex";
            }else{
                $chain_flag=0;
            }
        }while($chain_flag == 1);
    
        # input先を読み込む
        # $preapath.tmpの中身を一行ずつ読む
        &process_input_files($preapath);

        # 比較

        my $checkret = system("diff -Bb \"$preapath.tmp\" \"$preapath\"");
        return $checkret;

        sub process_input_files{
            my ($preapath) = @_;
            #プリアンブル読み込み制限(inputの循環回避用)
            my $loading_limit=1000;
            open(my $fh, '<', $preapath.".tmp") or die "Error: $!\n";
            print "Processing $preapath.tmp\n";
            my $i=0;
            while (my $line = <$fh>) {
                $i=$i+1;
                last if $i >= $loading_limit; 
                if ($line =~ /\\input\{([^}]*)\}/) {
                    my $inputname = $1;
                    $inputname =~ s/\} *$//g;
                    print "Found input directive: $inputname\n";
                    system("$gethead \"$inputname\"|$comphead >> \"$preapath.tmp\"");
                    system("echo \"\" >> \"$preapath.tmp\"");
                }
            }
        }
    }
    sub forget_preamble_change{
        my ($auxpath, $basename) = @_;
        system("rm \"$auxpath$basename.$prea_ext.tmp\"");
    }
    sub memorize_preamble_change{
        my ($auxpath, $basename) = @_;
        system("mv \"$auxpath$basename.$prea_ext.tmp\" \"$auxpath$basename.$prea_ext\"");
    }
}


# bibtex系
$bibtex_use=2;
$bibtex = 'upbibtex %O %S';
$biber = 'biber --bblencoding=utf8 -u -U --output_safechars %O %S';

# index
$makeindex = 'upmendex %O -o %D %S -s jpbase';

# ヴューワ
$dvi_previewer = "open %S";
$pdf_previewer = "open %S";

# 出力フォルダ指定
$out_dir = ".";
# 中間ファイルを別フォルダに隠しておける
$emulate_aux = 1;
$aux_dir = ".tex_intermediates";

# 中間ファイル登録
$clean_ext="$clean_ext run.xml";

Settings.jsonの設定

こちらはただしい高速LaTeX論およびVSCode で和文を編集するときのオススメ設定を参考にしました

すでにWindows上でLaTeXを使用するためにVSCodeのSettings.jsonを編集している場合、そちらの内容によっては正常に動作しない場合があります。
Windowsの方のsettings.jsonを削除する、あるいはこちらの設定と同じものに変更する、あるいは自力で修正してください

ここまでですでにWSLを起動するショートカットを作ったと思うので、それをダブルクリックで起動してください。

起動したら、左下の歯車マークをクリック→設定をクリック、で、VSCodeの設定ができるようになります。

ユーザー・リモート[WSL:Ubuntu]・ワークスペース

のように並んでいる場所があるので、そのリモート[WSL:Ubuntu]をクリックしてください。

ここで、WSL上でのVSCodeの設定をいじることができます。この画面上で操作してもよいのですが、settings.jsonを編集した方が楽なので画像の赤い丸で囲った場所をクリックしてください
settings.png

すると何やら書き込める場所が表示されます。
ただしい高速LaTeX論
に書いてあるコードをコピペするか、下記コードをコピペしてください。

ちなみに、下記にある私の設定では、参考元から少しいじってます。特に、後半にはlatex関係なく日本語の文章のための設定が加わっています(『一般設定』以下の部分)

settings.json
{
    "editor.formatOnSave": true,
    "latex-workshop.latex.recipe.default": "latexmk",
    "latex-workshop.latex.recipes": [
        {
            "name": "latexmk",
            "tools": ["latexmk"]
        }
    ],
    "latex-workshop.latex.tools": [
        {
            "name": "latexmk",
            "command": "latexmk",
            "args": [
                "%DOC%",
                "-silent" //ログをすべて表示させたい場合は不要
            ]
        }
    ],
    // 残りは任意(詳細は各自ググってください)
    "latex-workshop.intellisense.package.enabled": true,
    "latex-workshop.latex.outDir": "",
    "latex-workshop.view.pdf.viewer": "tab",
    "latex-workshop.latex.autoBuild.cleanAndRetry.enabled": false,
    "latex-workshop.latex.autoBuild.run": "onSave",
    "latex-workshop.synctex.afterBuild.enabled": true,

    //一般設定
    "[latex]": {
        //一行が長い場合折り返す(alt + Z で切り替え可能。折り返したくない場合は"off"にしてください)
        "editor.wordWrap": "on",
        //約物(。、や括弧など)のみで折り返したい場合、下のコメントアウトを消してください
        //"editor.wordBreak": "keepAll",

        //区切り文字を指定
        "editor.wordSeparators": "./\\()\"'-:,.;<>~!@#$%^&*|+=[]{}`~?゠・,、;:!?.。‘’“”()⦅⦆[]〚〛〔〕{}〈〉《》「」『』【】〖〗〝〟がてでとにのはへもやを",

        //半角スペースを除く空白文字(目に見えない文字)にハイライト
        "editor.unicodeHighlight.invisibleCharacters": true,

        //対応する括弧に色付け(半角の括弧はデフォルトで色付けされる)
        "editor.bracketPairColorization.enabled": true,
        "editor.language.colorizedBracketPairs": [
            ["‘", "’"],
            ["“", "”"],
            ["(", ")"],
            ["(", ")"],
            ["⦅", "⦆"],
            ["[", "]"],
            ["[", "]"],
            ["〚", "〛"],
            ["〔", "〕"],
            ["{", "}"],
            ["{", "}"],
            ["〈", "〉"],
            ["《", "》"],
            ["「", "」"],
            ["『", "』"],
            ["【", "】"],
            ["〖", "〗"],
            ["〝", "〟"]
        ],
        //下記の記号にハイライトがつかないようにする(全角カンマ『,』などをハイライトしたい場合はその部分を削除すること)
        "editor.unicodeHighlight.ambiguousCharacters": true,
        "editor.unicodeHighlight.allowedCharacters": {
            "゠": true,
            ",": true,
            ";": true,
            ":": true,
            "!": true,
            "?": true,
            ".": true,
            "‘": true,
            "’": true,
            "(": true,
            ")": true,
            "[": true,
            "]": true,
            "{": true,
            "}": true,
            "〔": true,
            "〕": true,
            "<": true,
            ">": true,
            "ノ": true
        }
    }
}

さらに高速化

ここまで完了すれば、ようやくupLaTeXを実行できる環境が整いました。どうせやるならもっと早くしたいですよね?というわけでもうちょっと続きます

draftを使って、図の読み込みを省略

texファイルの1行目は

\documentclass[uplatex,dvipdfmx]{jsarticle}
(以下略)

のように書くのですが、これを

\documentclass[uplatex,dvipdfmx,draft]{jsarticle}
(以下略)

とするだけ

最後に完成版のpdfを作りたいときはdraftを削除するだけ

subfilesを使う

どれだけ工夫しても、文書が長くなれば必然的に実行時間は長くなるので、じゃあ複数に分割してそれぞれで文書作成して、最後に全体をまとめればいいじゃん、という方法がsubfilesです。

私流の説明をしようかとも思いましたが、subfilesによるLaTeXファイル分割にかなり詳しく分かりやすく記載されているので、こちらを見てください

おわりに

以上、LaTeXインストール&高速化ガイドでした。で、実際インストールしたはいいとしてどうやって書くのか、については、他の人に任せようと思います。
イマドキのLaTeXの書き方入門
などを参考にするとよいかと思います

最後に、注意しておきますが本記事をもとにインストールした場合upLaTeXしか実行できません(.latexmkrcを書き換えれば他のに対応することも可能)
ほかの形式(Luaなど)で書かれたtexファイルをpdf化した場合はプリアンブル部分に少し修正が必要です。他の人からもらったtexファイルを実行するときなどは注意してください。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0