summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore7
-rw-r--r--Makefile30
-rw-r--r--footer.html1
-rw-r--r--gmi2html.c187
-rw-r--r--gmi2html.cgi.c361
-rw-r--r--header.html5
-rw-r--r--site/cgit.css72
-rw-r--r--site/en/hexchat.webmbin0 -> 11665500 bytes
-rw-r--r--site/en/index.gmi5
-rw-r--r--site/en/irc.gmi51
-rw-r--r--site/en/librejam/202108.gmi6
-rw-r--r--site/en/librejam/202110.gmi6
-rw-r--r--site/en/librejam/202112.gmi6
-rw-r--r--site/en/librejam/202202.gmi6
-rw-r--r--site/en/librejam/index.gmi48
-rw-r--r--site/en/trade.gmi47
-rw-r--r--site/style.css34
17 files changed, 552 insertions, 320 deletions
diff --git a/.gitignore b/.gitignore
index be44af2..8b2bfc5 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,11 +1,6 @@
-*.html
*.xml
-favicon.ico
-gmi2html
+gmi2html.cgi
-!header.html
-!footer.html
-!/lsand.html
!rss_header.xml
!rss_footer.xml
!rss_item_header.xml
diff --git a/Makefile b/Makefile
index 8f656a9..5eba701 100644
--- a/Makefile
+++ b/Makefile
@@ -1,41 +1,35 @@
-GEMTEXT=$(shell find -L site -type f -name "*.gmi" -print)
-HTML=$(GEMTEXT:%.gmi=%.html)
+.POSIX:
+
+CFLAGS = -O3 -std=c99 -Wall -pedantic -pedantic-errors -pipe
+
RSS=$(shell find -L . -type d -name "*.rss" -print)
RSS_XML=$(RSS:%.rss=%.xml)
.PHONY: clean
.PHONY: all
-all: $(HTML) $(RSS_XML)
-
-%.html: %.gmi header.html footer.html gmi2html
- @echo "GMI2HTML $@"
- cp header.html $@
- ./gmi2html < $< | sed -e 's/\.gmi/\.html/g ; /^<h2>.*/i </div><div class="content">' >> $@
- echo "</div>" >> $@
- cat footer.html >> $@
+all: $(RSS_XML)
-%.xml: %.rss %.rss.header.xml %.rss.item_header.xml rss_item_footer.xml rss_footer.xml
+%.xml: %.rss %.rss.header.xml %.rss.item_header.xml rss_item_footer.xml rss_footer.xml gmi2html.cgi
@echo "RSS $@"
cat $<.header.xml > $@
for i in $(shell ls -r $</*.gmi | head -n 15) ; do \
cat $<.item_header.xml >> $@; \
echo "<title>`sed -n '/^# .*/p' $$i | cut -c 3-`</title>" >> $@; \
echo "<pubDate>`basename $$i | head -c8 | xargs date '+%a, %d %b %Y' -d`</pubDate>" >> $@; \
- echo "<link>https://leagueh.xyz/$$i</link>" | sed 's/site\///g ; s/.gmi/.html/g' >> $@; \
- echo "<description>`./gmi2html < $$i | sed '/^#.*/d ; s/</\&lt;/g ; s/>/\&gt;/g '`</description>" >> $@; \
+ echo "<link>https://leagueh.xyz/$$i</link>" | sed 's/site\///g' >> $@; \
+ echo "<description>`REQUEST_METHOD=GET PATH_INFO=$$i ./gmi2html.cgi | tail -n +4 | sed '/^#.*/d ; s/</\&lt;/g ; s/>/\&gt;/g'`</description>" >> $@; \
cat rss_item_footer.xml >> $@; \
done
cat rss_footer.xml >> $@
-gmi2html: gmi2html.c
+gmi2html.cgi: gmi2html.cgi.c
@echo "CC $@"
- $(CC) $(CFLAGS) $^ -o $@
+ $(CC) $(CFLAGS) -o $@ $^
.PHONY: clean
clean:
- rm -f gmi2html
- rm -f ${HTML}
- rm -f ${RSS_XML}
+ rm -f gmi2html.cgi
+ rm -f $(RSS_XML)
$(V).SILENT:
diff --git a/footer.html b/footer.html
index 4035a66..0a93a56 100644
--- a/footer.html
+++ b/footer.html
@@ -1,3 +1,4 @@
+
<div class="footer">
<p>License: <a href="/git/loh-website/tree/LICENSE.md">AGPL3</a> | <a href="/git/loh-website">/git/loh-website</a></p>
<p>Contact <a href="mailto:root@leagueh.xyz">root@leagueh.xyz</a> for inquiries.</p>
diff --git a/gmi2html.c b/gmi2html.c
deleted file mode 100644
index 936a7fc..0000000
--- a/gmi2html.c
+++ /dev/null
@@ -1,187 +0,0 @@
-#include <ctype.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-static char *lstrip(char *restrict s) {
- size_t i;
- for(i = 0; s[i] != '\0'; i++) {
- if(!isspace(s[i])) {
- return &s[i];
- }
- }
- return &s[i];
-}
-
-static char *rstrip(char *restrict s) {
- char *last_nonspace = s;
- for(size_t i = 0; s[i] != '\0'; i++) {
- if(!isspace(s[i])) {
- last_nonspace = &s[i];
- }
- }
- if(last_nonspace[0] != '\0') {
- last_nonspace[1] = '\0';
- }
- return s;
-}
-
-static char *strip(char *restrict s) {
- return rstrip(lstrip(s));
-}
-
-static void print_sanitized(const char *restrict s) {
- size_t i = 0;
- while(s[i] != '\0') {
- if(s[i] == '<') {
- printf("&lt;");
- }
- else if(s[i] == '>') {
- printf("&gt;");
- }
- else if(s[i] == '&') {
- printf("&amp;");
- }
- else if(s[i] == '"') {
- printf("&quot;");
- }
- else {
- printf("%c", s[i]);
- }
- i++;
- }
-}
-
-int main(int argc, char **argv) {
- int list_mode = 0, preformat_mode = 0;
-
- // Read lines
- char *line = NULL;
- size_t line_buf_len = 0;
- ssize_t line_len;
- while((line_len = getline(&line, &line_buf_len, stdin)) != -1) {
- line[line_len - 1] = '\0';
- line_len--;
-
- // Disable list mode
- if(list_mode && (line[0] != '*' || line[1] != ' ')) {
- list_mode = 0;
- printf("</ul>\n");
- }
-
- // Preformatted mode
- if(preformat_mode) {
- if(line_len == 3 && line[0] == '`' && line[1] == '`' && line[2] == '`') {
- preformat_mode = 0;
- printf("</pre>\n");
- }
- else {
- print_sanitized(line);
- printf("\n");
- }
- continue;
- }
-
- // Blank lines
- if(line[0] == '\0') {
- printf("<br />\n");
- }
-
- // Links
- else if(line_len >= 2 && line[0] == '=' && line[1] == '>') {
-
- // Discard leading whitespace
- char *url = lstrip(&line[2]);
-
- // Get label
- char *label = NULL;
- for(size_t i = 0; url[i] != '\0'; i++) {
- if(isspace(url[i])) {
- url[i] = '\0';
- label = &url[i + 1];
- break;
- }
- }
-
- // Print link
- if(label == NULL) {
- label = url;
- }
- else {
- label = strip(label);
- }
- printf("<a href=\"");
- print_sanitized(url);
- printf("\">");
- print_sanitized(label);
- printf("</a><br />\n");
- }
-
- // Headings
- else if(line[0] == '#') {
- unsigned int header_count = 1;
- if(line_len >= 2 && line[1] == '#') {
- header_count++;
- if(line_len >= 3 && line[2] == '#') {
- header_count++;
- }
- }
- printf("<h%d>", header_count);
- print_sanitized(strip(line + header_count));
- printf("</h%d>\n", header_count);
- }
-
- // Lists
- else if(line_len >= 2 && line[0] == '*' && line[1] == ' ') {
- if(!list_mode) {
- list_mode = 1;
- printf("<ul>\n");
- }
- printf("<li>");
- print_sanitized(strip(line + 2));
- printf("</li>\n");
- }
-
- // Blockquotes
- else if(line[0] == '>') {
- printf("<q>");
- print_sanitized(strip(line + 1));
- printf("</q>\n");
- }
-
- // Preformatted text
- else if(line_len >= 3 && line[0] == '`' && line[1] == '`' && line[2] == '`') {
- preformat_mode = 1;
- printf("<pre>\n");
- }
-
- // Regular text
- else {
- printf("<p>");
- print_sanitized(strip(line));
- printf("</p>\n");
- }
- }
- free(line);
-
- // Disable list mode
- if(list_mode) {
- list_mode = 0;
- printf("</ul>\n");
- }
-
- // Preformatted mode
- if(preformat_mode) {
- preformat_mode = 0;
- printf("</pre>\n");
- }
-
- // Return
- if(feof(stdin)) {
- return EXIT_SUCCESS;
- }
- else {
- return EXIT_FAILURE;
- }
-}
-
diff --git a/gmi2html.cgi.c b/gmi2html.cgi.c
new file mode 100644
index 0000000..e28fd98
--- /dev/null
+++ b/gmi2html.cgi.c
@@ -0,0 +1,361 @@
+#include <ctype.h>
+#include <stdbool.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+/*
+ * !!! WARNING !!!
+ *
+ * This code technically breaks the C spec in that it requires at least three
+ * calls to ungetc() to work, whereas the C spec only guarantees that one call
+ * will work. In practice this doesn't seem to cause issues, but worth
+ * mentioning just in case you're doing weird strict-spec-compliance unit tests
+ * or something, I don't know.
+ *
+ * Everything else is strictly C99 compliant.
+ *
+ * Also, it complies to the Gemtext spec in every way except handling of CRLF
+ * line endings. Because honestly, fuck off. Nobody except asshole Windows devs
+ * uses those little shits anyways, every sane operating system has been using
+ * LF for decades. If you insist on being a special child and using Windows,
+ * then you can deal with the resulting nightmare. You don't get to force other
+ * people to clean up your bullshit. Love, Katherine.
+ *
+ */
+
+static char *path;
+static FILE *f = NULL;
+static FILE *head = NULL;
+static FILE *foot = NULL;
+
+static void print_char(int c) {
+ if(c == '"') {
+ fputs("&quot;", stdout);
+ }
+ else if(c == '\'') {
+ fputs("&apos;", stdout);
+ }
+ else if(c == '&') {
+ fputs("&amp;", stdout);
+ }
+ else if(c == '<') {
+ fputs("&lt;", stdout);
+ }
+ else if(c == '>') {
+ fputs("&gt;", stdout);
+ }
+ else {
+ putchar(c);
+ }
+}
+
+static char print_to_line_end() {
+ int c;
+ for(c = getc(f); c != '\n' && c != EOF; c = getc(f)) {
+ print_char(c);
+ }
+ return c;
+}
+
+static void skip_to_line_end() {
+ for(int c = getc(f); c != '\n' && c != EOF; c = getc(f)) {}
+}
+
+static void paragraph() {
+ fputs("<p>", stdout);
+ int c = print_to_line_end();
+ fputs("</p>", stdout);
+ print_char(c);
+}
+
+static void link() {
+
+ // Check that this is a link
+ int c = getc(f);
+ if(c != '>') {
+ ungetc(c, f);
+ ungetc('=', f);
+ paragraph();
+ return;
+ }
+
+ // Consume whitespace
+ while(isblank(c = getc(f))) {}
+ ungetc(c, f);
+
+ // Print opening tag
+ char url[4096] = {0};
+ size_t url_len = 0;
+ fputs("<p><a href='", stdout);
+ while((c = getc(f)) != ' ' && c != '\t' && c != '\n' && c != EOF) {
+ print_char(c);
+ if(url_len < sizeof(url) - 1) {
+ url[url_len] = c;
+ url_len++;
+ }
+ }
+ fputs("'>", stdout);
+
+ // Use URL as name if there's no label
+ if(c == '\n' || c == EOF) {
+ for(size_t i = 0; i < url_len; i++) {
+ print_char(url[i]);
+ }
+ }
+
+ // Print label
+ else {
+ ungetc(c, f);
+ while(isblank(c = getc(f))) {}
+ ungetc(c, f);
+ c = print_to_line_end();
+ }
+
+ // Print closing tag
+ fputs("</a></p>", stdout);
+ print_char(c);
+}
+
+static void header() {
+
+ // See what level the header is
+ unsigned char level = 1;
+ int c;
+ for(c = getc(f); c == '#' && level < 6; c = getc(f)) {
+ level++;
+ }
+
+ // Check for mandatory space
+ if(c != ' ') {
+ for(unsigned char i = 0; i < level; i++) {
+ ungetc('#', f);
+ }
+ ungetc(c, f);
+ paragraph();
+ return;
+ }
+
+ // Print header
+ printf("<h%d>", level);
+ c = print_to_line_end();
+ printf("</h%d>", level);
+ print_char(c);
+}
+
+static bool is_list_tag() {
+ int c;
+ if((c = getc(f)) != '*') {
+ ungetc(c, f);
+ return false;
+ }
+ else if((c = getc(f)) != ' ') {
+ ungetc(c, f);
+ ungetc('*', f);
+ return false;
+ }
+ return true;
+}
+
+static void list() {
+ ungetc('*', f);
+ if(!is_list_tag()) {
+ paragraph();
+ return;
+ }
+
+ // Print rest of elements
+ puts("<ul>");
+ ungetc(' ', f);
+ ungetc('*', f);
+ while(is_list_tag()) {
+ fputs("<li>", stdout);
+ int c = print_to_line_end();
+ fputs("</li>", stdout);
+ print_char(c);
+ }
+ puts("</ul>");
+ paragraph();
+}
+
+static void blockquote() {
+ fputs("<blockquote>", stdout);
+ int c = print_to_line_end();
+ fputs("</blockquote>", stdout);
+ print_char(c);
+}
+
+static bool is_preformat_tag() {
+ int c;
+ if((c = getc(f)) != '`') {
+ ungetc(c, f);
+ return false;
+ }
+ else if((c = getc(f)) != '`') {
+ ungetc(c, f);
+ ungetc('`', f);
+ return false;
+ }
+ else if((c = getc(f)) != '`') {
+ ungetc(c, f);
+ ungetc('`', f);
+ ungetc('`', f);
+ return false;
+ }
+ return true;
+}
+
+static void preformatted() {
+ ungetc('`', f);
+ if(!is_preformat_tag()) {
+ paragraph();
+ return;
+ }
+ skip_to_line_end();
+ puts("<pre>");
+
+ // Read lines until it ends
+ int c = 0;
+ while(!is_preformat_tag() && c != EOF) {
+ c = print_to_line_end();
+ print_char(c);
+ }
+ skip_to_line_end();
+ puts("</pre>");
+}
+
+// Always starts at the beginning of a line
+static void read_element() {
+ int c = getc(f);
+ if(c == EOF) {
+ return;
+ }
+ else if(c == '=') {
+ link();
+ }
+ else if(c == '#') {
+ header();
+ }
+ else if(c == '*') {
+ list();
+ }
+ else if(c == '>') {
+ blockquote();
+ }
+ else if(c == '`') {
+ preformatted();
+ }
+ else {
+ ungetc(c, f);
+ paragraph();
+ }
+}
+
+static void read_request() {
+
+ // Make sure this is a GET request
+ char *method = getenv("REQUEST_METHOD");
+ if(method == NULL || strcmp(method, "GET") != 0) {
+ puts("Status: 405 Method Not Allowed");
+ puts("Allow: GET\n");
+ exit(EXIT_SUCCESS);
+ }
+
+ // Get request path
+ path = getenv("PATH_INFO");
+ if(path == NULL) {
+ puts("Status: 500 Internal Server Error\n");
+ exit(EXIT_SUCCESS);
+ }
+
+ // Check file extension
+ char *extension = strrchr(path, '.');
+ if(extension == NULL || strcmp(extension, ".gmi") != 0) {
+ puts("Status: 403 Forbidden\n");
+ exit(EXIT_SUCCESS);
+ }
+}
+
+static void write_headers() {
+ puts("Content-Type: text/html");
+}
+
+static void open_head() {
+
+ // Get path
+ const char *path = getenv("GMI2HTML_HEAD");
+ if(path == NULL) {
+ return;
+ }
+
+ // Open file
+ head = fopen(path, "r");
+ if(head == NULL) {
+ puts("Status: 500 Internal Server Error\n");
+ exit(EXIT_SUCCESS);
+ }
+}
+
+static void open_foot() {
+
+ // Get path
+ const char *path = getenv("GMI2HTML_FOOT");
+ if(path == NULL) {
+ return;
+ }
+
+ // Open file
+ foot = fopen(path, "r");
+ if(foot == NULL) {
+ puts("Status: 500 Internal Server Error\n");
+ exit(EXIT_SUCCESS);
+ }
+}
+
+static void copy_file(FILE *restrict f) {
+ int c;
+ while((c = getc(f)) != EOF) {
+ putchar(c);
+ }
+ fclose(f);
+}
+
+static void write_content() {
+
+ // Open file
+ f = fopen(path, "r");
+ if(f == NULL) {
+ puts("Status: 404 Not Found\n");
+ exit(EXIT_SUCCESS);
+ }
+ puts("Status: 200 OK");
+ puts("");
+
+ // Copy head
+ if(head != NULL) {
+ copy_file(head);
+ }
+
+ // Read file
+ while(!feof(f) && !ferror(f)) {
+ read_element();
+ }
+
+ // Copy foot
+ if(foot != NULL) {
+ copy_file(foot);
+ }
+
+ // Close file
+ fclose(f);
+}
+
+int main(int argc, char **argv) {
+ read_request();
+ open_head();
+ open_foot();
+ write_headers();
+ write_content();
+ return EXIT_SUCCESS;
+}
+
diff --git a/header.html b/header.html
index 0bd147c..efa331f 100644
--- a/header.html
+++ b/header.html
@@ -3,8 +3,3 @@
<meta charset="UTF-8">
<link rel="stylesheet" href="/style.css">
<body>
-<div class="header">
-<a class="header" href="/">⚓</a>
-<p class="header">League of Humanity</p>
-</div>
-<div class="content">
diff --git a/site/cgit.css b/site/cgit.css
index 0bd0f6b..c43bf8b 100644
--- a/site/cgit.css
+++ b/site/cgit.css
@@ -1,9 +1,7 @@
@import url("/style.css");
html {
- font-family: monospace;
- font-size: large;
- max-width: 1024px;
+ max-width: 64em;
}
/* cgit */
@@ -18,8 +16,7 @@ div#cgit table#header td.main {
}
div#cgit table.tabs td a {
- padding: 2px 0.75em;
- font-size: 110%;
+ margin: 1em;
}
div#cgit table.tabs td a.active {
@@ -30,20 +27,6 @@ div#cgit table.tabs td.form form {
white-space: nowrap;
}
-div#cgit .left {
- text-align: left;
-}
-
-div#cgit .right {
- text-align: right;
-}
-
-div#cgit div.footer {
- margin-top: 0.5em;
- text-align: center;
- font-size: 80%;
-}
-
div#cgit table.list td {
padding-right: 1em;
white-space: nowrap;
@@ -53,47 +36,43 @@ div#cgit table.list th {
text-align: left;
}
-a.button {
- margin-left: 0.5em;
-}
-
/* Summary */
div#cgit a.branch-deco {
- margin: 0px 0.5em;
- padding: 0px 0.25em;
+ margin: 0.5em;
+ padding: 0.1em 0.25em;
background-color: var(--green);
color: var(--fg);
text-decoration: none;
}
div#cgit a.tag-deco {
- margin: 0px 0.5em;
- padding: 0px 0.25em;
+ margin: 0.5em;
+ padding: 0.1em 0.25em;
background-color: var(--yellow);
color: var(--fg);
text-decoration: none;
}
div#cgit a.tag-annotated-deco {
- margin: 0px 0.5em;
- padding: 0px 0.25em;
+ margin: 0.5em;
+ padding: 0.1em 0.25em;
background-color: var(--orange);
color: var(--fg);
text-decoration: none;
}
div#cgit a.remote-deco {
- margin: 0px 0.5em;
- padding: 0px 0.25em;
+ margin: 0.5em;
+ padding: 0.1em 0.25em;
background-color: var(--purple);
color: var(--fg);
text-decoration: none;
}
div#cgit a.deco {
- margin: 0px 0.5em;
- padding: 0px 0.25em;
+ margin: 0.5em;
+ padding: 0.1em 0.25em;
background-color: var(--red);
color: var(--fg);
text-decoration: none;
@@ -103,13 +82,7 @@ div#cgit a.deco {
div#cgit div.diffstat-header {
font-weight: bold;
- padding-top: 1.5em;
-}
-
-div#cgit table.diffstat td {
- padding: 0.2em 0.2em 0.1em 0.1em;
- font-size: 100%;
- border: none;
+ margin: 1em 0;
}
div#cgit table.diffstat td.mode {
@@ -121,11 +94,11 @@ div#cgit table.diffstat a {
}
div#cgit table.diffstat td.graph {
- width: 500px;
+ width: 100%;
}
div#cgit table.diffstat td.graph td {
- height: 7pt;
+ height: 1em;
}
div#cgit table.diffstat td.graph td.add {
@@ -137,22 +110,19 @@ div#cgit table.diffstat td.graph td.rem {
}
div#cgit div.diffstat-summary {
- padding-top: 0.5em;
+ margin-top: 1em;
}
div#cgit table.diff td {
- white-space: pre;
- border-radius: 0.5em;
background-color: var(--pre);
+ border-radius: 0.5em;
+ font-family: monospace;
+ padding: 1em;
+ white-space: pre;
}
div#cgit table.diff {
- width: 10px;
-}
-
-div#cgit table.diff td div.head {
- font-weight: bold;
- margin-top: 1em;
+ width: 100%;
}
div#cgit table.diff td div.hunk {
diff --git a/site/en/hexchat.webm b/site/en/hexchat.webm
new file mode 100644
index 0000000..b60d1e6
--- /dev/null
+++ b/site/en/hexchat.webm
Binary files differ
diff --git a/site/en/index.gmi b/site/en/index.gmi
index 9a918eb..33cb49a 100644
--- a/site/en/index.gmi
+++ b/site/en/index.gmi
@@ -4,8 +4,8 @@ The League of Humanity is a community focused on promoting kindness and supporti
=> news.xml Site news
=> privacy.gmi Online privacy guide
+=> irc.gmi IRC network
=> https://leagueh.xyz/git/ Git repositories
-=> ircs://leagueh.xyz/#loh-en #loh-en on LOHIRC. Connect using an IRC client *with SSL*
## Sitemap
@@ -16,7 +16,8 @@ The League of Humanity is a community focused on promoting kindness and supporti
Find other people interested in the same sorts of things.
-=> librejam/index.gmi LibreJam - a bimonthly game jam to promote libre games
+=> trade.gmi Trade - a virtual card trading game played over SSH.
+=> librejam/index.gmi LibreJam - a bimonthly game jam to promote libre games.
## FAQ
diff --git a/site/en/irc.gmi b/site/en/irc.gmi
new file mode 100644
index 0000000..e890581
--- /dev/null
+++ b/site/en/irc.gmi
@@ -0,0 +1,51 @@
+# LOHIRC network
+
+Our IRC network provides a safe and well-moderated space for discussion, idle chat, and support. It's highly recommended that you come visit!
+
+=> ircs://leagueh.xyz/#loh-en #loh-en on LOHIRC. Connect using an IRC client *with SSL*
+
+## How to connect using Hexchat (Windows, Linux, BSD)
+
+First, download and install Hexchat from the official Hexchat site. Open Hexchat and set the nickname field to your chosen name, and the "second choice" and "third choice" fields to alternative nicknames if the one you chose is already taken. Your username should usually be the same as your nickname, but it can be different if you want.
+
+Next, add a new network and name it LOHIRC. Click edit to edit the new network, and then click edit again to set the server address. Set the server address to "leagueh.xyz/6697". Finally, make sure "Use SSL for all the servers on this network" is checked, then click close to save the network.
+
+Now whenever you open Hexchat, you can select LOHIRC from the network list and click "Connect" to connect to it. The chat window will then open, and ask you if you want to join a channel. Select "Join this channel" and enter "#loh-en" to join the general English channel, then click ok. You can now start chatting!
+
+=> https://hexchat.github.io/downloads.html Hexchat downloads
+=> hexchat.webm Guide video
+
+### How to connect on other platforms
+
+* Windows: Hexchat
+* Linux/BSD: Hexchat, irssi, WeeChat
+* Android: Revolution IRC
+
+## IRC tips
+
+The most significant difference between IRC and other chat services is that when you're not connected to the server, you can't receive messages. Users won't be able to direct message you, and you won't be able to see messages that were sent before you reconnected. In this way, IRC is similar to real life: You can't talk to someone unless you're in the same room as them. Keep this in mind when going offline, but know that it's perfectly normal to not be always connected to the Internet, going offline every once in a while is healthy.
+
+Also note that users don't have to register an account to connect to the network; this means that anyone can take your username at any time. To prevent this, you can register an LOH account via SSH using "ssh register@leagueh.xyz". More information on this will be posted later.
+
+Below is a list of useful IRC commands:
+
+* /list - List all available channels
+* /join <channel> - Join a channel
+* /part <channel> - Leave a channel
+* /who <channel> - See who is in a channel
+* /topic <channel> - See a channel's topic
+* /whois <nick> - See more information about a user
+* /ison <nick> - See if a user is online
+* /msg <nick> - Send a single direct message to a user
+* /query <nick> - Open a direct messaging window with a user
+* /help <command> - See information on a command
+
+Finally, keep in mind that *anybody* can create channels on IRC, not just server operators as is the case with a certain competing service. At any time you can create a new channel by simply using "/join #newchannelname", and if there are no existing users in that channel you will automatically be made a channel operator. Keep in mind that operator status will be lost if you disconnect while other users are in the channel, so for best results contact a server operator to make it permanent.
+
+LOHIRC is also not the only IRC network out there; in fact, it's an extremely small one. If you're looking for a larger community or support for a particular project, consider hopping into some other IRC networks such as OFTC or Libera Chat.
+
+=> https://www.oftc.net/ OFTC IRC network
+=> https://libera.chat/ Libera Chat IRC network
+
+Happy chatting!
+
diff --git a/site/en/librejam/202108.gmi b/site/en/librejam/202108.gmi
new file mode 100644
index 0000000..6c800fe
--- /dev/null
+++ b/site/en/librejam/202108.gmi
@@ -0,0 +1,6 @@
+# LibreJam - 202108
+* Week Number: 202108
+* Theme: Swarm
+* Theme announced at: 2021-08-01 00:00 UTC
+* Submissions end at: 2021-08-07 23:59 UTC
+* Ratings end at: 2021-08-14 23:59 UTC
diff --git a/site/en/librejam/202110.gmi b/site/en/librejam/202110.gmi
new file mode 100644
index 0000000..4dac963
--- /dev/null
+++ b/site/en/librejam/202110.gmi
@@ -0,0 +1,6 @@
+# LibreJam - 202110
+* Week Number: 202110
+* Theme: Noise
+* Theme announced at: 2021-10-01 00:00 UTC
+* Submissions end at: 2021-10-07 23:59 UTC
+* Ratings end at: 2021-10-14 23:59 UTC
diff --git a/site/en/librejam/202112.gmi b/site/en/librejam/202112.gmi
new file mode 100644
index 0000000..bd15588
--- /dev/null
+++ b/site/en/librejam/202112.gmi
@@ -0,0 +1,6 @@
+# LibreJam - 202112
+* Week Number: 202112
+* Theme: Leech
+* Theme announced at: 2021-12-01 00:00 UTC
+* Submissions end at: 2021-12-07 23:59 UTC
+* Ratings end at: 2021-12-14 23:59 UTC
diff --git a/site/en/librejam/202202.gmi b/site/en/librejam/202202.gmi
new file mode 100644
index 0000000..f6e15b0
--- /dev/null
+++ b/site/en/librejam/202202.gmi
@@ -0,0 +1,6 @@
+# LibreJam - 202202
+* Week Number: 202202
+* Theme: Gates
+* Theme announced at: 2022-02-01 00:00 UTC
+* Submissions end at: 2022-02-14 23:59 UTC
+* Ratings end at: 2022-02-21 23:59 UTC
diff --git a/site/en/librejam/index.gmi b/site/en/librejam/index.gmi
index 9af6620..698b78d 100644
--- a/site/en/librejam/index.gmi
+++ b/site/en/librejam/index.gmi
@@ -1,14 +1,13 @@
# LibreJam
Hello, and welcome to the home of the bimonthly game jam for libre games, LibreJam!
-At the beginning of every other month, the jam begins, with a unique theme being released to add extra challenge. Participants have one week to develop and publish their game, working solo or in teams. Once time is up, all games are published to the site for others to view, and ratings are opened for seven days, before a winner is announced.
+At the beginning of every other month, the jam begins, with a unique theme being released to add extra challenge. Participants have two weeks to develop and publish their game, working solo or in teams. Once time is up, all games are published to the site for others to view, and ratings are opened for seven days, before a winner is announced.
## Current Jam
-* Status: Go!
-* Week number: 202108
-* Theme: Swarm
-* Theme announced at: 2021-08-01 00:00 UTC
-* Submissions end at: 2021-08-07 23:59 UTC
-* Ratings end at: 2021-08-14 23:59 UTC
+* Week number: 202208
+* Theme: Replication
+* Theme announced at: 2022-08-01 00:00 UTC
+* Submissions end at: 2022-08-14 23:59 UTC
+* Ratings end at: 2022-08-21 23:59 UTC
## Rules
* All code and assets must be provided under an FSD-approved[1] license. Any software required to run the game must also be available under an FSD-approved license.
@@ -18,31 +17,44 @@ At the beginning of every other month, the jam begins, with a unique theme being
=> https://www.gnu.org/licenses/license-list.html [1] FSD approved license list
## Submissions
-Once your game is finished, submit it by posting it in the mailing list[2]. The subject line should be in the format "[SUBMISSION] WEEK - Game name here". Obviously, you should replace "WEEK" with the week number (top of this page).
-You can either attach your game's source code (in "tar". or "zip" format) to the email *or* upload it to an external source (please do this if your game is larger than 1 MiBs!). If you choose the latter, you must provide a SHA256 checksum, so we can verify the file has not changed. On UNIX systems, you can find the SHA256 checksum of a file easily using the "sha256sum" command.
-Note that the mailing list is not private; your messages will be displayed publicly, and others will be able to reply to it with their own comments and feedback.
-=> https://leagueh.xyz/m/librejam/ [2] LibreJam mailing list
+Once your game is finished, submit it by using our IRC bot.
+Please include a Readme file in your repository and give a brief description of your game and instructions on how to run it. Also create a branch with the version of the game, which you want to submit.
+Note that the submissions will be publicy viewable in the sumissions list[2], and others will be able to reply to it with their own comments and feedback via our IRC Bot.
+
+Bot command for submissions:
+```
+!submit <url> [-b branch] <name>
+```
+=> gemini://xwx.moe/librejam IRC bot submissions page
## Ratings
-Anyone can submit ratings for games, not just jam participants. To submit a rating, reply to the submission post for the game in question on the mailing list for the following categories:
-* Overall (1-10)
-* Theme (1-10)
-* Graphics (1-10)
-* Sound (1-10)
+Anyone can submit ratings for games, not just jam participants. To submit a rating, use our IRC Bot.
Ratings are accepted until the end time given at the top of the page, after which ratings for all games are tallied and winners are announced.
+Bot command for rating:
+```
+!rate <index> <1-10> [comment]
+```
+
## Socialising
-Come and chat with us in the #librejam IRC channel[3] on LOHIRC. Here you can brainstorm, team up and chat about development! If you have a question about the jam, write to the mailing list, or chat in the IRC channel.
+Come and chat with us in the #librejam IRC channel[3] (webchat also available[4]) on LOHIRC. Here you can brainstorm, team up and chat about development! If you have a question about the jam, come and chat in the IRC channel.
=> ircs://leagueh.xyz/#librejam [3] #librejam on LOHIRC. Connect using an IRC client *with SSL*
+=> https://kiwiirc.com/nextclient/?settings=9990a2af03a4a53c76b3529a6c420adc [4] Webchat at KiwiIRC
## Guidelines
In addition to the above rules, there are some guidelines that you might want to keep in mind while developing your game. These are not mandatory, but they're generally good advice for helping you create an end product which is fun for everyone:
* If you are submitting your game in a language other than English, please consider providing an English translation as well.
* Write a build script which makes compiling your game from source easy. Many people are using devices with different software or libraries. As a result, it is often necessary for them to compile your game from source in order to play it. Creating an easy to use build script not only helps expand your audience, but it is also good software development practice in general, and reflects well on your competency as a programmer.
* Allow players to rebind the controls. Not everyone uses a standard "QWERTY" keyboard layout. Permanently setting your game controls to common combinations like "WASD" can make life very difficult for such players.
-* Describe your game in your submission post. This will improve your chances of receiving feedback.
+* Describe your game in your submissions readme. This will improve your chances of receiving feedback.
## Jam index
+=> 202206.gmi 202206 - Heist
+=> 202204.gmi 202204 - Power
+=> 202202.gmi 202202 - Gates
+=> 202112.gmi 202112 - Leech
+=> 202110.gmi 202110 - Noise
+=> 202108.gmi 202108 - Swarm
=> 202106.gmi 202106 - Time
=> 202104.gmi 202104 - Snowed in
=> 202102.gmi 202102 - Subnautical
diff --git a/site/en/trade.gmi b/site/en/trade.gmi
new file mode 100644
index 0000000..bd2530f
--- /dev/null
+++ b/site/en/trade.gmi
@@ -0,0 +1,47 @@
+# Trade
+
+Trade is a virtual card trading game played in the terminal with ASCII art graphics.
+
+## How to play
+
+Playing Trade is simple. Register an LOH account with 'ssh register@leagueh.xyz', then log in with 'ssh YourName@leagueh.xyz'.
+
+Use the 'help' command to show a help message, and 'open' to open a card pack. Each pack contains three random cards, and you can open a pack once a day. You can see the cards you have with 'list YourName'.
+
+### Tiers
+
+Cards are placed into tiers based on their copy number. There are 16 tiers, whose rarity increases exponentially, which are listed below from most common to least common:
+
+* Alpha
+* Beta
+* Gamma
+* Delta
+* Epsilon
+* Zeta
+* Theta
+* Iota
+* Kappa
+* Lambda
+* Omicron
+* Rho
+* Sigma
+* Tau
+* Upsilon
+* Omega
+
+There is one Omega-tier copy of each card, two Upsilon-tier copies, four Tau-tier copies, and so on. There are 65,536 copies of every card in total.
+
+### Trading
+
+Trading is easy. First, find someone to trade with. The best place to look for traders is #loh-en on the LOH IRC server.
+
+Once you've found someone to trade with, type 'offer TheirName'. You will then be prompted to enter the names and copy numbers of the cards you would like to give them, and then the names and copy numbers of the cards you want to receive from them. After selecting your cards, you will be asked to confirm your trade.
+
+Finally, ask the trader to type 'trade YourName' to accept your trade offer. If they confirm, the trade will be completed.
+
+## Contributing
+
+If you have the time and would like to contribute to the game, please consider creating your own card designs! Submissions can be sent to root@leagueh.xyz (or katp32 on the LOH IRC server), and will be included in the next season of cards.
+
+Legal notice: Submitted card designs are made a component of the Trade source code, and are therefore provided under the AGPL3 license. By submitting a card design, or any other contribution to the Trade source code, you agree to these terms.
+
diff --git a/site/style.css b/site/style.css
index 488afe3..1985812 100644
--- a/site/style.css
+++ b/site/style.css
@@ -46,17 +46,6 @@ html {
max-width: 48em;
}
-/* Put a border around content sections */
-div.content {
- border-style: double;
- padding: 1em;
-}
-
-/* Disable margins on text, we use <br> for that */
-h1, h2, h3, h4, h5, h6, p, ul, pre {
- margin: 0;
-}
-
/* Add hashtag symbols for cosmetic purposes */
h1::before {
content: "# ";
@@ -88,7 +77,7 @@ a {
line-height: 1.3;
}
-/* Appropriately style preformatted/"code" text */
+/* Appropriately style preformatted text */
pre {
background-color: var(--pre);
border-radius: 0.5em;
@@ -101,29 +90,8 @@ a:hover {
color: var(--bg);
}
-/* Header */
-.header {
- font-size: xx-large;
- text-align: center;
- margin: 0.5em;
-}
-
-p.header {
- margin-top: 0.5em;
-}
-
-a.header {
- background-color: var(--fg);
- border-radius: 0.25em;
- color: transparent;
- padding: 0.25em;
- text-decoration: none;
- text-shadow: 0 0 0 var(--bg);
-}
-
/* Footer */
.footer {
text-align: center;
margin: 1em;
}
-