Merge pull request #6011 from roc-lang/tutorial-etc

Update WIP tutorial
This commit is contained in:
Richard Feldman 2023-11-19 00:28:15 -05:00 committed by GitHub
commit 48e9b53522
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 213 additions and 40 deletions

View File

@ -20,7 +20,7 @@ use target_lexicon::Triple;
use crate::cli_gen::eval_llvm;
pub const WELCOME_MESSAGE: &str = concatcp!(
"\n The rockin ",
"\n The rockin' ",
BLUE,
"roc repl",
END_COL,

View File

@ -8,7 +8,7 @@ Let's start by getting acquainted with Roc's [_Read-Eval-Print-Loop_](https://en
If Roc is [installed](#installation), you should see this:
<pre><samp>The rockin roc repl</samp></pre>
<pre><samp>The rockin' roc repl</samp></pre>
So far, so good!

View File

@ -24,7 +24,7 @@
</nav>
</div>
<main id="repl">
<h1>The rockin Roc REPL</h1>
<h1>The rockin' Roc REPL</h1>
<code class="history">
<div id="help-text"></div>
<div id="history-text"><div id="loading-message">Loading REPL WebAssembly module…please wait!</div></div>

View File

@ -1,29 +1,38 @@
# Tutorial
<nav id="tutorial-toc">
<ol>
<li><a href="#repl">REPL</a></li>
<li><a href="#building-an-application">Building an Application</a></li>
<li><a href="#defining-functions">Defining Functions</a></li>
<li><a href="#if-then-else">if-then-else</a></li>
<li><a href="#debugging">Debugging</a></li>
<li><a href="#records">Records</a></li>
<li><a href="#tags">Tags &amp; Pattern Matching</a></li>
<li><a href="#booleans">Booleans</a></li>
<li><a href="#lists">Lists</a></li>
<li><a href="#types">Types</a></li>
<li><a href="#numeric-types">Numeric Types</a></li>
<li><a href="#crashing">Crashing</a></li>
<li><a href="#tests-and-expectations">Tests and Expectations</a></li>
<li><a href="#modules">Modules</a></li>
<li><a href="#tasks">Tasks</a></li>
<li><a href="#abilities">Abilities</a></li>
<li><a href="#appendix-advanced-concepts">Advanced Concepts</a></li>
<li><a href="#reserved-keywords">Reserved Keywords</a></li>
<li><a href="#operator-desugaring-table">Operator Desugaring Table</a></li>
</ol>
</nav>
<section id="tutorial-body">
<section>
<h1>Tutorial<label id="tutorial-toc-toggle-label" for="tutorial-toc-toggle">contents</label></h1>
<p>Welcome to Roc!</p>
<p>This tutorial will teach you how to build Roc applications. Along the way, you'll learn how to write tests, use the REPL, and more!</p>
</section>
<section>
<h2 id="installation"><a href="#installation">Installation</a></h2>
<p>Roc doesnt have a numbered release or an installer yet, but you can follow the install instructions for your OS<a href="https://github.com/roc-lang/roc/tree/main/getting_started#installation"> here </a>. If you get stuck, friendly people will be happy to help if you open a topic in<a href="https://roc.zulipchat.com/#narrow/stream/231634-beginners"> #beginners </a>on<a href="https://roc.zulipchat.com/"> Roc Zulip Chat </a>and ask for assistance!</p>
</section>
This tutorial will teach you how to build Roc applications. Along the way, you'll learn how to write tests, use the REPL, and much more!
<div id="tutorial-toc">
<ul>
<li><a href="#strings-and-numbers">Strings and Numbers</a></li>
<li><a href="#building-an-application">Building an Application</a></li>
<li><a href="#debugging">Debugging</a></li>
<li><a href="#records">Records</a></li>
<li><a href="#optional-record-fields">Optional Record Fields</a></li>
<li><a href="#tags">Tags</a></li>
<li><a href="#booleans">Booleans</a></li>
<li><a href="#lists">Lists</a></li>
<li><a href="#types">Types</a></li>
<li><a href="#numeric-types">Numeric types</a></li>
<li><a href="#crashing">Crashing</a></li>
<li><a href="#modules">Modules</a></li>
<li><a href="#tasks">Tasks</a></li>
<li><a href="#backpassing">Backpassing</a></li>
<li><a href="#abilities">Abilities</a></li>
<li><a href="#appendix-advanced-concepts">Appendix: Advanced Concepts</a></li>
</ul>
</div>
## [Strings and Numbers](#strings-and-numbers) {#strings-and-numbers}
## [REPL](#repl) {#repl}
Let's start by getting acquainted with Roc's [_Read-Eval-Print-Loop_](https://en.wikipedia.org/wiki/Read%E2%80%93eval%E2%80%93print_loop), or **REPL** for short. Run this in a terminal:
@ -1981,6 +1990,12 @@ For this reason, any time you see a function that only runs a `when` on its only
\[This part of the tutorial has not been written yet. Coming soon!\]
### [Reserved Keywords](#reserved-keywords) {#reserved-keywords}
These are all the reserved keywords in Roc. You can't choose any of these as names, except as record field names.
`if`, `then`, `else`, `when`, `as`, `is`, `dbg`, `expect`, `expect-fx`, `crash`, `interface`, `app`, `package`, `platform`, `hosted`, `exposes`, `imports`, `with`, `generates`, `packages`, `requires`, `provides`, `to`
### [Operator Desugaring Table](#operator-desugaring-table) {#operator-desugaring-table}
Here are various Roc expressions involving operators, and what they desugar to.
@ -2003,8 +2018,5 @@ Here are various Roc expressions involving operators, and what they desugar to.
| <code>a \|> b</code> | `b a` |
| <code>a b c \|> f x y</code> | `f (a b c) x y` |
### [Language Keywords](#language-keywords) {#language-keywords}
These are all of the language keywords supported by Roc;
`if`,`then`,`else`,`when`,`as`,`is`,`dbg`,`expect`,`expect-fx`,`crash`,`interface`,`app`,`package`,`platform`,`hosted`,`exposes`,`imports`,`with`,`generates`,`packages`,`requires`,`provides`,`to`
</section>

View File

@ -56,10 +56,10 @@ view = \page, htmlContent ->
[text htmlContent]
bodyAttrs =
if page == "index.html" then
[id "homepage-main"]
else
[class "article-layout"]
when page is
"index.html" -> [id "homepage-main"]
"tutorial.html" -> [id "tutorial-main", class "article-layout"]
_ -> [class "article-layout"]
html [lang "en", class "no-js"] [
head [] [
@ -72,6 +72,7 @@ view = \page, htmlContent ->
# The homepage doesn't actually use latin-ext
preloadWoff2 "/fonts/lato-v23-latin/lato-v23-latin-regular.woff2",
preloadWoff2 "/fonts/source-code-pro-v22-latin/source-code-pro-v22-latin-regular.woff2",
preloadWoff2 "/fonts/permanent-marker-v16-latin/permanent-marker-v16-latin-regular.woff2",
link [rel "prefetch", href "/repl/roc_repl_wasm.js"],
link [rel "stylesheet", href "/wip/site.css"],
link [rel "stylesheet", href "/wip/repl.css"],

View File

@ -1,5 +1,6 @@
:root {
/* WCAG AAA Compliant colors */
--code-bg: #f4f8f9;
--gray-bg: #f4f8f9;
--gray: #717171;
--orange: #bf5000;
@ -33,6 +34,11 @@
--font-size-normal: 18px;
--body-max-width: 1024px;
--dark-code-bg: #202746;
/* Tutorial */
--header-link-color: #107F79;
--header-link-hover: #222;
--h1-color: #8055E4;
}
html {
@ -217,7 +223,7 @@ h2 {
color: var(--heading-color);
}
.article-layout main {
.article-layout main, .article-layout pre {
max-width: 720px;
}
@ -527,6 +533,10 @@ li {
--body-max-width: none;
}
#tutorial-main main {
max-width: none;
}
#homepage-logo {
/* The bird runs off the screen unless we shrink it */
height: 80px;
@ -637,6 +647,7 @@ li {
h5 {
line-height: 1.2em !important;
font-size: 2rem !important;
width: auto;
}
#top-bar-links {
@ -685,6 +696,19 @@ li {
}
}
@font-face {
font-family: "Permanent Marker";
font-style: normal;
font-weight: 400;
font-display: swap;
src: url("/fonts/permanent-marker-v16-latin/permanent-marker-v16-latin-regular.woff2") format("woff2"),
url("/fonts/permanent-marker-v16-latin/permanent-marker-v16-latin-regular.woff") format("woff");
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA,
U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212,
U+2215, U+FEFF, U+FFFD;
}
/* latin-ext */
@font-face {
font-family: "Lato";
@ -745,7 +769,7 @@ li {
@media (prefers-color-scheme: dark) {
:root {
/* WCAG AAA Compliant colors */
/* WCAG AAA Compliant colors */
--code-bg: #202746;
--gray-bg: #202746;
--gray: #b6b6b6;
--orange: #fd6e08;
@ -765,6 +789,11 @@ li {
--faded-color: #bbbbbb;
--gray: #6e6e6e;
--heading-color: #eee;
/* Tutorial */
--header-link-color: #9C7CEA;
--header-link-hover: #ddd;
--h1-color: #1bc6bd;
}
.logo-dark {
@ -1100,10 +1129,85 @@ code .dim {
border-color: var(--light-cyan);
}
/* Tutorial Table of Contents */
/* Tutorial */
#tutorial-main main {
display: flex;
flex-direction: row-reverse;
max-width: 1024px;
}
#tutorial-main h1,
#tutorial-main h2,
#tutorial-main h3,
#tutorial-main h4,
#tutorial-main h5 {
font-family: "Permanent Marker";
line-height: 1rem;
margin-top: 1.75rem;
margin-bottom: 0;
border: none;
}
#tutorial-main h1 a,
#tutorial-main h2 a,
#tutorial-main h3 a,
#tutorial-main h4 a,
#tutorial-main h5 a {
color: var(--header-link-color);
}
#tutorial-main h1 a:hover,
#tutorial-main h2 a:hover,
#tutorial-main h3 a:hover,
#tutorial-main h4 a:hover,
#tutorial-main h5 a:hover {
text-decoration: none;
color: var(--header-link-hover);
}
#tutorial-main h1 {
font-size: 7rem;
line-height: 7rem;
color: var(--h1-color);
margin-top: 24px;
margin-bottom: 1.75rem;
text-shadow: 1px 1px 1px #010101;
}
#tutorial-main h2 {
font-size: 4rem;
line-height: 4rem;
text-shadow: 1px 1px 1px #010101;
padding: 0.8rem 0;
margin-top: 2.5rem;
width: 60rem; /* Without this, "Building an application" wraps and looks awkward */
}
#tutorial-main h3 {
font-size: 3rem;
line-height: 3rem;
text-shadow: 1px 1px 1px #010101;
margin-bottom: 0.5rem;
}
#tutorial-main h4 {
font-size: 2rem;
text-shadow: 1px 1px 1px #010101;
}
#tutorial-body, #tutorial-body pre {
max-width: 646px;
}
#tutorial-toc {
background-color: var(--gray-bg);
flex: 0 0 auto; /* Take up as much space as it needs */
margin-top: 30px;
background: var(--code-bg);
padding: 12px 24px;
margin-left: 64px;
align-self: flex-start; /* Aligns to the start, not stretching in height */
}
#tutorial-toc > ul {
@ -1122,6 +1226,62 @@ code .dim {
text-overflow: ellipsis; /* Adds an ellipsis if the content overflows */
}
#tutorial-toc code {
background: none;
color: inherit;
margin: 0;
padding: 0;
}
#tutorial-toc ol {
padding: 3px;
margin: 8px 0;
list-style: none;
padding-bottom: 0;
margin-bottom: 0;
}
#tutorial-toc h2 {
font-family: inherit;
font-size: 2em;
text-shadow: none;
margin: 0;
padding: 16px 0;
}
#toc-search {
background-color: var(--toc-search-bg);
border: 1px solid var(--toc-search-border);
color: inherit;
padding: 6px 8px;
margin-top: 16px;
margin-bottom: 4px;
box-sizing: border-box;
width: 100%;
font-size: inherit;
}
#tutorial-toc-toggle,
#tutorial-toc-toggle-label,
#close-tutorial-toc {
display: none;
/* This may be overridden on mobile-friendly screen widths */
}
#tutorial-toc-toggle,
#tutorial-toc-toggle-label {
font-size: 1.1rem;
float: right;
}
#close-tutorial-toc {
position: absolute;
top: 20px;
right: 8px;
font-size: 18px;
padding: 12px 24px;
}
/* for larger screens */
@media only screen and (min-width: 768px) {
#tutorial-toc > ul > li {

View File

@ -40,7 +40,7 @@ const repl = {
},
{
match: (input) => input.replace(/ /g, "").match(/^name="/i),
show: '<p>This created a new <a href="https://www.roc-lang.org/tutorial#defs">definition</a>&mdash;<code>name</code> is now defined to be equal to the <a href="/tutorial#strings-and-numbers">string</a> you entered.</p><p>Try using this definition by entering <code>"Hi, \\(name)!"</code></p>',
show: '<p>This created a new <a href="https://www.roc-lang.org/tutorial#defs">definition</a>&mdash;<code>name</code> is now defined to be equal to the string you entered.</p><p>Try using this definition by entering <code>"Hi, \\(name)!"</code></p>',
},
{
match: (input) => input.match(/^["][^\\]+\\\(name\)/i),