Compare commits

..

1 commit

Author SHA1 Message Date
1f166971b2
first tests
fails with photoswipe...
2025-02-15 10:05:23 +01:00
35 changed files with 520 additions and 507 deletions
.gitignoreREADME.md
assets
config/_default
content
equipment
notebooks/google-pixel-tablet
radio-stuff/accessories
links
notes
firefox
hamradio-computer
posts
2020/3-hs-dual-hat-with-pistar-v4
2024/62-a-slim-dstar-gateway-on-a-raspberry-pi-2
2025
75-winlink-on-android-with-woad
76-airdrop-on-linux
77-robust-packet-radio-link500-woad
99-my-schools-power-supply
99-the-repair-of-the-blue-bypass-led-on-the-pa500
99-view-the-weather
gmid.conf
layouts

5
.gitignore vendored
View file

@ -1,12 +1,7 @@
.hugo_build.lock
# As for the go.{mod,sum} files, I want them nearly empty
# in the repo but don't track changes so I did this:
# git update-index --assume-unchanged go.mod
# git update-index --assume-unchanged go.sum
resources
public
go.mod
go.sum
man
*.bak
gmid.*

View file

@ -5,19 +5,6 @@ my personal website on `oe7drt.com`.
The domain name is actually my amateur radio callsign with the `.com` TLD.
### View via
- http
You won't reach my website on plain old http.
- https
https://oe7drt.com/
- Tor Hidden Service
http://5uxkejb6la7olhncaotybxrscmdlbxwy64ucuyrum4tsgfuoxbyav2qd.onion/
- Gopher
gopher://oe7drt.com/
- Gemini
gemini://oe7drt.com/
### Build tools
I write content and code with Neovim or VS Code. Hugo puts it then

View file

@ -0,0 +1,159 @@
/*
Put this file in /static/css/hugo-easy-gallery.css
Documentation and licence at https://github.com/liwenyip/hugo-easy-gallery/
*/
/*
Grid Layout Styles
*/
.gallery {
overflow: hidden;
margin: 10px;
max-width: 768px;
}
.gallery .box {
float: left;
position: relative;
/* Default: 1 tile wide */
width: 100%;
padding-bottom: 100%;
}
@media only screen and (min-width : 365px) {
/* Tablet view: 2 tiles */
.gallery .box {
width: 50%;
padding-bottom: 50%;
}
}
@media only screen and (min-width : 480px) {
/* Small desktop / ipad view: 3 tiles */
.gallery .box {
width: 33.3%;
padding-bottom: 33.3%; /* */
}
}
@media only screen and (min-width : 9999px) {
/* Medium desktop: 4 tiles */
.box {
width: 25%;
padding-bottom: 25%;
}
}
/*
Transition styles
*/
.gallery.hover-transition figure,
.gallery.hover-effect-zoom .img,
.gallery:not(.caption-effect-appear) figcaption,
.fancy-figure:not(.caption-effect-appear) figcaption {
-webkit-transition: all 0.3s ease-in-out;
-moz-transition: all 0.3s ease-in-out;
-o-transition: all 0.3s ease-in-out;
transition: all 0.3s ease-in-out;
}
/*
figure styles
*/
figure {
position:relative; /* purely to allow absolution positioning of figcaption */
overflow: hidden;
}
.gallery figure {
position: absolute;
left: 5px;
right: 5px;
top: 5px;
bottom: 5px;
}
.gallery.hover-effect-grow figure:hover {
transform: scale(1.05);
}
.gallery.hover-effect-shrink figure:hover {
transform: scale(0.95);
}
.gallery.hover-effect-slidedown figure:hover {
transform: translateY(5px);
}
.gallery.hover-effect-slideup figure:hover {
transform: translateY(-5px);
}
/*
img / a styles
*/
.gallery .img {
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
background-size: cover;
background-position: 50% 50%;
background-repeat: no-repeat;
}
.gallery.hover-effect-zoom figure:hover .img {
transform: scale(1.05);
}
.gallery img {
display: none; /* only show the img if not inside a gallery */
}
figure a {
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
}
/*
figcaption styles
*/
.gallery figcaption,
.fancy-figure figcaption {
position: absolute;
bottom: 0;
left: 0;
right: 0;
background: #000;
color: #FFF;
text-align: center;
font-size: 75%; /* change this if you want bigger text */
background: rgba(0, 0, 0, 0.5);
opacity: 1;
cursor: pointer;
}
.gallery.caption-position-none figcaption,
.fancy-figure.caption-position-none figcaption {
display: none;
}
.gallery.caption-position-center figcaption,
.fancy-figure.caption-position-center figcaption {
top: 0;
padding: 40% 5px;
}
.gallery.caption-position-bottom figcaption,
.fancy-figure.caption-position-bottom figcaption {
padding: 5px;
}
.gallery.caption-effect-fade figure:not(:hover) figcaption,
.gallery.caption-effect-appear figure:not(:hover) figcaption,
.fancy-figure.caption-effect-fade figure:not(:hover) figcaption,
.fancy-figure.caption-effect-appear figure:not(:hover) figcaption {
background: rgba(0, 0, 0, 0);
opacity: 0;
}
.gallery.caption-effect-slide.caption-position-bottom figure:not(:hover) figcaption,
.fancy-figure.caption-effect-slide.caption-position-bottom figure:not(:hover) figcaption {
margin-bottom: -100%;
}
.gallery.caption-effect-slide.caption-position-center figure:not(:hover) figcaption,
.fancy-figure.caption-effect-slide.caption-position-center figure:not(:hover) figcaption {
top: 100%;
}
figcaption p {
margin: auto; /* override style in theme */
}

View file

@ -0,0 +1,80 @@
/*
Put this file in /static/js/load-photoswipe.js
Documentation and licence at https://github.com/liwenyip/hugo-easy-gallery/
*/
/* Show an alert if this js file has been loaded twice */
if (window.loadphotoswipejs) {
window.alert("You've loaded load-photoswipe.js twice. See https://github.com/liwenyip/hugo-easy-gallery/issues/6")
}
var loadphotoswipejs = 1
/* TODO: Make the share function work */
$( document ).ready(function() {
/*
Initialise Photoswipe
*/
var items = []; // array of slide objects that will be passed to PhotoSwipe()
// for every figure element on the page:
$('figure').each( function() {
if ($(this).attr('class') == 'no-photoswipe') return true; // ignore any figures where class="no-photoswipe"
// get properties from child a/img/figcaption elements,
var $figure = $(this),
$a = $figure.find('a'),
$img = $figure.find('img'),
$src = $a.attr('href'),
$title = $img.attr('alt'),
$msrc = $img.attr('src');
// if data-size on <a> tag is set, read it and create an item
if ($a.data('size')) {
var $size = $a.data('size').split('x');
var item = {
src : $src,
w : $size[0],
h : $size[1],
title : $title,
msrc : $msrc
};
console.log("Using pre-defined dimensions for " + $src);
// if not, set temp default size then load the image to check actual size
} else {
var item = {
src : $src,
w : 800, // temp default size
h : 600, // temp default size
title : $title,
msrc : $msrc
};
console.log("Using default dimensions for " + $src);
// load the image to check its dimensions
// update the item as soon as w and h are known (check every 30ms)
var img = new Image();
img.src = $src;
var wait = setInterval(function() {
var w = img.naturalWidth,
h = img.naturalHeight;
if (w && h) {
clearInterval(wait);
item.w = w;
item.h = h;
console.log("Got actual dimensions for " + img.src);
}
}, 30);
}
// Save the index of this image then add it to the array
var index = items.length;
items.push(item);
// Event handler for click on a figure
$figure.on('click', function(event) {
event.preventDefault(); // prevent the normal behaviour i.e. load the <a> hyperlink
// Get the PSWP element and initialise it with the desired options
var $pswp = $('.pswp')[0];
var options = {
index: index,
bgOpacity: 0.8,
showHideOpacity: true
}
new PhotoSwipe($pswp, PhotoSwipeUI_Default, items, options).init();
});
});
});

View file

@ -10,11 +10,11 @@ theme = [ "congo", "plausible-hugo" ]
# theme = [ "plausible-hugo", "congo" ]
# congo (default), avocado, cherry, fire, ocean, sapphire and slate.
# colorScheme = "congo"
colorScheme = "congo"
# colorScheme = "avocado"
# colorScheme = "cherry"
# colorScheme = "fire"
colorScheme = "ocean"
# colorScheme = "ocean"
# colorScheme = "sapphire"
# colorScheme = "slate"
# defaultAppearance = "dark" # valid options: light or dark

View file

@ -1,28 +0,0 @@
---
title: Google Pixel Tablet (2023)
summary:
date: 2025-02-21
# coverCaption:
# lastmod:
showBreadcrumbs: true
showReadingTime: false
showWordCount: false
---
Initially I wanted a cheap tablet to be used exclusively for Amateur Radio,
but the first tablet that I bought was a faulty device (a DOGEE T36) which
randomly rebootet itself, especially when I tried to access the settings-app.
Hell, I couldn't even change the device name.
After one day of frustration I sent the device back and ordered the
[Pixel Tablet]. I quickly put [GrapheneOS] onto it and installed all needed
applications for my particular use case.
Until now (end of February) I'm very happy with it (both the hardware and the
GrapheneOS operating system).
[GrapheneOS]: https://grapheneos.org/
[Pixel Tablet]: https://store.google.com/de/product/pixel_tablet
## Main usage

Binary file not shown.

View file

@ -4,7 +4,7 @@ summary: An absolute must-have if you own a QRP radio like the TX-500.
aliases:
- /equipment/accessories/diy599-pa500/
date: 2023-05-01T11:43:21+02:00
lastmod: 2025-03-09T20:49:08+0000
lastmod: 2024-09-28T15:50:12+0000
showBreadcrumbs: true
showReadingTime: false
@ -13,36 +13,5 @@ showWordCount: false
This tuner/amplifier can also be used with other QRP radios as the TX-500.
## Blue light repair
I am subscribed to a few mailing lists and recently I came across this one here:
[PA500 blue bypass light][1] - as the title suggests, it is about the blue bypass light.
[1]: https://groups.io/g/diy599/topic/pa500_blue_bypass_light/110888256
I am pretty sure the blue light lit randomly, I think I've seen it when I changed the
PA500 operational mode back to full automatic.
Anyway, the blue light was off for a while now and I wasn't sure what I should do with it,
just ignore it or send the PA500 back for repair - none of that was a satisfying option to
me as both would nag on my mind :D
When I found the article mentioned above I knew I wasn't the only one with this problem and
I joined the conversation and asked about the blue light when Oliver suggested to send me one.
Now what?
{{< figure src="pa500-opened.jpg" caption="The PA500 -- opened; showing the location of the LEDs" >}}
Right! I changed the blue LED last saturday (today is Sunday, 3 March) and I had the chance to
test it today -- it is perfectly fine!
{{< figure src="pa500-leds.jpg" caption="Soldering the LED with the LEDS attached to the aluminium housing so it will get the correct alignment to fit into the hole later" >}}
I figured that out after I soldered the LED -- luckily I only had to push the LED a bit down to get it
into the hole.
Although I used a 1mm tip I thought I might got the board too hot already (350°C).
{{< figure src="pa500-working.jpg" caption="Finally the LED lights again!" >}}
I like it very much, I don't use the automatic PTT control via VOX -- I
connect a cable to the computer or Digirig.

Binary file not shown.

View file

@ -6,7 +6,7 @@ summary: |
coverCaption: My selfmade common mode choke placed into a neat plastic case
with BNC connectors.
date: 2023-10-26T13:36:26+02:00
lastmod: 2025-03-09T11:08:33+0000
lastmod: 2024-09-28T23:48:06+0000
showBreadcrumbs: true
showReadingTime: false
@ -16,12 +16,13 @@ showWordCount: false
So this is basically a 140-43 toroid with 9 turns of RG174 connected to
BNC connectors.
It works very well and I have made two measurements:
It works very well and I have made two measurements recently.
{{< figure src="logmag_through.png" caption="The maximum loss is on 10m around 0.2dB" >}}
{{< figure src="logmag_outer.png" caption="It attenuates common mode current with more than 20dB" >}}
Another picture with open case:
I find this okay for now but I still wonder if this can be made any better
(maybe 30dB attenuation?). Would I benefit from even more attenuation?
{{< figure src="choke-inside.jpg" caption="A look inside the \"plastic\"" >}}
I will probably find out on another day.

View file

@ -38,6 +38,10 @@ and PDF files of the links too.
[opengist](https://gist.oe7drt.net/)
: Selfhosted version of Github gists where I save some random snippets.
[LibreTranslate](https://translate.oe7drt.net/)
: I was testing Mastodon again (this time on my local server at home) in a virtual machine.
Within that I created another user that runs an instance of LibreTranslate.
[Mastodon](https://social.oe7drt.net/)
: I do some testing on this private instance every now and then and if you need an instance
to test out a few things feel free to create users over there. It is currently subscribed

View file

@ -1,132 +0,0 @@
---
title: Firefox
date: 2025-02-20T21:30:37+0100
# lastmod:
tags:
- firefox
#showDate: false
showReadingTime: false
showWordCount: false
showPagination: false
#showAuthor: false
showBreadcrumbs: true
feed_exclude: true
# site_exclude: true
draft: true
---
## Opening links
(1) In a new tab, type or paste about:config in the address bar and press Enter/Return. Click the button promising to be careful or accepting the risk.
(2) In the search box above the list, type or paste neww and pause while the list is filtered
(3) Review/Adjust the preferences as follows:
(A) browser.link.open_newwindow - for links in Firefox tabs
This is the one that has a checkbox on the Preferences page:
3 = divert new window to a new tab (default)
2 = allow link to open a new window
1 = force new window into same tab
(B) browser.link.open_newwindow.restriction - for links in Firefox tabs
By default, if a page sets width, height, or toolbars for a popup, Firefox will let it be a separate window. To force those into a tab as well, you can change this preference to 0:
0 = apply the setting under (A) to ALL new windows (even script windows with features)
2 = apply the setting under (A) to normal windows, but NOT to script windows with features (default)
1 = override the setting under (A) and always use new windows
(C) browser.link.open_newwindow.override.external - for links in other programs
-1 = apply the setting under (A) to external links (default)
3 = open external links in a new tab in the last active window
2 = open external links in a new window <= Try this one
1 = open external links in the last active tab replacing the current page
To return to normal if things go haywire, right-click each "modified" preference and choose Reset.
## Video (description) by Mental Outlaw
Maximize Your Browsers Privacy and Security with ZERO ADDONS!!!
Mental Outlaw
In this video I show you how to maximize your Browsers Privacy and Security with no browser extensions by going into about:config and changing the settings for better privacy and security. The Settings I use in this video are as follows
****\*****about:config settings start****\*****
Disable WebRTC:
WebRTC can give up your real IP even when using VPN or Tor. Type in
media.peerconnection.enabled = false
Enable fingerprint resistance: With this alone we pretty much negate the need for canvas defender, or any other fingerprint blocking addon.
privacy.resistfingerprinting = true
3DES Cypher:
3DES has known security flaws
security.ssl3.rsa_des_ede3_sha = false
Require Safe Negotiation: Optimize SSL
security.ssl.require_safe_negotiation = true
Disable TLS 1.0, 1.1
security.tls.version.min = 3
enables TLS 1.3
tls.version.max = 4
Disable 0 round trip time to better secure your forward secrecy
security.tls.enable_0rtt_data = false
Disable Automatic Formfill
browser.formfil.enable = false
Disable disk caching
browser.cache.disk.enable = false
browser.cache.disk_cache_ssl = false
browser.cache.memory.enable = false
browser.cache.offline.enable = false
browser.cache.insecure.enable = false
Disable geolocation services
geo.enabled = false
Disable plugin scanning.
Can improve functionality, as some sites scan for adblockers and script blockers. Should be used even on non-hardened firefox.
plugin.scan.plid.all = false
Disable ALL telemetery
browser.newtabpage.activity-stream.feeds.telemetry browser.newtabpage.activity-stream.telemetry = false
browser.pingcentre.telemetry = false
devtools.onboarding.telemetry-logged = false
media.wmf.deblacklisting-for-telemetry-in-gpu-process = false
toolkit.telemetry.archive.enabled = false
toolkit.telemetry.bhrping.enabled = false
toolkit.telemetry.firstshutdownping.enabled = false
toolkit.telemetry.hybridcontent.enabled = false
toolkit.telemetry.newprofileping.enabled = false
toolkit.telemetry.unified = false
toolkit.telemetry.updateping.enabled = false
toolkit.telemetry.shutdownpingsender.enabled = false
Disable WebGL
Allows direct access to GPU.
webgl.disabled = true
Enable first-party isolation
Prevents browsers from making requests outside of the primary domain of the website. Prevents supercookies. may cause websites that rely on 3rd party scripts and libraries to break, however those are generally only used for tracking so fuck em anyway.
privacy.firstparty.isolate = true
Disable TLS false start
security.ssl.enable_false_start = false
****\*****about:config settings end****\*****

View file

@ -13,13 +13,6 @@ tags:
- archlinux
- systemd
- beelink
- WoAD
- radiomail
- VARA HF
- VARA FM
- Packet Radio
- Winlink
- wine
#showDate: false
showReadingTime: false
@ -82,17 +75,6 @@ to reboot without su
/etc/polkit-1/rules.d/49-nopasswd_global.rules
```
/* Allow members of the wheel group to execute any actions
* without password authentication, similar to "sudo NOPASSWD:"
*/
polkit.addRule(function(action, subject) {
if (subject.isInGroup("wheel")) {
return polkit.Result.YES;
}
});
```
### passwordless ssh login
ssh-add -L > .ssh/authorized_keys
@ -115,8 +97,6 @@ can also be done on most installation media that use grub by hitting
### Wine
#### Default (Arch)
Windows tools will require wine, so we install this right now
paru -S wine
@ -128,9 +108,6 @@ paru -S lib32-gnutls
export WINEARCH=win32
export WINEPREFIX=/home/dominic/.wine-winlink
you can also include these two lines in a .bash_profile or similar.
I use this sometimes in my `~/.zshrc.local` as i include this already.
since we exported WINEPREFIX we can omit the use of it in THIS SESSION
(this terminal window). if you use another you have to export the variable
again or prefix any command with
@ -145,18 +122,14 @@ winetricks -q allfonts
adding some .NET frameworks we will mostly use/need
```
winetricks -q dotnet35sp1
winetricks vb6run
winetricks vcrun2015
```
optional if errors
```
winetricks -q dotnet40
winetricks -q dotnet46
```
registering notepad.exe as default application for logfiles
@ -164,18 +137,6 @@ create a backup of the wine installation
tar -cJf wine-backup\_$(date +%Y-%m-%d-%H-%M-%S)\_initial-setup.tar.xz .wine-winlink
#### Debian
```
sudo dpkg --add-architecture i386
sudo apt update
sudo apt install wine wine32 fonts-wine
```
```
sudo apt install gcc-multilib g++-multilib
```
### VARA tools
vara hf, vara fm

View file

@ -4,7 +4,6 @@ aliases:
- /posts/2020-01-23-hs-dual-hat-with-pistar-v4
- /blog/amateur-radio/2020-01-23-hs-dual-hat-with-pistar-v4/
- /amateur-radio/2020-01-23-hs-dual-hat-with-pistar-v4/
- /posts/2022/26-raspberry-pi-4-64bit-dual-hat
summary: >
This is a MMDVM_HS_Dual_Hat hotspot in duplex mode with DMRGateway
and an actual Pi-Star image.
@ -17,7 +16,7 @@ tags:
- hotspot
- mmdvm
date: 2020-01-23T15:03:35+01:00
lastmod: 2025-04-05T21:30:31+0000
lastmod: 2024-09-28T23:48:06+0000
---
{{< alert circle-info >}}

View file

@ -3,7 +3,7 @@ title: A slim D-STAR gateway on a Raspberry Pi 2
summary: I wrote down the installation of a forked DStarGateway with a slim
dashboard based on Javascript on a Raspberry Pi 2 -- using Archlinux.
date: 2024-02-03T06:33:16+0100
lastmod: 2025-03-22T00:08:11+0000
lastmod: 2024-09-28T23:48:07+0000
categories:
- amateur-radio
tags:
@ -672,9 +672,9 @@ on the hotspot and all HTTPS traffic is handled by a reverse proxy in my network
another complexity that I don't need.
I have also uploaded my fork of it (including the modifications below) on my git repo:
<https://repo.oe7drt.net/dominic/dsgwdashboard/src/branch/only_http>
<https://gits.oe7drt.net/dominic/dsgwdashboard/src/branch/only_http>
~~You can see the dashboard in action at: <https://hotspot.oe7drt.net/>~~
You can see the dashboard in action at: <https://hotspot.oe7drt.net/>
{{< /alert >}}
But: I will not install this as it is in his instructions, because I don't like

Binary file not shown.

Binary file not shown.

Binary file not shown.

View file

@ -35,6 +35,8 @@ I assume the app is all set up with basic information like CALLSIGN, Grid, etc.
## Packet connection
{{< gallery dir="img1" />}}
I love simple and small configurations (mostly) and this one is really small.
When I'm out hiking I usually have an <abbr title="handheld transceiver">HT</abbr>
with me -- usually an Icom ID-52. Together with a Mobilinkd

View file

@ -3,22 +3,35 @@ title: AirDrop on Linux?
summary: >
This is my method of using something similar as AirDrop on my Linux
and Android devices.
<small>The thumbnail was created with Google AI (Imagen 3).</small>
date: 2025-03-09T22:08:38+0100
lastmod: 2025-03-16T08:46:21+0000
date: 2025-01-19T19:39:36+0100
# lastmod:
categories:
- amateur-radio
- computerstuff
tags:
- android
- linux
- windows
- ios
- draft_post
# showBreadcrumbs: true
# showDate: false
# showReadingTime: false
# showWordCount: false
# showPagination: false
# feed_exclude: true
# site_exclude: true
# some help
#
# highlighting with highlights
#
# use table, as inline creates a padding around
# and it pushes the text more to the right side (end of screen)
#
# ~~~html {linenos=table,hl_lines="3-6"}
# ~~~html {linenos=inline,hl_lines="1,3-6"}
draft: true
---
It works amazing! I push big folders of music to my phone or just share some pictures --
no problem for [Localsend](https://localsend.org/).
I have it on an old iPhone, on my daily driver Android phone and on my laptops.
Bring the devices into the same network and start sharing. Using favorites with PIN codes
makes it easy to auto-deploy files and folders on my often used devices.
https://localsend.org/ is the key for this.
and it works absolutely fine

View file

@ -1,44 +0,0 @@
---
title: Robust Packet Radio with the LINK500 using WoAD and Winlink Express
summary: >
This looks like a solid setup for Winlink-style field operation outside
in the mountains with one major disadvantage (CAT control)
date: 2025-03-09T22:08:56+0100
# lastmod:
categories:
- amateur-radio
tags:
- Android
- APRS
- GPS
- Mobilinkd
- Packet Radio
- Portable
- Radiomail
- Signalink
- tx500
- Winlink
- Winlink Express
- draft_post
# showBreadcrumbs: true
# showDate: false
# showReadingTime: false
# showWordCount: false
# showPagination: false
# feed_exclude: true
# site_exclude: true
# some help
#
# highlighting with highlights
#
# use table, as inline creates a padding around
# and it pushes the text more to the right side (end of screen)
#
# ~~~html {linenos=table,hl_lines="3-6"}
# ~~~html {linenos=inline,hl_lines="1,3-6"}
draft: true
---

View file

@ -1,38 +0,0 @@
---
title: My schools power supply
summary: >
A few impressions of the "quick" repair of my old power supply, that I
put together in school back in 2000-something.
date: 2025-03-16T10:20:52+01:00
# lastmod:
categories:
- amateur-radio
tags:
- diy
- repair
- soldering
- draft_post
# showBreadcrumbs: true
# showDate: false
# showReadingTime: false
# showWordCount: false
# showPagination: false
# feed_exclude: true
# site_exclude: true
# some help
#
# highlighting with highlights
#
# use table, as inline creates a padding around
# and it pushes the text more to the right side (end of screen)
#
# ~~~html {linenos=table,hl_lines="3-6"}
# ~~~html {linenos=inline,hl_lines="1,3-6"}
draft: true
---
I've been using my partly broken power supply now

View file

@ -1,37 +0,0 @@
---
title: The repair of the blue bypass LED on the PA500
summary: >
I'd be more interested in the cause of this faulty LED, as I know two cases of
this "broken" lED (that worked before).
date: 2025-03-16T10:25:50+01:00
# lastmod:
categories:
- amateur-radio
tags:
- diy
- repair
- soldering
- pa500
- draft_post
# showBreadcrumbs: true
# showDate: false
# showReadingTime: false
# showWordCount: false
# showPagination: false
# feed_exclude: true
# site_exclude: true
# some help
#
# highlighting with highlights
#
# use table, as inline creates a padding around
# and it pushes the text more to the right side (end of screen)
#
# ~~~html {linenos=table,hl_lines="3-6"}
# ~~~html {linenos=inline,hl_lines="1,3-6"}
draft: true
---

View file

@ -1,40 +0,0 @@
---
title: View the weather
summary:
date: 2025-03-16T10:41:04+01:00
# lastmod:
categories:
- amateur-radio
tags:
- command line
- diy
- ffmpeg
- linux
- scripting
- selfhost
- server
- weewx
- wx
- draft_post
# showBreadcrumbs: true
# showDate: false
# showReadingTime: false
# showWordCount: false
# showPagination: false
# feed_exclude: true
# site_exclude: true
# some help
#
# highlighting with highlights
#
# use table, as inline creates a padding around
# and it pushes the text more to the right side (end of screen)
#
# ~~~html {linenos=table,hl_lines="3-6"}
# ~~~html {linenos=inline,hl_lines="1,3-6"}
draft: true
---

View file

@ -1,21 +0,0 @@
# create certs for localhost
# openssl req -x509 -newkey rsa:4096 -nodes -keyout gmid.key \
# -out gmid.pem -days 365 -subj "/CN=localhost"
protocols "tlsv1.3"
types {
# include "/usr/share/misc/mime.types"
include "/usr/share/doc/gmid/mime.types"
}
server "localhost" {
listen on * port 1965
cert "/home/dominic/sites/oe7drt-website/gmid.pem"
key "/home/dominic/sites/oe7drt-website/gmid.key"
# root "/srv/sites/oe7drt-gemini"
root "/home/dominic/sites/oe7drt-website/public"
lang "en"
}

View file

@ -24,7 +24,8 @@ Contact
English, German
<https://oe7drt.com/about/#contact>
Built with
Built on/with
* Lenovo X1 Carbon (Fedora/Arch)
* Hugo v{{ hugo.Version }} ({{ hugo.GoVersion }}) <https://gohugo.io/>
* AstroNvim <https://astronvim.com/>
* Gimp <https://www.gimp.org/>
@ -32,6 +33,13 @@ Built with
* Rsync <https://rsync.samba.org/>
* FFmpeg <https://ffmpeg.org/>
Sources:
<https://repo.oe7drt.net/dominic/oe7drt-website>
Runs on
* KVM Rootserver
* AMD EPYC 9634 84-Core Processor (4 Cores)
* 8 GB ECC DDR4 RAM
* 2,5 Gbit/s redundant network connection
* Arch Linux
(was before OpenBSD 7.5, 7.4, 7.3, 7.2 and Rocky Linux 9 (and 8))
* Apache 2
* mod_md

View file

@ -36,40 +36,13 @@
</p>
</div>
</div>
{{ with resources.Get "js/lightbox.js" }} {{ if hugo.IsDevelopment }} {{ with .
| js.Build }}
<script
defer
type="text/javascript"
src="{{ .RelPermalink }}"
data-copy="Copy"
data-copied="Copied"
src="https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.1/photoswipe.min.js"
integrity="sha256-UplRCs9v4KXVJvVY+p+RSo5Q4ilAUXh7kpjyIP5odyc="
crossorigin="anonymous"
></script>
{{ end }} {{ else }} {{ $opts := (dict "minify" true "targetPath"
"js/lightbox.js") }} {{ with . | js.Build $opts | fingerprint }}
<script
defer
type="text/javascript"
src="{{ .RelPermalink }}"
data-copy="Copy"
data-copied="Copied"
integrity="{{ .Data.Integrity }}"
src="https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.1/photoswipe-ui-default.min.js"
integrity="sha256-PWHOlUzc96pMc8ThwRIXPn8yH4NOLu42RQ0b9SpnpFk="
crossorigin="anonymous"
></script>
{{ end }} {{ end }} {{ end }} {{ with resources.Get "css/lightbox.css" }} {{ if
hugo.IsDevelopment }} {{ with . }}
<link
type="text/css"
rel="stylesheet"
media="screen,print"
href="{{ .RelPermalink }}"
/>
{{ end }} {{ else }} {{ with . | fingerprint }}
<link
type="text/css"
rel="stylesheet"
media="screen,print"
href="{{ .RelPermalink }}"
integrity="{{ .Data.Integrity }}"
/>
{{ end }} {{ end }} {{ end }}

View file

@ -2,6 +2,48 @@
"plausible_head.html" . }} {{- end }}
<meta name="fediverse:creator" content="@oe7drt@mastodon.radio" />
<script
src="https://code.jquery.com/jquery-1.12.4.min.js"
integrity="sha256-ZosEbRLbNQzLpnKIkEdrPv7lOy9C27hHQ+Xp8a4MxAQ="
crossorigin="anonymous"
></script>
{{ with resources.Get "js/load-photoswipe.js" }} {{ if hugo.IsDevelopment }} {{
with . | js.Build }}
<script
defer
type="text/javascript"
src="{{ .RelPermalink }}"
data-copy="Copy"
data-copied="Copied"
></script>
{{ end }} {{ else }} {{ $opts := (dict "minify" true "targetPath"
"js/load-photoswipe.js") }} {{ with . | js.Build $opts | fingerprint }}
<script
defer
type="text/javascript"
src="{{ .RelPermalink }}"
data-copy="Copy"
data-copied="Copied"
integrity="{{ .Data.Integrity }}"
></script>
{{ end }} {{ end }} {{ end }} {{ with resources.Get "css/hugo-easy-gallery.css"
}} {{ if hugo.IsDevelopment }} {{ with . }}
<link
type="text/css"
rel="stylesheet"
media="screen,print"
href="{{ .RelPermalink }}"
/>
{{ end }} {{ else }} {{ with . | fingerprint }}
<link
type="text/css"
rel="stylesheet"
media="screen,print"
href="{{ .RelPermalink }}"
integrity="{{ .Data.Integrity }}"
/>
{{ end }} {{ end }} {{ end }}
<meta
http-equiv="onion-location"
content="http://5uxkejb6la7olhncaotybxrscmdlbxwy64ucuyrum4tsgfuoxbyav2qd.onion"

View file

@ -0,0 +1,26 @@
<!--
Put this file in /layouts/shortcodes/figure.html
NB this overrides Hugo's built-in "figure" shortcode but is backwards compatible
Documentation and licence at https://github.com/liwenyip/hugo-easy-gallery/
-->
<!-- use either src or link-thumb for thumbnail image -->
{{- $thumb := .Get "src" | default (printf "%s." (.Get "thumb") | replace (.Get "link") ".") }}
<div class="box{{ with .Get "caption-position" }} fancy-figure caption-position-{{.}}{{end}}{{ with .Get "caption-effect" }} caption-effect-{{.}}{{end}}" {{ with .Get "width" }}style="max-width:{{.}}"{{end}}>
<figure {{ with .Get "class" }}class="{{.}}"{{ end }} itemprop="associatedMedia" itemscope itemtype="http://schema.org/ImageObject">
<div class="img"{{ if .Parent }} style="background-image: url('{{ $thumb | relURL }}');"{{ end }}{{ with .Get "size" }} data-size="{{.}}"{{ end }}>
<img itemprop="thumbnail" src="{{ $thumb | relURL }}" {{ with .Get "alt" | default (.Get "caption") }}alt="{{.}}"{{ end }}/><!-- <img> hidden if in .gallery -->
</div>
{{ with .Get "link" | default (.Get "src") }}<a href="{{ . | relURL }}" itemprop="contentUrl"></a>{{ end }}
{{- if or (or (.Get "title") (.Get "caption")) (.Get "attr")}}
<figcaption>
{{- with .Get "title" }}<h4>{{.}}</h4>{{ end }}
{{- if or (.Get "caption") (.Get "attr")}}
<p>
{{- .Get "caption" -}}
{{- with .Get "attrlink"}}<a href="{{.}}">{{ .Get "attr" }}</a>{{ else }}{{ .Get "attr"}}{{ end -}}
</p>
{{- end }}
</figcaption>
{{- end }}
</figure>
</div>

View file

@ -0,0 +1,41 @@
<!--
Put this file in /layouts/shortcodes/gallery.html
Documentation and licence at https://github.com/liwenyip/hugo-easy-gallery/
-->
<!-- count how many times we've called this shortcode; load the css if it's the first time -->
{{- if not ($.Page.Scratch.Get "figurecount") }}<link rel="stylesheet" href={{ "css/hugo-easy-gallery.css" | relURL }} />{{ end }}
{{- $.Page.Scratch.Add "figurecount" 1 }}
{{ $baseURL := .Site.BaseURL }}
<div class="gallery caption-position-{{ with .Get "caption-position" | default "bottom" }}{{.}}{{end}} caption-effect-{{ with .Get "caption-effect" | default "slide" }}{{.}}{{end}} hover-effect-{{ with .Get "hover-effect" | default "zoom" }}{{.}}{{end}} {{ if ne (.Get "hover-transition") "none" }}hover-transition{{end}}" itemscope itemtype="http://schema.org/ImageGallery">
{{- with (.Get "dir") -}}
<!-- If a directory was specified, generate figures for all of the images in the directory -->
{{- $files := readDir (path.Join "content/" (path.Dir $.Page.File.Path) "/" .) }}
{{- range $files -}}
<!-- skip files that aren't images, or that include the thumb suffix in their name -->
{{- $thumbext := $.Get "thumb" | default "-thumb" }}
{{- $isthumb := .Name | findRE ($thumbext | printf "%s\\.") }}<!-- is the current file a thumbnail image? -->
{{- $isimg := lower .Name | findRE "\\.(gif|jpg|jpeg|tiff|png|bmp|webp|avif|jxl)" }}<!-- is the current file an image? -->
{{- if and $isimg (not $isthumb) }}
{{- $caption := .Name | replaceRE "\\..*" "" | humanize }}<!-- humanized filename without extension -->
{{- $linkURL := print $baseURL (path.Dir $.Page.File.Path) "/" ($.Get "dir") "/" .Name | absURL }}<!-- absolute URL to hi-res image -->
{{- $thumb := .Name | replaceRE "(\\.)" ($thumbext | printf "%s.") }}<!-- filename of thumbnail image -->
{{- $thumbexists := where $files "Name" $thumb }}<!-- does a thumbnail image exist? -->
{{- $thumbURL := print $baseURL (path.Dir $.Page.File.Path) "/" ($.Get "dir") "/" $thumb | absURL }}<!-- absolute URL to thumbnail image -->
<div class="box">
<figure itemprop="associatedMedia" itemscope itemtype="http://schema.org/ImageObject">
<div class="img" style="background-image: url('{{ if $thumbexists }}{{ $thumbURL }}{{ else }}{{ $linkURL }}{{ end }}');" >
<img itemprop="thumbnail" src="{{ if $thumbexists }}{{ $thumbURL }}{{ else }}{{ $linkURL }}{{ end }}" alt="{{ $caption }}" /><!-- <img> hidden if in .gallery -->
</div>
<figcaption>
<p>{{ $caption }}</p>
</figcaption>
<a href="{{ $linkURL }}" itemprop="contentUrl"></a><!-- put <a> last so it is stacked on top -->
</figure>
</div>
{{- end }}
{{- end }}
{{- else -}}
<!-- If no directory was specified, include any figure shortcodes called within the gallery -->
{{ .Inner }}
{{- end }}
</div>

View file

@ -0,0 +1,24 @@
<style>
.image-gallery {overflow: auto; margin-left: -1%!important;}
.image-gallery li {float: left; display: block; margin: 0 0 1% 1%; width: 19%;}
.image-gallery li a {text-align: center; text-decoration: none!important; color: #777;}
.image-gallery li a span {display: block; text-overflow: ellipsis; overflow: hidden; white-space: nowrap; padding: 3px 0;}
.image-gallery li a img {width: 100%; display: block;}
</style>
<!-- TODO: remove the /static part 4 lines below because I want to include them from the actual directory -->
{{ $dir := string (.Get "gallery_dir") }}
<ul class="image-gallery">
{{ range (readDir (print "/static" $dir)) }}
{{- $image := resources.Get (printf "%s/%s" $dir .Name) -}}
{{- $imageurl := printf "%s/%s" $dir .Name -}}
{{- $imagetitle := index (split .Name ".") 0 -}}
<li>
<a href="{{ ($image.Fit "1600x1600 q50").Permalink }}" title="{{ $imagetitle }}" class="lightbox-image">
<img src="{{ ($image.Fill "300x300 q50").Permalink }}" alt="{{ $imagetitle }}" title="{{ $imagetitle }}">
<span>{{ $imagetitle }}</span>
</a>
</li>
{{ end }}
</ul>

View file

@ -0,0 +1,75 @@
<!--
Put this file in /layouts/shortcodes/load-photoswipe.html
Documentation and licence at https://github.com/liwenyip/hugo-easy-gallery/
-->
<!-- prevent this shortcode from being loaded more than once per page -->
{{ if not ($.Page.Scratch.Get "photoswipeloaded") }}
{{ $.Page.Scratch.Set "photoswipeloaded" 1 }}
<!--
*** jQuery must be loaded before load-photoswipe.js ***
- If your template already loads jQuery in the header then you don't need to load it again here.
- If your template already loads jQuery in the footer, then you could load load-photoswipe.js from the footer instead
-->
<!-- these files are loaded in the theme footer
<script src="https://code.jquery.com/jquery-1.12.4.min.js" integrity="sha256-ZosEbRLbNQzLpnKIkEdrPv7lOy9C27hHQ+Xp8a4MxAQ=" crossorigin="anonymous"></script>
<script src="/js/load-photoswipe.js"></script>
-->
<!-- Photoswipe css/js libraries -->
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.1/photoswipe.min.css" integrity="sha256-sCl5PUOGMLfFYctzDW3MtRib0ctyUvI9Qsmq2wXOeBY=" crossorigin="anonymous" />
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.1/default-skin/default-skin.min.css" integrity="sha256-BFeI1V+Vh1Rk37wswuOYn5lsTcaU96hGaI7OUVCLjPc=" crossorigin="anonymous" />
<!-- these files are loaded in the theme footer
<script src="https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.1/photoswipe.min.js" integrity="sha256-UplRCs9v4KXVJvVY+p+RSo5Q4ilAUXh7kpjyIP5odyc=" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.1/photoswipe-ui-default.min.js" integrity="sha256-PWHOlUzc96pMc8ThwRIXPn8yH4NOLu42RQ0b9SpnpFk=" crossorigin="anonymous"></script>
-->
<!-- Root element of PhotoSwipe. Must have class pswp. -->
<div class="pswp" tabindex="-1" role="dialog" aria-hidden="true">
<!-- Background of PhotoSwipe.
It's a separate element, as animating opacity is faster than rgba(). -->
<div class="pswp__bg"></div>
<!-- Slides wrapper with overflow:hidden. -->
<div class="pswp__scroll-wrap">
<!-- Container that holds slides.
PhotoSwipe keeps only 3 of them in DOM to save memory.
Don't modify these 3 pswp__item elements, data is added later on. -->
<div class="pswp__container">
<div class="pswp__item"></div>
<div class="pswp__item"></div>
<div class="pswp__item"></div>
</div>
<!-- Default (PhotoSwipeUI_Default) interface on top of sliding area. Can be changed. -->
<div class="pswp__ui pswp__ui--hidden">
<div class="pswp__top-bar">
<!-- Controls are self-explanatory. Order can be changed. -->
<div class="pswp__counter"></div>
<button class="pswp__button pswp__button--close" title="Close (Esc)"></button>
<button class="pswp__button pswp__button--share" title="Share"></button>
<button class="pswp__button pswp__button--fs" title="Toggle fullscreen"></button>
<button class="pswp__button pswp__button--zoom" title="Zoom in/out"></button>
<!-- Preloader demo http://codepen.io/dimsemenov/pen/yyBWoR -->
<!-- element will get class pswp__preloader--active when preloader is running -->
<div class="pswp__preloader">
<div class="pswp__preloader__icn">
<div class="pswp__preloader__cut">
<div class="pswp__preloader__donut"></div>
</div>
</div>
</div>
</div>
<div class="pswp__share-modal pswp__share-modal--hidden pswp__single-tap">
<div class="pswp__share-tooltip"></div>
</div>
<button class="pswp__button pswp__button--arrow--left" title="Previous (arrow left)">
</button>
<button class="pswp__button pswp__button--arrow--right" title="Next (arrow right)">
</button>
<div class="pswp__caption">
<div class="pswp__caption__center"></div>
</div>
</div>
</div>
</div>
{{ end }}