Compare commits

...

11 Commits

Author SHA1 Message Date
hedy 660cd3bd5b
Better post meta formatting on gemini 2024-04-10 21:14:23 +08:00
hedy db72daf150
Don't make post description italicized 2024-04-10 21:14:12 +08:00
hedy 70a557b3fd
Add hr for footer for text-based browsers 2024-04-10 21:13:53 +08:00
hedy 175279bda8
Fix update date on atom feeds 2024-04-10 21:13:34 +08:00
hedy 3de8393a3d
Better styling for footnotes 2024-04-10 21:13:10 +08:00
hedy c1e93c0abf
Add shortcode for getting the RelPermalink of a post resource 2024-04-10 21:12:35 +08:00
hedy 62b5d77e9c
New post 2024-04-10 21:09:54 +08:00
hedy fbda5c5624
Show descriptions in gemlog post list 2024-04-10 20:43:32 +08:00
hedy f1e903e3d7
Switch to python script for gemini cleaning 2024-04-10 20:37:18 +08:00
hedy 711d0cfaa0
Fix typo 2024-04-10 15:10:14 +08:00
hedy 4bf15aa4d3
Restructure hierarchy of after-content and footer to modify placing of hr 2024-04-10 15:02:22 +08:00
18 changed files with 727 additions and 55 deletions

View File

@ -49,27 +49,7 @@ gemini:
$(RSYNC) $(RSYNC_FLAGS) public/posts/gemini/index.gmi $(GEMINI_DEST)/posts/index.gmi
gemini-clean:
@# This is the target that has caused me the most trouble, literally lost my
@# entire public_gemini from this when I had a bug here.
@# So PLEASE PLEASE PLEASE make sure to run make all (or make backup
@# manually) before using this!
@#
@# Remove copied post files
find $(GEMINI_DEST) -wholename '*/$(GEMINI_DEST_BASE)/posts/????-??-??-*.gmi' -delete
find $(GEMINI_DEST) -wholename '*/$(GEMINI_DEST_BASE)/????-??-??-*.gmi' -delete
@# Use ugly urls, find the dirs that only contains a single 'index.gmi',
@# excluding the root index.gmi
find $(GEMINI_DEST) -wholename '*/index.gmi' -not -wholename '$(UGLYURL_EXCLUDE)' -not -wholename '*/posts/index.gmi' -not -wholename '*/$(GEMINI_DEST_BASE)/index.gmi' -exec echo '{}' \; > out.txt
@# Copy /blah/index.gmi to blah.gmi then rm /blah/
@while read line; do \
dest=$$( echo $$line | sed 's_/index.gmi$$_.gmi_'); \
dir=$$( echo $$line | sed 's_/index.gmi$$__'); \
echo Syncing and removing $$(basename $$dir); \
rsync $$line $$dest; \
rm -rf $$dir; \
done < out.txt; \
rm out.txt
@echo done
GEMINI_DEST=$(GEMINI_DEST) python3 bin/gemini-clean.py
html:
$(RSYNC) $(RSYNC_FLAGS) public/ --exclude '*.gmi' --exclude gemini $(HTML_DEST)

View File

@ -20,6 +20,22 @@ design. It has a few custom colors, a sans-serif font stack, and some styling in
the footer and nav. Everything else is partially based on top of [simple
css](https://simplecss.org) and sometimes [seirdy's site](https://seirdy.one).
## hardcoded values
In WWW, posts' resources are stored under the same directory as the post:
- `/posts/my-slug/index.html` (the post itself)
- `/posts/my-slug/resource-1.png`
- `/posts/my-slug/resource-2.svg`
In gemini, posts' resources are stored together under a separate folder:
- `/posts/my-slug.gmi` (the post itself)
- `/posts/assets/my-slug_resource-1.png`
- `/posts/assets/my-slug_resource-2.png`
These files might need to be changed to customize this:
- `bin/gemini-clean.py`
- `layouts/shortcodes/get-resource-link.*`
## todo
- [x] let gemini version also have a post page at /posts/index.gmi

View File

@ -274,8 +274,13 @@ main, #after-content {
max-width: 45rem;
margin: auto;
}
#after-content {
margin-bottom: 4rem;
}
#after-content:empty {
display: none;
}
footer {
text-align: center;
font-size: .9rem;
@ -546,17 +551,28 @@ a.anchor:hover {
color: var(--text-light);
}
#content div#main {
border-bottom: 2px solid var(--border-light);
padding-bottom: 1rem;
}
.footnotes {
margin-top: 3rem;
font-size: .9rem;
color: var(--text-light);
}
.footnotes #footnotes-heading {
margin-top: 1.5rem;
}
.footnotes ol {
margin-top: none;
}
small {
font-size: .8rem;
color: var(--text-light);
}
#after-content {
/* TODO: check if the #after-content block has any content before adding the
* section in _default/baseof.html */
margin-top: 2rem;
}
ul li {
/* Fix sizing of tap target when i's a list of links */
margin-bottom: 0.5rem;

95
bin/gemini-clean.py Normal file
View File

@ -0,0 +1,95 @@
#!/usr/bin/env python3
# gemini-clean
# 2024 - hedy - initial implementation with logging
# post process gemini output
import os
import shutil
import sys
from functools import wraps
from glob import glob
GMI_DEST = os.environ["GEMINI_DEST"]
DRY_RUN = len(sys.argv) > 2 and \
sys.argv[1].lower() in ('n', '-n', '--dry-run', 'wtf', 'f')
def log(fn):
@wraps(fn)
def inner(*args):
if DRY_RUN:
print("would", end=" ")
print(fn.__name__.replace('_', ' '),
'->'.join(p.removeprefix(GMI_DEST) for p in args))
if not DRY_RUN:
fn(*args)
return inner
@log
def remove(p: str):
if os.path.isdir(p):
os.rmdir(p)
else:
os.remove(p)
@log
def FORCE_remove_dir(p: str):
shutil.rmtree(p, ignore_errors=True)
@log
def rename(f: str, t: str):
os.rename(f, t)
@log
def mkdir(d: str):
os.makedirs(d, exist_ok=True)
################################################################
## Begin gemini clean up
# Copied as-is files
for file in (*glob(f"{GMI_DEST}/posts/????-??-??-*.gmi"),
*glob(f"{GMI_DEST}/????-??-??-*.gmi")):
remove(file)
# Uglify URLs
for dir in glob(f"{GMI_DEST}/*/"):
if dir.split("/")[-1] == "posts":
continue
files = glob(f"{dir}/*")
if len(files) == 1 and files[0].split("/")[-1] == "index.gmi":
new_file = files[0].replace("/index.gmi", ".gmi")
rename(files[0], new_file)
remove(dir)
################################################################
## Uglify posts URLs and move post assets to a dedicated folder.
rsrc_dir = f"{GMI_DEST}/posts/assets/"
rsrc_fmt = rsrc_dir + "{slug}_{file}"
# Initialize empty resource dir
FORCE_remove_dir(rsrc_dir)
mkdir(rsrc_dir)
for path in glob(f"{GMI_DEST}/posts/*"):
if not os.path.isdir(path):
continue
if path == rsrc_dir.rstrip('/'):
continue
for file in glob(f"{path}/*"):
basename = file.split("/")[-1]
if basename == "index.gmi":
# Uglify posts URLs
slug = file.split("/")[-2]
rename(file, f"{path}.gmi")
continue
# Treat any non-index.gmi file in a post dir as resource for this post.
# Move to dedicated resource directory.
rename(file, rsrc_fmt.format(slug=slug, file=basename))
remove(path)

View File

@ -17,7 +17,7 @@ This is where my gemlog and blog lives. It is statically generated with Hugo and
=> https://gohugo.io Hugo Homepage
=> //tilde.cafe
The site source is always linked at the footer, pointing to the SourceHut repo. It is also mirroed on GitHub.
The site source is always linked at the footer, pointing to the SourceHut repo. It is also mirrored on GitHub.
=> https://git.sr.ht/~hedy/site
=> https://github.com/hedyhli/site

Binary file not shown.

View File

@ -0,0 +1,253 @@
The visual block mode in Vim lets you edit text simultaneously across adjacent lines, similar to the "Alt-drag" feature in modern editors, but there's more you can do with it.
One of the basic formatting style that can be done to plain text content would be putting blocks of lines into columns, i.e., from this:
```
List title 1
- Item 1
- Item 2
- Item 3
List title 2
- Item 1
- Item 2
- Item 3
```
To this:
```
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
You can easily convert the text in between those two formats just by using visual block mode to do something similar to paste(1) (see the appendix).
=> {{< get-resource-link "demo.webm">}} Demo video
## Creating columns
Let's start with the vertical form, and put your cursor on the position marked by the block (▋)
```
List title 1
- Item 1
- Item 2
- Item 3
List title 2
- Item 1
- Item 2
▋ Item 3
```
Begin visual block selection mode with `<C-v>`. Select the first character at each line with `3k`, then extend selection to the entire block using `$h`.
Your cursor should now be on the "2" with the entire "List title 2" and the three list items below it selected:
```
List title 1
- Item 1
- Item 2
- Item 3
List title ▋
- Item 1
- Item 2
- Item 3
```
Now hit `x` (or `d`) to remove the block and save it in one of the default registers temporarily.
```
List title 1
- Item 1
- Item 2
- Item 3
```
Now, we prepare the first list to be able to paste the second list that was just deleted. Pad spaces at the end of each line of the first list. Spaces will be shown as `_` throughout the example.
If you don't already have Vim/Neovim setup to highlight trailing spaces, you can do so temporarily now by running `:match Underlined '\s\+$'`.
```
List title 1_
- Item 1_____
- Item 2_____
- Item 3_____
```
Now we can paste the block we've deleted! Place your cursor on the trailing
space after "List title 1":
```
List title 1▋
- Item 1_____
- Item 2_____
- Item 3_____
```
And hit `p`:
```
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
_Voila!_ The two lists are now merged into two columns side by side.
You can easily adjust the spacing between the columns using visual block mode. Place your cursor on the space in-between the two list titles:
```
List title 1▋List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
Enter visual block mode and select the entire vertical column of spaces:
```
List title 1▋List title 2
- Item 1 ▋- Item 1
- Item 2 ▋- Item 2
- Item 3 ▋- Item 3
```
Hit `A` to append text after each selection. Add a few spaces as you see fit, and exit visual block mode (`ESC`).
```
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
## Removing columns
Let's transform the text in reverse[^1]. We'll break these two columns up and have them show up one following another vertically like what we've started with. This might be needed when the first or second list becomes too long and you decide to stop having them show up side by side.
[^1]: If you actually just want to reverse the process without any editing in between, you should of course use a few undo commands ;-)
First, place your cursor at the beginning of the third item on the second list.
```
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 ▋ Item 3
```
We'll use a similar process as before to select the second list with visual block mode. Enter visual block mode with `<C-v>`, hit `3k`, then `$h`.
Now delete the text like before.
Next we'll have to create enough space under the first list for the second list to be pasted. (Note the trailing spaces here are only shown for completeness.)
```
List title 1____
- Item 1________
- Item 2________
- Item 3________
```
There should be four empty lines after a blank line following the first list.
Place your cursor on the start of the second blank line:
```
List title 1____
- Item 1________
- Item 2________
- Item 3________
```
And hit `p`.
```
List title 1____
- Item 1________
- Item 2________
- Item 3________
List title 2
- Item 1
- Item 2
- Item 3
```
And we're back to the original format.
You can easily remove the trailing spaces on the first list by running the substitution command on a visual selection of the first list.
Use either visual mode or visual line mode to select the first paragraph, then use `:'<,'>s/\s\+$//`.
```
List title 1
- Item 1
- Item 2
- Item 3
List title 2
- Item 1
- Item 2
- Item 3
```
That's it!
Visual block mode is just one of the useful tools when formatting plain text and making ascii art. I frequently use the replace mode ("write through") with `R` to overwrite content without breaking up columns.
You can learn more about the visual block mode in Vim in the docs:
```vim
:h visual-block
```
## Appendix
Here's an example shell session to demonstrate how you can do the same thing described in the article using the shell built-in `paste(1)`. Again, spaces are represented as `_`.
```
$ cat > l1.txt
List title 1_
- Item 1_____
- Item 2_____
- Item 3_____
^D
```
```
$ cat > l2.txt
List title 2
- Item 1
- Item 2
- Item 3
^D
```
```
$ paste -d ' ' l1.txt l2.txt
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
As for converting it back, I might opt for awk(1), another scripting language, or just use Vim's visual block mode.

View File

@ -0,0 +1,300 @@
---
title: "Vim visual block mode for column editing"
description: The visual block mode in Vim/Neovim is quite powerful. You can use it for "column" editing and vertically pasting blocks of text similar to paste(1).
date: 2024-04-10T13:22:46+08:00
draft: false
outputs:
- html
- gemtext
tags:
- howto
slug: vim-column-editing
footnotes_heading: Footnotes
---
The visual block mode in Vim lets you edit text simultaneously across adjacent
lines, similar to the "Alt-drag" feature in modern editors, but there's more you
can do with it.
One of the basic formatting style that can be done to plain text content would
be putting blocks of lines into columns, i.e., from this:
```text
List title 1
- Item 1
- Item 2
- Item 3
List title 2
- Item 1
- Item 2
- Item 3
```
To this:
```text
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
You can easily convert the text in between those two formats just by using
visual block mode to do something similar to paste(1) (see the
[appendix](#appendix)).
Here's a video demonstration.
<video controls="" autoplay="" name="media">
<source src="{{< get-resource-link "demo.webm">}}" alt="demo video" type="video/webm">
</video>
## Creating columns
Let's start with the vertical form, and put your cursor on the position marked
by the block (`▋`)
```text
List title 1
- Item 1
- Item 2
- Item 3
List title 2
- Item 1
- Item 2
▋ Item 3
```
Begin visual block selection mode with `<C-v>`. Select the first character at
each line with `3k`, then extend selection to the entire block using `$h`.
Your cursor should now be on the "2" with the entire "List title 2" and the
three list items below it selected:
```text
List title 1
- Item 1
- Item 2
- Item 3
List title ▋
- Item 1
- Item 2
- Item 3
```
Now hit `x` (or `d`) to remove the block and save it in one of the default
registers temporarily.
```text
List title 1
- Item 1
- Item 2
- Item 3
```
Now, we prepare the first list to be able to paste the second list that was just
deleted. Pad spaces at the end of each line of the first list. Spaces will be shown
as `_` throughout the example.
If you don't already have Vim/Neovim setup to highlight trailing spaces, you can
do so temporarily now by running `:match Underlined '\s\+$'`.
```text
List title 1_
- Item 1_____
- Item 2_____
- Item 3_____
```
Now we can paste the block we've deleted! Place your cursor on the trailing
space after "List title 1":
```text
List title 1▋
- Item 1_____
- Item 2_____
- Item 3_____
```
And hit `p`:
```text
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
_Voila!_ The two lists are now merged into two columns side by side.
You can easily adjust the spacing between the columns using visual block mode.
Place your cursor on the space in-between the two list titles:
```text
List title 1▋List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
Enter visual block mode and select the entire vertical column of spaces:
```text
List title 1▋List title 2
- Item 1 ▋- Item 1
- Item 2 ▋- Item 2
- Item 3 ▋- Item 3
```
Hit `A` to append text after each selection. Add a few spaces as you see fit,
and exit visual block mode (`ESC`).
```text
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
## Removing columns
Let's transform the text in reverse[^1]. We'll break these two columns up and have
them show up one following another vertically like what we've started with. This
might be needed when the first or second list becomes too long and you decide to
stop having them show up side by side.
[^1]: If you actually just want to reverse the process without any editing in
between, you should of course use a few undo commands ;-)
First, place your cursor at the beginning of the third item on the second list.
```text
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 ▋ Item 3
```
We'll use a similar process as before to select the second list with visual
block mode. Enter visual block mode with `<C-v>`, hit `3k`, then `$h`.
Now delete the text like before.
Next we'll have to create enough space under the first list for the second list
to be pasted. (Note the trailing spaces here are only shown for completeness.)
```text
List title 1____
- Item 1________
- Item 2________
- Item 3________
```
There should be four empty lines after a blank line following the first list.
Place your cursor on the start of the second blank line:
```text
List title 1____
- Item 1________
- Item 2________
- Item 3________
```
And hit `p`.
```text
List title 1____
- Item 1________
- Item 2________
- Item 3________
List title 2
- Item 1
- Item 2
- Item 3
```
And we're back to the original format.
You can easily remove the trailing spaces on the first list by running the
substitution command on a visual selection of the first list.
Use either visual mode or visual line mode to select the first paragraph, then
use `:'<,'>s/\s\+$//`.
```text
List title 1
- Item 1
- Item 2
- Item 3
List title 2
- Item 1
- Item 2
- Item 3
```
That's it!
Visual block mode is just one of the useful tools when formatting plain text and
making ascii art. I frequently use the replace mode ("write through") with `R`
to overwrite content without breaking up columns.
You can learn more about the visual block mode in Vim in the docs:
```vim
:h visual-block
```
## Appendix
Here's an example shell session to demonstrate how you can do the same thing
described in the article using the shell built-in `paste(1)`. Again, spaces are
represented as `_`.
```text
$ cat > l1.txt
List title 1_
- Item 1_____
- Item 2_____
- Item 3_____
^D
```
```text
$ cat > l2.txt
List title 2
- Item 1
- Item 2
- Item 3
^D
```
```text
$ paste -d ' ' l1.txt l2.txt
List title 1 List title 2
- Item 1 - Item 1
- Item 2 - Item 2
- Item 3 - Item 3
```
As for converting it back, I might opt for awk(1), another scripting language,
or just use Vim's visual block mode.

View File

@ -8,13 +8,13 @@
{{ partial "header.html" . }}
</header>
<main id="content">
{{ block "main" . }}{{ end }}
<div id="main">
{{ block "main" . }}{{ end }}
</div>
</main>
<section id="after-content">
{{ block "after" . }}{{ end }}
</section>
<!-- Don't use line breaks here, we want to hide this section if 'after' is empty. -->
<section id="after-content">{{- block "after" . }}{{ end }}</section>
<footer>
<hr>
{{ partial "footer.html" . }}
</footer>
</body>

View File

@ -10,7 +10,7 @@
<feed xmlns="http://www.w3.org/2005/Atom">
<title>hedy's blog</title>
<link href="{{ .RelPermalink }}"/>
<updated>{{ .Date.Format "2006-01-02" | safeHTML }}T12:00:00Z</updated>
<updated>{{ time.Now | time.Format "2006-01-02" | safeHTML }}T12:00:00Z</updated>
<id>{{ .RelPermalink }}</id>
<author>
<name>{{ $.Site.Author.name }}</name>

View File

@ -10,7 +10,7 @@
<feed xmlns="http://www.w3.org/2005/Atom">
<title>hedy's gemlog</title>
<link href="{{ .Site.Params.geminiRoot }}"/>
<updated>{{ .Date.Format "2006-01-02" | safeHTML }}T12:00:00Z</updated>
<updated>{{ time.Now | time.Format "2006-01-02" | safeHTML }}T12:00:00Z</updated>
<id>{{ .Site.Params.geminiRoot }}</id>
<author>
<name>{{ $.Site.Author.name }}</name>

View File

@ -1,3 +1,4 @@
<hr style="display: none;">
<p>
Copyright © {{ with .Site.Params.CopyrightYearStart }}{{ . }}-{{ end -}}
{{ now.Format "2006" }}

View File

@ -10,4 +10,6 @@
=> /feed.xml Atom feed
{{ range (where .Site.RegularPages "Section" "posts") }}
{{- if .OutputFormats.Get "gemtext" }}
=> {{replace (replace .RelPermalink "/gemini" "" 1) "/index.gmi" ".gmi" 1}} {{ .Date.Format "2006-01-02" }}: {{.Title | safeHTML}}{{ end }}{{- end }}
=> {{replace (replace .RelPermalink "/gemini" "" 1) "/index.gmi" ".gmi" 1}} {{ .Date.Format "2006-01-02" }} · {{.Title | safeHTML}}{{ end }}
{{ .Description }}
{{ end }}

View File

@ -1,10 +1,5 @@
{{ if .Params.footnote_heading -}}
{{ $references := `(<section class="footnotes" role="doc-endnotes">
{{ $footnotes := `(<div class="footnotes" role="doc-endnotes">
<hr>)` -}}
{{ $heading := .Params.footnote_heading -}}
{{ $referencesWithHeading := printf `<section class="footnotes" role="doc-endnotes" aria-labelledby="note-hd">
<h2 id="note-hd">%s</h2>` ($heading) -}}
{{ .Content | replaceRE $references $referencesWithHeading | safeHTML -}}
{{ else -}}
{{ .Content -}}
{{ end -}}
{{ $footnotesWithHeading := printf `<div class="footnotes" role="doc-endnotes">
<hr><p id="footnotes-heading">%s</p>` "Footnotes" -}}
{{ .Content | replaceRE $footnotes $footnotesWithHeading | safeHTML -}}

View File

@ -2,14 +2,15 @@
# {{ $.Title }}
Posted {{ .Date.Format "2006-01-02" }}
{{ $lastmod := .Lastmod -}}
{{ if lt .Date $lastmod -}}
Last updated {{ .Lastmod.Format "2006-01-02" }}{{ end }}
{{ $taxonomy := "tags" -}}
{{- with .Param $taxonomy -}}
{{- if gt (len .) 1 -}}
{{- $lastmod := .Lastmod }}
{{- if lt .Date $lastmod }}
Last updated {{ .Lastmod.Format "2006-01-02" }}
{{- end }}
{{- $taxonomy := "tags" }}
{{- with .Param $taxonomy }}
{{- if gt (len .) 1 }}
Tags:
{{- else if gt (len .) 0 -}}
{{- else if gt (len .) 0 }}
Tag:
{{- end -}}
@ -18,7 +19,17 @@ Tag:
{{- end }}
--
{{ trim (readFile (replace $.File.Path ".md" ".gmi")) "\n" | safeHTML }}
{{- /*
* https://discourse.gohugo.io/t/using-renderstring-to-expand-shortcodes/40994/7
* support for using shortcodes in gemtext whilst having content as raw text.
*/ -}}
{{- $content := printf "~~~\n%s~~~" (trim (readFile (replace $.File.Path ".md" ".gmi")) "\n" | safeHTML) | .Page.RenderString | htmlUnescape }}
{{- $lines := split $content "\n" }}
{{- range $i, $_ := $lines }}
{{- if and $i (ne $i (sub (len $lines) 1)) }}
{{ . }}
{{- end -}}
{{- end -}}
--
Questions/comments:
@ -26,5 +37,5 @@ Questions/comments:
=> mailto:~hedy/posts@lists.sr.ht Public gemlog mailing list (plain-text only)
=> mailto:{{ .Site.Author.email }} Or email me directly
=> .. Home
=> / Home
{{- end }}

View File

@ -4,7 +4,7 @@
<header id="post-header">
<h1 itemprop="name headline" class="p-name">{{ .Title }}</h1>
{{ with .Description -}}
<div class="post-description"><p><em>{{ . }}</em></p></div>
<div class="post-description"><p>{{ . }}</p></div>
{{- end }}
<div class="post-meta">
<p>Posted on

View File

@ -0,0 +1,2 @@
{{ $src := $.Page.Resources.GetMatch (.Get 0) -}}
{{ printf "/posts/assets/%s_%s" $.Page.Slug $src.Name -}}

View File

@ -0,0 +1 @@
{{ $src := $.Page.Resources.GetMatch (.Get 0) }}{{ $src.RelPermalink }}