\documentclass{lug}

\usepackage{etoolbox}
\usepackage{etoolbox}
\usepackage{textcomp}
\usepackage[nodisplayskipstretch]{setspace}
\usepackage{xspace}
\usepackage{enumitem}
\usepackage{array}

\setminted{autogobble,breaklines,mathescape,fontsize=\tiny}

\newcolumntype{C}{>{\centering\arraybackslash}p{0.3\textwidth}}
\newcolumntype{D}{>{\centering\arraybackslash}p{0.6\textwidth}}

\makeatletter
\newlength\beamerleftmargin
\setlength\beamerleftmargin{\Gm@lmargin}
\makeatother

\setitemize{label=\usebeamerfont*{itemize item}%
  \usebeamercolor[fg]{itemize item}
  \usebeamertemplate{itemize item}}

\AtBeginSection[]{
  \begin{frame}
     \vfill
     \centering
     \includegraphics[width=2cm]{\secimage}

     \vspace{1cm}

     \begin{beamercolorbox}[sep=10pt,center]{title}
        \usebeamerfont{title}\insertsectionhead\par%
     \end{beamercolorbox}
     \vfill 
  \end{frame}
}

\makeatletter
\patchcmd{\beamer@sectionintoc}{\vskip1.5em}{\vskip0.5em}{}{}
\makeatother

\newcommand{\pmidg}[1]{\parbox{\widthof{#1}}{#1}}
\newcommand{\splitslide}[4]{%
    \noindent
    \begin{minipage}{#1 \textwidth - #2 }
        #3
    \end{minipage}%
    \hspace{ \dimexpr #2 * 2 \relax }%
    \begin{minipage}{\textwidth - #1 \textwidth - #2 }
        #4
    \end{minipage}
}
\setbeamerfont{footnote}{size=\tiny}

\title{Web Assembly}
\author{Sam Sartor}
\institute{Mines Linux Users Group}

\begin{document}

\newcommand{\secimage}{graphics/html_icon}
\section{Client Code}

\begin{frame}{What is a website?}
    \splitslide{0.7}{1em}{

        A website is really just a fancy document, temporarily downloaded from
        some remote computer system.

        \vspace{2ex}

        Indeed, Sir Tim Berners-Lee created the world-wide-web as a way of
        sharing research papers.

        \vspace{2ex}

        These documents contain text, images, and styling information.

    }{\pmidg{
        \includegraphics[width=\columnwidth]{graphics/cyrillic_doc}
    }}
\end{frame}

\begin{frame}{Interactive Websites}
    \splitslide{0.7}{1em}{

        Is it possible to make websites interactive?

        \vspace{2ex}

        We would have to include some instructions along with the document. We
        need some kind of scripting language for webpages.

    }{\pmidg{
        \includegraphics[width=\columnwidth]{graphics/buttons}
    }}
\end{frame}

\renewcommand{\secimage}{graphics/sad_js}
\section{JavaScript}

\begin{frame}{On a dark and stormy night \dots}
    \begin{center}

        \textbf{The year is 1995.} Netscape Communications Corporation is
        dying. In a frantic attempt to one-up Microsoft, the company decides to
        embed a scripting language into the Netscape browser.
        
        \vspace{2ex}
        
        They give \textbf{Brendan Eich} 10 days to make a prototype.

        \vspace{2ex}

        Eich dreams of Scheme. He wants his new language to be elegant, fast,
        and pure. \textbf{But it is too late.} The lawyers at Netscape have made a deal
        with Sun Microsystems.

        \vspace{2ex}
        
        It will be known as \textbf{JavaScript}.
    \end{center}
\end{frame}

\begin{frame}{\texttt{!![]+!![]}}
    \begin{center}
        \includegraphics[width=\textwidth]{graphics/js_the_good}
    \end{center}
\end{frame}

\begin{frame}{This page uses 800 thousand lines of JavaScript}
    \vspace*{-4pt}%
    \hspace*{-\beamerleftmargin}%
    \includegraphics[width=\paperwidth]{graphics/pivotal_tracker}
\end{frame}

\renewcommand{\secimage}{graphics/emscripten_icon}
\section{Emscripten}

\begin{frame}{We need C}
    \splitslide{0.75}{1em}{\begin{itemize}
        \item People start writing games in JavaScript
        \item Why can't we use the Unity game engine?
        \item It's written in C
        \item Browsers don't run C
        \item Browsers only run JavaScript
        \item What if we compiled C to JavaScript?
    \end{itemize}}{\pmidg{
        \includegraphics[width=\columnwidth]{graphics/html5_logo} \\
        \vspace{1cm} \\
        \includegraphics[width=\columnwidth]{graphics/unity_logo}
    }}
\end{frame}

\begin{frame}{Emscripten}
    \begin{center}
        Introducing\dots\\
        \includegraphics[height=2cm]{graphics/emscripten_logo} \\
        \vspace{1cm}
        \textit{It compiles things to JavaScript!}
    \end{center}
\end{frame}

\begin{frame}{asm.js Example}
    \begin{center}\begin{tabular}{CD}
        C & asm.js \\
        \inputminted{c}{code/factorial.c} &
        \inputminted{js}{code/factorial.asm.js}
    \end{tabular}\end{center}
\end{frame}

\begin{frame}{That was a Bad Idea}
    \splitslide{0.75}{1em}{
        JavaScript was designed for\dots

        \vspace{1ex}

        \begin{tabular}{c l}
            {\color{green}\checkmark} & Crazy people \\
            {\color{yellow}$\bullet$} & Humans \\
            {\color{red}$\times$} & Computers
        \end{tabular}

        \vspace{3ex}

        Why compile low-level $\to$ high-level?

        \vspace{3ex}

        Why don't we have \emph{machine code for the web?}

    }{\pmidg{
        \includegraphics[width=\columnwidth]{graphics/machine_code}
    }}
\end{frame}

\renewcommand{\secimage}{graphics/wasm_logo}
\section{Web Assembly}

\begin{frame}{Which Direction?}
    \begin{center}
        {
            \Huge
            \pmidg{\includegraphics[height=2cm]{graphics/js_logo}}
            {\color{red}$\nleftarrow$} 
            \pmidg{\includegraphics[height=2cm]{graphics/c_logo}}
            {\color{green}$\rightarrow$}
            \pmidg{\includegraphics[height=2cm]{graphics/wasm_logo}}
        }

        \vspace{2cm}

        \pmidg{\includegraphics[height=4ex]{graphics/emscripten_logo}}
        can compile your code to \textit{Web Assembly}!
    \end{center}
\end{frame}

\begin{frame}{WASM Example}
    \begin{center}\begin{tabular}{CCC}
        C & WASM Text & WASM Binary \\
        \inputminted{c}{code/factorial.c} &
        \inputminted{asm}{code/factorial.wasm.txt} &
        \inputminted{text}{code/factorial.wasm.hex}
    \end{tabular}\end{center}
\end{frame}

\begin{frame}{Software in the Browser}
    \pmidg{\includegraphics[width=\columnwidth]{graphics/wasm_chain}}
\end{frame}

\renewcommand{\secimage}{graphics/js_disabled}
\section{Practical WASM}

\renewcommand{\secimage}{graphics/c_logo}
\section{C/C++}

\begin{frame}[fragile]{emsdk}

    We can use the emscripten sdk to compile C/C++ to JavaScript and WASM.

    \vspace{2ex}

    Emscripten can build a test HTML webpage, JavaScript file, or a pure wasm
    library.

    \begin{minted}[fontsize=\footnotesize]{bash}
        $ emcc demo.c -s WASM=1 -o demo.html
        $ emcc demo.c -s WASM=1 -o demo.js
        $ emcc demo.c -s WASM=1 -s SIDE_MODULE=1 -o demo.wasm 
    \end{minted}

\end{frame}

\renewcommand{\secimage}{graphics/rust_logo}
\section{Rust}

\begin{frame}{The Rust Language}
    \splitslide{0.57}{1em}{

        \textbf{Rust} is a systems programming language that runs blazingly fast,
        prevents segfaults, and guarantees thread safety.

    } {
        \inputminted{rust}{code/demo.rs}
    }
\end{frame}

\begin{frame}[fragile]{Rust Toolchains}

    Rust can be easily compiled to JavaScript and WebAssembly!

    \vspace{2ex}

    You can install a WASM toolchain by running \\
    \texttt{\$ rustup toolchain add wasm32-*-*}

    \vspace{2ex}

    The available toolchains are:

    \begin{tabular}{rl}
        \texttt{wasm32-unknown-unknown} & compile to pure WASM \\
        \texttt{wasm32-unknown-emscripten} & compile to a WASM executable \\
        \texttt{asmjs-unknown-emscripten} & compile to JavaScript \\
    \end{tabular}

\end{frame}

\begin{frame}[fragile]{Cargo}
    Rust comes with a build system called \textbf{Cargo}.

    \vspace{2ex}

    \begin{minted}{bash}
$ cargo run
   Finished helloworld [unoptimized + debuginfo] target(s) in 0.0 secs
    Running `target/debug/helloworld`
Hello, world!
    \end{minted}

    Cargo can target WASM!

    \begin{minted}{bash}
$ cargo build --target wasm32-unknown-emscripten
   Compiling helloworld v0.1.0 (file:///home/sam/Code/helloworld)
    Finished dev [unoptimized + debuginfo] target(s) in 1.26 sec
$ cd target/wasm32-unknown-emscripten/debug/
$ node helloworld.js
Hello, world!
    \end{minted}

\end{frame}

\renewcommand{\secimage}{graphics/stdweb_logo}
\section{stdweb}

\begin{frame}{Interact}

    The whole point is to make interactive websites. How can we edit HTML
    through Rust? How do we make Rust web development feasible?

    \vspace{1cm}

    \begin{center}
        Introducing\dots\\
        \vspace{0.2cm}
        \includegraphics[height=3cm]{graphics/stdweb.png}
    \end{center}
    
\end{frame}

\begin{frame}{Communicate}

    \texttt{stdweb} provides JavaScript's abilities within Rust:
    
    \inputminted[fontsize=\footnotesize]{rust}{code/js.sw.rs}
    
    We can connect to buttons and other page elements:
    
    \inputminted[fontsize=\footnotesize]{rust}{code/button.sw.rs}
    
\end{frame}

\begin{frame}[fragile]{\texttt{cargo-web}}

    We can install the \texttt{cargo-web} tool to make Rust WASM even easier!

    \begin{minted}[fontsize=\footnotesize]{bash}
$ cargo web start
    Finished release [optimized] target(s) in 0.0 secs
    You can access the web server at `http://127.0.0.1:8000`.
    \end{minted}
    
\end{frame}

\renewcommand{\secimage}{graphics/parcel_logo}
\section{parcel}

\begin{frame}{Bundeling JS and Rust}

We can use Parcel to bundle JS and WASM into the same project.

In \texttt{main.js}:

\inputminted[fontsize=\footnotesize]{js}{code/add.js}

In \texttt{add.rs}:

\inputminted[fontsize=\footnotesize]{rust}{code/add.rs}

\end{frame}

\renewcommand{\secimage}{graphics/together}
\section{Putting it all Together}

\begin{frame}{Conclusion}
    \splitslide{0.72}{1em}{
        \begin{itemize}
            \item Faster websites
            \item Written in any language
            \item With desktop libraries
            \item With native graphics
            \item With modern tools
        \end{itemize}
    }{\pmidg{
        \includegraphics[width=\columnwidth]{graphics/mcode}
    }}
\end{frame}

\renewcommand{\secimage}{graphics/questions}
\section{Questions?}

\end{document}
