Files
leecat.art/_site/leatherworking-favorites/index.html

1668 lines
42 KiB
HTML
Raw Normal View History

<!doctype html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>leatherworking favorites | hello hello</title>
<meta name="description" content="Lee Cattarin... on the internet!">
<link rel="alternate" href="/feed.xml" type="application/atom+xml" title="hello hello">
<meta property="og:title" content="leatherworking favorites">
<meta property="og:type" content="website">
<meta property="og:description" content="Lee Cattarin... on the internet!">
<meta property="og:site_name" content="hello hello">
<meta property="og:image" content="/img/leather-harness-wip.jpg">
<meta property="og:image:alt" content="two pieces of a chest harness sitting on a messy workbench. both pieces are about 8 inches long total and consist of two large o-rings joined by a dark teal leather strap. the o rings and rivets are matte black.">
<meta name="generator" content="Eleventy v3.1.2">
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin="">
<link href="https://fonts.googleapis.com/css2?family=Atkinson+Hyperlegible+Mono:ital,wght@0,200..800;1,200..800&family=Atkinson+Hyperlegible+Next:ital,wght@0,200..800;1,200..800&display=swap" rel="stylesheet">
<script src="https://kit.fontawesome.com/884dded219.js" crossorigin="anonymous"></script>
<style>.post-metadata {
display: flex;
flex-flow: row wrap;
justify-content: space-between;
align-items: baseline;
margin: 1.5rem 0 .5rem;
}
.post-metadata p {
font-size: .9rem;
margin: 0;
}
.post-tags {
display: flex;
flex-flow: row wrap;
gap: .5rem;
list-style: none;
margin: 0;
}
.post-tags li {
margin: 0;
}
.post-tags li a {
text-decoration: none;
color: var(--color-teal);
padding: 0 .5rem;
border-radius: 1rem;
box-shadow: .15rem .15rem var(--color-shadow);
border: .08rem solid var(--color-teal);
line-height: 2;
/* Click animation handling */
position: relative;
top: 0;
left: 0;
transition: top .1s ease-in, left .1s ease-in;
}
.post-tags li a:focus-visible {
outline: none;
background-color: var(--color-teal);
color: var(--color-bg);
}
@media (any-hover: hover) {
.post-tags li a:hover {
outline: none;
background-color: var(--color-teal);
color: var(--color-bg);
}
}
@media (forced-colors: active) {
.post-tags li a:focus-visible {
outline-offset: .08rem;
outline: .08rem solid;
}
@media (any-hover: hover) {
.post-tags li a:hover {
outline-offset: .08rem;
outline: .08rem solid;
}
}
}
/* Click animation */
.post-tags li a:active {
top: .1rem;
left: .1rem;
box-shadow: .05rem .05rem var(--color-shadow);
}
/* Adapted from PrismJS 1.30.0 Tomorrow Night theme
https://prismjs.com/download
*/
code,
pre,
code[class*=language-],
pre[class*=language-] {
font-family: var(--font-family-code);
background-color: var(--color-bg-alt);
font-size: .9rem;
text-shadow: 0 1px var(--color-shadow);
-moz-tab-size: 4;
-o-tab-size: 4;
tab-size: 4;
-webkit-hyphens: none;
-moz-hyphens: none;
-ms-hyphens: none;
hyphens: none;
}
pre,
pre[class*=language-] {
margin: 1rem 0;
padding: 1rem;
line-height: 1.5;
white-space: pre-wrap;
word-break: break-word;
overflow-wrap: break-word;
border-radius: .5rem;
overflow: auto;
}
:not(pre)>code,
:not(pre)>code[class*=language-] {
padding: .2rem;
border-radius: .25rem;
white-space: normal;
}
/* Selected text */
code ::-moz-selection,
code::-moz-selection,
pre ::-moz-selection,
pre::-moz-selection,
code[class*=language-] ::-moz-selection,
code[class*=language-]::-moz-selection,
pre[class*=language-] ::-moz-selection,
pre[class*=language-]::-moz-selection,
code ::selection,
code::selection,
pre ::selection,
pre::selection,
code[class*=language-] ::selection,
code[class*=language-]::selection,
pre[class*=language-] ::selection,
pre[class*=language-]::selection {
text-shadow: none;
background-color: var(--color-bg);
}
/* Syntax highlighting */
.token.namespace {
opacity: .7;
}
.token.bold,
.token.important {
font-weight:700
}
.token.italic {
font-style:italic
}
.token.block-comment,
.token.cdata,
.token.comment,
.token.doctype,
.token.prolog,
.token.punctuation {
color: var(--color-grey);
}
.token.attr-name,
.token.deleted,
.token.namespace,
.token.tag {
color: var(--color-red);
}
.token.boolean,
.token.function,
.token.number {
color: var(--color-orange);
}
.token.class-name,
.token.constant,
.token.property,
.token.symbol {
color: var(--color-yellow);
}
.token.attr-value,
.token.char,
.token.regex,
.token.string,
.token.variable,
.token.inserted {
color: var(--color-green);
}
.token.entity,
.token.operator,
.token.url,
.token.function-name {
color:var(--color-blue);
}
.token.atrule,
.token.builtin,
.token.important,
.token.keyword,
.token.selector {
color: var(--color-purple);
}
2026-02-20 08:36:56 -08:00
#postlist,
#taglist {
list-style: none;
}
#postlist, .post,
#taglist, .tag {
margin: 0;
}
/* Odd-numbered posts & tag layout/coloration */
.post:nth-child(odd) .postlink,
.tag:nth-child(odd) .taglink {
grid-template-areas:
'img h2'
'img info'
'img .';
grid-template-columns: 45% auto;;
--color-primary: var(--color-teal);
--color-accent: var(--color-pink);
}
/* Even-numbered posts & tags layout/coloration */
.post:nth-child(even) .postlink,
.tag:nth-child(even) .taglink {
grid-template-areas:
'h2 img'
'info img'
'. img';
grid-template-columns: auto 45%;
--color-primary: var(--color-pink);
--color-accent: var(--color-teal);
}
/* Layout for all posts on mobile */
@media (max-width: 650px) {
.post:nth-child(n) .postlink,
.tag:nth-child(n) .taglink {
grid-template-areas:
'img'
'h2'
'info';
grid-template-columns: auto;
}
}
/* Link */
.postlink,
.taglink {
display: grid;
border: .25rem solid var(--color-primary);
border-radius: 1.25rem;
box-shadow: .35rem .35rem var(--color-shadow);
margin: 2rem 0;
text-decoration: none;
/* Click animation handling */
position: relative;
top: 0;
left: 0;
transition: top .05s ease-in, left .05s ease-in;
}
.postlink:focus-visible,
.taglink:focus-visible {
background-color: var(--color-primary);
outline: none;
}
@media (any-hover: hover) {
.postlink:hover,
.taglink:hover {
background-color: var(--color-primary);
}
}
/* Forced colors */
@media (forced-colors: active) {
.postlink:focus-visible,
.taglink:focus-visible {
outline-offset: .25rem;
outline: .25rem solid;
}
@media (any-hover: hover) {
.postlink:hover,
.taglink:hover {
outline-offset: .25rem;
outline: .25rem solid;
}
}
}
/* Click animation */
.postlink:active,
.taglink:active {
box-shadow: none;
top: .2rem;
left: .2rem;
box-shadow: .15rem .15rem var(--color-shadow);
}
/* Post & tag elements */
.post h2, .post img,
.post ul, .post li,
.tag h2, .tag p,
.tag img {
margin: 0;
}
.post h2,
.tag h2 {
grid-area: h2;
padding: .25rem .5rem;
text-transform: uppercase;
font-size: 1.5rem;
color: var(--color-primary);
border-radius: 1rem 1rem 0 0;
border-bottom: .25rem solid var(--color-accent);
}
.post:nth-child(even) h2,
.tag:nth-child(even) h2 {
text-align: right;
}
.postlink:focus-visible h2,
.taglink:focus-visible h2 {
color: var(--color-bg);
border-color: var(--color-bg);
}
@media (any-hover: hover) {
.postlink:hover h2,
.taglink:hover h2 {
color: var(--color-bg);
border-color: var(--color-bg);
}
}
/* Images */
.post img,
.tag-imgs {
grid-area: img;
}
.tag-imgs {
display: grid;
grid-template-columns: repeat(2, 1fr);
gap: .15rem;
}
.tag-imgs img {
aspect-ratio: 3 / 2;
object-fit: cover;
}
.missing-image {
width: 100%;
aspect-ratio: 3 / 2;
background-color: var(--color-bg-alt);
border-radius: calc(1rem);
}
.taglink:focus-visible .missing-image {
opacity: .7;
}
@media (any-hover: hover) {
.taglink:hover .missing-image {
opacity: .7;
}
}
/* Post tags */
.postlist-tags {
grid-area: info;
list-style: none;
display: flex;
flex-flow: row wrap;
gap: .5rem;
padding: .5rem;
}
.post:nth-child(odd) .postlist-tags {
justify-content: flex-end;
}
.postlist-tags li,
.tagcount {
background-color: var(--color-primary);
color: var(--color-bg);
padding: 0 .5rem;
border-radius: 1rem;
}
.postlink:focus-visible .postlist-tags li,
.taglink:focus-visible .tagcount {
background-color: var(--color-bg);
color: var(--color-primary);
}
@media (any-hover: hover) {
.postlink:hover .postlist-tags li,
.taglink:hover .tagcount {
background-color: var(--color-bg);
color: var(--color-primary);
}
}
/* Tag count */
.tag p {
grid-area: info;
padding: .5rem;
}
.tag:nth-child(odd) p {
text-align: right;
}
:root {
color-scheme: light dark;
--font-family: 'Atkinson Hyperlegible Next', sans-serif;
--font-family-code: 'Atkinson Hyperlegible Mono', monospace;
--color-dark: #2e303e;
--color-dark-alt: #3c3f52;
--color-light: #ebeeef;
--color-light-alt: #dbe1e3;
--color-teal-dark: #18737b;
--color-teal-light: #25b0bc;
--color-pink-dark: #94195d;
--color-pink-light: #ee9fcb;
--color-shadow: rgba(2, 10, 40, .25);
/* Used for syntax highlighting */
--color-red-light: #e95678;
--color-orange-light: #fab795;
--color-yellow-light: #fbe6bc;
--color-green-light: #29d398;
--color-blue-light: #26bbd9;
--color-purple-light: #ddaeea;
--color-grey-light: #b9c3c6;
--color-red-dark: #991433;
--color-orange-dark: #883206;
--color-yellow-dark: #6a4906;
--color-green-dark: #125940;
--color-blue-dark: #125663;
--color-purple-dark: #722999;
--color-grey-dark: #4a4b64;
--color-text: light-dark(var(--color-dark), var(--color-light));
--color-bg: light-dark(var(--color-light), var(--color-dark));
--color-text-alt: light-dark(var(--color-dark-alt), var(--color-light-alt));
--color-bg-alt: light-dark(var(--color-light-alt), var(--color-dark-alt));
--color-teal: light-dark(var(--color-teal-dark), var(--color-teal-light));
--color-pink: light-dark(var(--color-pink-dark), var(--color-pink-light));
--color-red: light-dark(var(--color-red-dark), var(--color-red-light));
--color-orange: light-dark(var(--color-orange-dark), var(--color-orange-light));
--color-yellow: light-dark(var(--color-yellow-dark), var(--color-yellow-light));
--color-green: light-dark(var(--color-green-dark), var(--color-green-light));
--color-blue: light-dark(var(--color-blue-dark), var(--color-blue-light));
--color-purple: light-dark(var(--color-purple-dark), var(--color-purple-light));
--color-grey: light-dark(var(--color-grey-dark), var(--color-grey-light));
}
/* Base */
* {
box-sizing: border-box;
margin: 0;
padding: 0;
}
body {
font-family: var(--font-family);
color: var(--color-text);
background-color: var(--color-bg);
}
main {
width: 60vw;
max-width: 1000px;
margin: 0 auto;
2026-02-20 08:36:56 -08:00
scroll-margin-top: 7rem;
}
@media (max-width: 1050px) {
main {
width: 75vw;
}
}
@media (max-width: 650px) {
main {
width: 92vw;
}
}
/* Headers */
h1, h2, h3, h4, h5, h6 {
line-height: 1.25;
color: var(--color-teal);
}
h1 {
margin-top: 3rem;
font-size: 3.5rem;
text-align: center;
}
2026-02-20 08:36:56 -08:00
h2, h3, h4, h5, h6 {
scroll-margin-top: 5rem;
}
h2 {
margin-top: 2rem;
font-size: 2.2rem;
}
h3 {
margin-top: 1.5rem;
font-size: 1.6rem;
}
@media (max-width: 650px) {
h1 { font-size: 2.8rem; }
h2 { font-size: 1.8rem; }
h3 { font-size: 1.35rem; }
}
h4, h5, h6 {
margin-top: 1rem;
font-size: 1.2rem;
}
/* Images */
img {
display: block;
max-width: 100%;
height: auto;
border-radius: 1rem;
}
/* Paragraphs */
p {
margin: 1.25rem 0;
line-height: 1.4;
}
strong,
b {
font-weight: 900;
}
/* Links */
a {
color: var(--color-text);
border-radius: .25rem;
text-decoration: underline;
text-decoration-style: solid;
text-decoration-thickness: .2em;
text-decoration-color: var(--color-teal);
transition: text-decoration-thickness .5s;
}
a:focus-visible {
text-decoration: none;
outline: .15rem solid var(--color-teal);
}
@media (any-hover: hover) {
a:hover {
text-decoration-thickness: .4em;
}
}
a:active {
text-decoration-thickness: .4em;
}
/* Heading anchors */
a.ha,
span.ha-placeholder {
color: var(--color-pink);
}
span.ha-placeholder {
opacity: .55;
}
/* Lists */
::marker {
color: var(--color-pink);
}
ul, ol, dl, li {
margin-left: 1rem;
}
li {
line-height: 1.2 5;
margin-top: .65rem;
margin-bottom: .65rem;
}
li ul, li ol {
margin: .5rem 0;
}
dt {
font-weight: 900;
margin-top: .5rem;
}
dd {
margin-left: 2rem;
margin-bottom: .75rem;
}
/* Blockquotes */
blockquote {
margin: .5rem 0;
padding: 0 1rem;
border-radius: .25rem 1rem 1rem .25rem;
line-height: 1.25;
border-left: .5rem solid var(--color-pink);
}
blockquote,
blockquote p,
blockquote ol,
blockquote ul {
background-color: var(--color-bg-alt);
padding: .5rem;
}
blockquote p {
margin: 0;
}
/* Tables */
table {
width: 100%;
border-spacing: 0; /* border collapse doesn't play nice with radii */
border-radius: .3rem;
border: thin solid var(--color-pink);
}
th {
color: var(--color-bg);
background-color: var(--color-pink);
}
th code {
color: var(--color-text); /* Yes, I actually do this somewhere */
}
th, td {
padding: .5rem;
text-align: left;
}
tr:nth-child(even) { background-color: var(--color-bg-alt); }
th:not(:first-child) { border-left: thin solid var(--color-bg); }
th:first-child { border-top-left-radius: .25rem; }
th:last-child { border-top-right-radius: .25rem; }
td:not(:first-child) { border-left: thin solid var(--color-pink); }
/* Times */
time {
color: var(--color-grey);
}
/* Horizontal rules */
hr {
2026-02-20 08:36:56 -08:00
border: .25rem solid var(--color-pink);
margin: 2rem 0;
}
/* Used on home, reference, gallery pages */
.centered {
text-align: center;
}
/* Currently only used for resume, but it's generalizable */
.upper {
text-transform: uppercase;
}
/* Header */
header {
position: sticky;
top: 0;
background-color: var(--color-bg);
padding: .75rem 0;
z-index: 10;
2026-02-20 08:36:56 -08:00
border-bottom: .5rem solid var(--color-teal);
box-shadow: 0 .25rem .15rem var(--color-shadow);
}
/* Header links, pagination links */
header a,
.pagination a,
.webring ul a {
border-radius: 1rem;
border: .125rem solid var(--color-pink);
color: var(--color-pink);
text-decoration: none;
padding: 0 .25rem;
box-shadow: .15rem .15rem var(--color-shadow);
font-size: 1.2rem;
/* Click animation handling */
position: relative;
top: 0;
left: 0;
transition: top .05s ease-in, left .05s ease-in;
}
header a,
.pagination .older a,
.webring .prev a,
.webring .rand a {
padding-right: .35rem;
}
.pagination .newer a,
.webring .next a,
.webring .rand a {
padding-left: .35rem;
}
header a:focus-visible,
.pagination a:focus-visible,
.webring ul a:focus-visible {
color: var(--color-bg);
border-color: var(--color-pink);
background-color: var(--color-pink);
outline: none;
}
@media (any-hover: hover) {
header a:hover,
.pagination a:hover,
.webring ul a:hover {
color: var(--color-bg);
border-color: var(--color-pink);
background-color: var(--color-pink);
}
}
@media (forced-colors: active) {
header a:focus-visible,
.pagination a:focus-visible,
.webring ul a:focus-visible {
outline-offset: .125rem;
outline: .125rem solid;
}
@media (any-hover: hover) {
header a:hover,
.pagination a:hover,
.webring ul a:hover {
outline-offset: .125rem;
outline: .125rem solid;
}
}
}
/* Click animation */
header a:active,
.pagination a:active,
.webring ul a:active {
top: .1rem;
left: .1rem;
box-shadow: .05rem .05rem var(--color-shadow);
}
/* Current page */
header a[aria-current="page"] {
border-color: var(--color-teal);
color: var(--color-teal);
}
header a[aria-current="page"]:focus-visible {
color: var(--color-bg);
border-color: var(--color-teal);
background-color: var(--color-teal);
}
@media (any-hover: hover) {
header a[aria-current="page"]:hover {
color: var(--color-bg);
background-color: var(--color-teal);
border-color: var(--color-teal);
}
}
/* Header link icons, pagination icons */
header i,
.pagination i,
.webring ul i {
color: var(--color-teal);
}
header i,
.pagination .older i,
.webring .prev i,
.webring .rand i:nth-child(1) {
padding-left: .25rem;
}
.pagination .newer i,
.webring .next i,
.webring .rand i:nth-child(2) {
padding-right: .25rem;
}
header a[aria-current="page"] i {
color: var(--color-pink);
}
header a:focus-visible i,
a[aria-current="page"] a:focus-visible i,
.pagination a:focus-visible i,
.webring ul a:focus-visible i {
color: var(--color-bg);
}
@media (any-hover: hover) {
header a:hover i,
header a[aria-current="page"]:hover i,
.pagination a:hover i,
.webring ul a:hover i {
color: var(--color-bg);
}
}
/* Skip link */
#skip {
left: -999px;
position: absolute;
top: auto;
width: 1px;
height: 1px;
overflow: hidden;
z-index: -99;
}
#skip:focus-visible {
display: inline-block;
left: auto;
top: auto;
width: auto;
height: auto;
overflow: auto;
margin: 0 10%;
z-index: 999;
}
/* Nav */
header ul {
display: flex;
list-style: none;
gap: 1rem;
justify-content: center;
}
header ul,
header li {
margin: 0;
}
@media (max-width: 650px) {
.menu-text {
display: none; /* Icons only on small screens */
}
header a {
padding: .15rem .5rem;
}
header i {
padding: 0;
}
}
/* Footer */
footer {
padding: 1rem 0;
font-size: .9rem;
2026-02-20 08:36:56 -08:00
border-top: .5rem solid var(--color-pink);
}
footer ul {
display: flex;
list-style: none;
gap: .5rem;
justify-content: center;
margin: 0;
}
footer li {
margin: 0;
}
footer li:nth-child(2)::before,
footer li:nth-child(2)::after {
content: " ● " / "";
color: var(--color-teal);
}
@media (max-width: 650px) {
footer ul {
flex-flow: column;
text-align: center;
}
footer li:nth-child(2)::before,
footer li:nth-child(2)::after {
content: none;
}
}
footer a {
text-decoration-color: var(--color-pink);
}
footer a:focus-visible {
outline-color: var(--color-pink);
}
/* Pagination */
.pagination,
.pagination li {
margin: 0;
}
.pagination {
display: grid;
grid-template-columns: repeat(2, 1fr);
grid-template-areas: "older newer";
list-style: none;
margin-top: 3rem;
}
@media (max-width: 650px) {
.post-pagination {
grid-template-columns: 1fr;
grid-template-areas:
"older"
"newer";
gap: .75rem;
}
}
.pagination .older {
grid-area: older;
}
.pagination .newer {
grid-area: newer;
text-align: right;
}
/* webring navigation */
.webring {
margin-bottom: 3rem;
}
.webring ul {
display: flex;
flex-flow: row wrap;
list-style: none;
justify-content: space-around;
gap: .35rem;
}
.webring ul,
.webring li {
margin-left: 0;
}
@media print {
/* Nav elements */
header,
footer,
nav {
display: none !important;
}
/* Base */
body {
background-color: #fff;
color: #000;
}
main {
width: 95vw;
}
h1,h2,h3,h4,h5,h6 {
color: #000;
}
/* Links */
/* Hover is not really necessary, but it's annoying when testing otherwise */
a,
a:hover {
text-decoration-style: dotted;
text-decoration-thickness: .1rem;
text-decoration-color: #000;
}
a::after{
content: " (" attr(href) ")";
}
/* Code */
code,
pre,
code[class*=language-],
pre[class*=language-] {
text-shadow: none;
background-color: var(--color-light);
color: #000 !important;
}
.token.namespace {
opacity: 1;
}
.token.block-comment,
.token.cdata,
.token.comment,
.token.doctype,
.token.prolog,
.token.punctuation,
.token.attr-name,
.token.deleted,
.token.namespace,
.token.tag,
.token.boolean,
.token.function,
.token.number,
.token.class-name,
.token.constant,
.token.property,
.token.symbol,
.token.attr-value,
.token.char,
.token.regex,
.token.string,
.token.variable,
.token.inserted,
.token.entity,
.token.operator,
.token.url,
.token.function-name,
.token.atrule,
.token.builtin,
.token.important,
.token.keyword,
.token.selector {
color: #000;
}
}</style>
<script type="module">// Thank you to https://github.com/daviddarnes/heading-anchors
// Thank you to https://amberwilson.co.uk/blog/are-your-anchor-links-accessible/
let globalInstanceIndex = 0;
class HeadingAnchors extends HTMLElement {
static register(tagName = "heading-anchors", registry = window.customElements) {
if(registry && !registry.get(tagName)) {
registry.define(tagName, this);
}
}
static attributes = {
exclude: "data-ha-exclude",
prefix: "prefix",
content: "content",
}
static classes = {
anchor: "ha",
placeholder: "ha-placeholder",
srOnly: "ha-visualhide",
}
static defaultSelector = "h2,h3,h4,h5,h6";
static css = `
.${HeadingAnchors.classes.srOnly} {
clip: rect(0 0 0 0);
height: 1px;
overflow: hidden;
position: absolute;
width: 1px;
}
.${HeadingAnchors.classes.anchor} {
position: absolute;
left: var(--ha_offsetx);
top: var(--ha_offsety);
text-decoration: none;
opacity: 0;
}
.${HeadingAnchors.classes.placeholder} {
opacity: .3;
}
.${HeadingAnchors.classes.anchor}:is(:focus-within, :hover) {
opacity: 1;
}
.${HeadingAnchors.classes.anchor},
.${HeadingAnchors.classes.placeholder} {
display: inline-block;
padding: 0 .25em;
/* Disable selection of visually hidden label */
-webkit-user-select: none;
user-select: none;
}
@supports (anchor-name: none) {
.${HeadingAnchors.classes.anchor} {
position: absolute;
left: anchor(left);
top: anchor(top);
}
}`;
get supports() {
return "replaceSync" in CSSStyleSheet.prototype;
}
get supportsAnchorPosition() {
return CSS.supports("anchor-name: none");
}
constructor() {
super();
if(!this.supports) {
return;
}
let sheet = new CSSStyleSheet();
sheet.replaceSync(HeadingAnchors.css);
document.adoptedStyleSheets = [...document.adoptedStyleSheets, sheet];
this.headingStyles = {};
this.instanceIndex = globalInstanceIndex++;
}
connectedCallback() {
if (!this.supports) {
return;
}
this.headings.forEach((heading, index) => {
if(!heading.hasAttribute(HeadingAnchors.attributes.exclude)) {
let anchor = this.getAnchorElement(heading);
let placeholder = this.getPlaceholderElement();
// Prefers anchor position approach for better accessibility
// https://amberwilson.co.uk/blog/are-your-anchor-links-accessible/
if(this.supportsAnchorPosition) {
let anchorName = `--ha_${this.instanceIndex}_${index}`;
placeholder.style.setProperty("anchor-name", anchorName);
anchor.style.positionAnchor = anchorName;
}
heading.appendChild(placeholder);
heading.after(anchor);
}
});
}
// Polyfill-only
positionAnchorFromPlaceholder(placeholder) {
if(!placeholder) {
return;
}
let heading = placeholder.closest("h1,h2,h3,h4,h5,h6");
if(!heading.nextElementSibling) {
return;
}
// TODO next element could be more defensive
this.positionAnchor(heading.nextElementSibling);
}
// Polyfill-only
positionAnchor(anchor) {
if(!anchor || !anchor.previousElementSibling) {
return;
}
// TODO previous element could be more defensive
let heading = anchor.previousElementSibling;
this.setFontProp(heading, anchor);
if(this.supportsAnchorPosition) {
// quit early
return;
}
let placeholder = heading.querySelector(`.${HeadingAnchors.classes.placeholder}`);
if(placeholder) {
anchor.style.setProperty("--ha_offsetx", `${placeholder.offsetLeft}px`);
anchor.style.setProperty("--ha_offsety", `${placeholder.offsetTop}px`);
}
}
setFontProp(heading, anchor) {
let placeholder = heading.querySelector(`.${HeadingAnchors.classes.placeholder}`);
if(placeholder) {
let style = getComputedStyle(placeholder);
let props = ["font-weight", "font-size", "line-height", "font-family"];
let [weight, size, lh, family] = props.map(name => style.getPropertyValue(name));
anchor.style.setProperty("font", `${weight} ${size}/${lh} ${family}`);
let vars = style.getPropertyValue("font-variation-settings");
if(vars) {
anchor.style.setProperty("font-variation-settings", vars);
}
}
}
getAccessibleTextPrefix() {
// Useful for i18n
return this.getAttribute(HeadingAnchors.attributes.prefix) || "Jump to section titled";
}
getContent() {
if(this.hasAttribute(HeadingAnchors.attributes.content)) {
return this.getAttribute(HeadingAnchors.attributes.content);
}
return "#";
}
// Placeholder nests inside of heading
getPlaceholderElement() {
let ph = document.createElement("span");
ph.setAttribute("aria-hidden", true);
ph.classList.add(HeadingAnchors.classes.placeholder);
let content = this.getContent();
if(content) {
ph.innerHTML = content; // CHANGED HERE
}
ph.addEventListener("mouseover", (e) => {
let placeholder = e.target.closest(`.${HeadingAnchors.classes.placeholder}`);
if(placeholder) {
this.positionAnchorFromPlaceholder(placeholder);
}
});
return ph;
}
getAnchorElement(heading) {
let anchor = document.createElement("a");
anchor.href = `#${heading.id}`;
anchor.classList.add(HeadingAnchors.classes.anchor);
let content = this.getContent();
anchor.innerHTML = `<span class="${HeadingAnchors.classes.srOnly}">${this.getAccessibleTextPrefix()}: ${heading.textContent}</span>${content ? `<span aria-hidden="true">${content}</span>` : ""}`;
anchor.addEventListener("focus", e => {
let anchor = e.target.closest(`.${HeadingAnchors.classes.anchor}`);
if(anchor) {
this.positionAnchor(anchor);
}
});
anchor.addEventListener("mouseover", (e) => {
// when CSS anchor positioning is supported, this is only used to set the font
let anchor = e.target.closest(`.${HeadingAnchors.classes.anchor}`);
this.positionAnchor(anchor);
});
return anchor;
}
get headings() {
return this.querySelectorAll(this.selector.split(",").map(entry => `${entry.trim()}[id]`));
}
get selector() {
return this.getAttribute("selector") || HeadingAnchors.defaultSelector;
}
}
HeadingAnchors.register();
export { HeadingAnchors }</script>
</head>
<body>
<header>
<a href="#main" id="skip" title="skip to main content" aria-label="skip to main content">
<i class="fa-solid fa-forward" aria-hidden="true"></i> skip
</a>
<nav aria-label="main navigation">
<ul>
<li>
<a href="/reference/" title="read reference posts" aria-label="read reference posts">
<i class="fa-regular fa-folder-open" aria-hidden="true"></i>
<span class="menu-text">reference</span>
</a>
</li>
<li>
<a href="/gallery/" title="view the gallery" aria-label="view the gallery">
<i class="fa-regular fa-images" aria-hidden="true"></i>
<span class="menu-text">gallery</span>
</a>
</li>
<li>
<a href="/" title="" aria-label="">
<i class="fa fa-solid fa-crow" aria-hidden="true"></i>
<span class="menu-text">home</span>
</a>
</li>
<li>
<a href="/about/" title="about Lee" aria-label="about Lee">
<i class="fa-regular fa-user" aria-hidden="true"></i>
<span class="menu-text">about</span>
</a>
</li>
<li>
<a href="/contact/" title="contact Lee" aria-label="contact Lee">
<i class="fa-solid fa-envelope-open-text" aria-hidden="true"></i>
<span class="menu-text">contact</span>
</a>
</li>
</ul>
</nav>
</header>
<main id="main">
2026-02-20 08:36:56 -08:00
<heading-anchors content="<i class='fa-solid fa-anchor'></i>">
<article>
<h1 id="leatherworking-favorites">leatherworking favorites</h1>
<div class="post-metadata">
<p>
posted on
<time datetime="2023-10-08">October 8, 2023</time>
by Lee Cattarin
</p>
<ul class="post-tags">
<li>
<a href="/tags/leather/">leather</a>
</li>
</ul>
</div>
<img src="/img/leather-harness-wip.jpg" alt="two pieces of a chest harness sitting on a messy workbench. both pieces are about 8 inches long total and consist of two large o-rings joined by a dark teal leather strap. the o rings and rivets are matte black." loading="lazy" decoding="async" width="1000" height="750">
<h2 id="practices">practices</h2>
<ul>
<li>cardboard templates have been really handy for the spacing of rivets and such. I use cereal boxes since they are not corrugated.</li>
</ul>
<h2 id="tools">tools</h2>
<p>If I have linked a tool, I really like that specific tool and find it stands out. Otherwise, idk, I've used precisely one edge beveler, I have no idea how it compares.</p>
<ul>
<li>(need to have) some kind of scratch awl for marking</li>
<li>(need to have) cutproof mat</li>
<li>(need to have basically whenever you are using a mallet) <a href="https://www.buckleguy.com/cutting-board-multiple-sizes/" target="_blank" rel="external">&quot;poundo board&quot; or cutting board</a> (this is just an example, I got mine elsewhere) - importantly, this is distinct from your cutproof mat. you <em>can</em> use this in place of your cutproof mat but it tends to pick up a lot of punctures which can leave indents in your leather with pressure - so I only use mine for mallet-ing and otherwise use my cutproof mat</li>
<li>(nice to have) <a href="https://www.weaverleathersupply.com/products/pattern-sheet-24-x-45" target="_blank" rel="external">pattern plastic</a> - but like I said above you can use non-corrugated cardboard</li>
<li>(nice to have) <a href="https://www.buckleguy.com/bg-acrylic-tool-leather-thickness-gauge/" target="_blank" rel="external">acrylic leather thickness gauge</a> - but you can also just use a ruler or calipers, or learn to gauge by eye/feel</li>
</ul>
<h3 id="cutting">cutting</h3>
<ul>
<li>(need to have) metal cork-backed ruler (cork backing will keep it from slip-sliding around)</li>
<li>(nice to have, but any sharp blade will do) <a href="https://www.buckleguy.com/ergo-kiwi-knife-2-0/" target="_blank" rel="external">ergo kiwi knife</a></li>
<li>(nice to have for harnesses, belts) strap cutter</li>
<li>(nice to have for small objects with a lot of layers at the seams, like wallets) skiving knife of some kind. there's a lot of different types out there. I have a CS Osborne leather knife and I don't love it, but idk if that's just because I am still learning how to skive.
<ul>
<li>you're supposed to skive on a fucken <a href="https://www.weaverleathersupply.com/products/marble-tooling-slab" target="_blank" rel="external">rock</a> so as not to absolutely wreck your cutproof mat. I haven't got my rock yet but I haven't ruined my mat yet either.</li>
<li>ok so I got a <a href="https://www.weaverleathersupply.com/products/flat-leather-knife" target="_blank" rel="external">skiving knife</a> from Weaver and it <em>definitely</em> beats out the CS Osborne leather knife</li>
</ul>
</li>
</ul>
<h3 id="edging-and-burnishing">edging and burnishing</h3>
<ul>
<li>(nice to have) edge beveler</li>
<li>(need to have) sandpaper in maybe two grits. I have 100 and 600 sitting around right now</li>
<li>(need to have) some small pieces of heavy canvas</li>
<li>(nice to have) <a href="https://www.buckleguy.com/seiwa-tokonole-leather-burnishing-gum-multiple-sizes-colors/" target="_blank" rel="external">tokonole!!!</a>
<ul>
<li>tokonole can even burnish chrome tan leather and flesh side of veg tan</li>
</ul>
</li>
<li>(nice to have) <a href="https://www.buckleguy.com/leather-edge-slicker-burnishing-tool-beech-wood/" target="_blank" rel="external">wooden edge burnishing tool</a> but tbh I find myself just using canvas instead of my burnishing tool
<ul>
<li>you can also use wooden tool handles, if you have for example an edge beveler with a wooden handle sitting around</li>
</ul>
</li>
<li>(nice to have/need to have if you don't get tokonole) beeswax</li>
<li>(nice to have) <a href="https://www.dickblick.com/items/lineco-micro-spatula-flat/" target="_blank" rel="external">micro spatula</a> - I bought this for bookbinding but I find it useful for applying tokonole or doing other odd lil jobs</li>
</ul>
<h3 id="punching">punching</h3>
<ul>
<li>(need to have) a mallet or something for hitting things. yes there are $100 mauls you can buy. idk a shitty mallet is working fine for me so far
<ul>
<li>alright i splurged on a maul and it was worth it. dammit.</li>
</ul>
</li>
<li>(nice to have) <a href="https://www.talasonline.com/Japanese-Push-Drill" target="_blank" rel="external">japanese push drill</a> and <a href="https://www.talasonline.com/Japanese-Push-Drill-Replacement-Bits" :target="_blank">bits</a></li>
<li>if you don't want to go in on a $50 push drill, start with just some simple <a href="https://www.buckleguy.com/245-belt-punch-multiple-sizes/" target="_blank" rel="external">single-hole punches</a> or a <a href="https://www.buckleguy.com/223-revolving-punch/" :target="_blank">rotary punch</a>. rotary punches are pretty heavily recommended since they come with a range of punch sizes; I avoid them like the plague because I have small shitty hands and I think those would pair poorly with a rotary punch.</li>
<li>if you're going to be attaching buckles, you'll need oblong holes for the buckle tongue. two options:
<ul>
<li>punch a standard hole at each end of your eventual oblong, then using a ruler and sharp small blade cut between those holes to create your oblong
<img src="/img/oblong-punch-alternative.jpg" alt="A small piece of leather showing the steps to creating an oblong hole. First there is just a straight 1-inch line drawn by scratch awl. Holes are punched at both ends of that line. Two cuts are made coming from the right-side hole inwards (shown by arrows), about halfway. Similar cuts are then made from the left-hand hole inwards to meet them." loading="lazy" decoding="async" width="1000" height="1000"></li>
<li>get an <a href="https://www.buckleguy.com/151-bag-punch-multiple-sizes/" target="_blank" rel="external">oblong punch</a>. shaped punches are <em>expensive as shit</em> but if you're doing more than a few buckles this is worth it.</li>
</ul>
</li>
<li>another shaped punch: the <a href="https://www.buckleguy.com/0150-strap-end-punch-english-point-multiple-sizes-1/" target="_blank" rel="external">english point strap end punch</a>. I don't own this yet but am heavily considering it if I am going to make more harnesses (and I am). you don't specifically need english point - there's other strap end styles - but having <em>a</em> strap end punch in the size of your choosing is useful for harnesses, belts, anything with a lot of straps.
<ul>
<li>with strap end punches, you can use a larger punch on a smaller strap (for an imperfect result, tbf) but not vice versa</li>
<li>there are also strap end acrylic templates out there on several retailers sites - I have a tandy one</li>
</ul>
</li>
</ul>
<h3 id="riveting-snapping-etc">riveting, snapping, etc</h3>
<ul>
<li>for any given size/brand of rivets, you can usually buy a <a href="https://www.buckleguy.com/bg-rivet-setter-9-2mm-concave-end/" target="_blank" rel="external">setter</a> and <a href="https://www.buckleguy.com/bg-rivet-setter-base-for-9-2-11-13mm-cap-rivets/" :target="_blank">anvil</a> for maybe $25 together
<ul>
<li>also I have one extra of both of those specific linked items, so if you're short on cash lmk and I will ship em to ya - since I have switched over to the next option</li>
</ul>
</li>
<li>however, if you think you might get really into leatherworking, or if you think you will be getting multiple sizes of rivets, attaching snaps, attaching other types of rivet-style clasps, whatever, I would highly recommend <a href="https://www.buckleguy.com/bg-setter-post-base-for-screw-in-dies/" target="_blank" rel="external">this setter post and base</a> and <a href="https://www.buckleguy.com/bg-rivet-setter-die-multiple-sizes-requires-hand-tool-post-base-or-bg-hand-press/" :target="_blank">a rivet setter die</a> or whichever setter die you need for your specific thing
<ul>
<li>these dies also work with <a href="https://www.buckleguy.com/bg-180-convertible-hand-or-foot-press/" target="_blank" rel="external">larger presses</a> and make it much more possible to transition from a hand press to a full press without having to re-buy all your dies</li>
<li>according to Corter Leather at the very least (I don't really have the experience to make a full comparison) this system is much more reliable for well-balanced, well-rounded rivets, snaps, etc</li>
</ul>
</li>
</ul>
<h3 id="stitching">stitching</h3>
<ul>
<li>(nice to have) wing divider for drawing stitching lines</li>
<li>(need to have) stitching chisels! if you want to save some money, you mostly need the 6-tooth and the 2-tooth - 6 for straightaways, 2 for curves. I occasionally use my 4-tooth and <em>very</em> occasionally use my 1-tooth (except for zippers. if you wanna do zippers get a 1-tooth).
<ul>
<li>my stitching chisels are 4mm spacing. I picked this pretty arbitrarily :)</li>
<li>technically you could just buy a diamond awl or a 1-tooth chisel and poke each hole individually and that <em>would</em> be cheaper but oh my god love yourself</li>
</ul>
</li>
<li>(nice to have, any needles will do but oh my god these are pretty hashtag worth) <a href="https://www.buckleguy.com/517-harness-needles-for-hand-sewing-blunt-tip-5-needles/" target="_blank" rel="external">cs osborne harness needles, blunt tip</a></li>
<li>(need to have) thread - I am using <a href="https://www.buckleguy.com/ritza-25-tiger-thread/" target="_blank" rel="external">Ritza 25 Tiger Thread</a> (currently I have the 1.0mm size. I find it a little large and will probably size down when I order other colors - update, sized down to .8 and even have some .6 - much preferable) and have also used <a href="https://threadsofmeisi.com/collections/meisi-superfine-linen-threads" :target="_blank">MeiSi Superfine Linen Thread</a> but polyester threads are easier to seal off with a lighter</li>
<li>(nice to have) some kind of <a href="https://www.joann.com/needle-pullers-3-pkg/3500295.html" target="_blank" rel="external">silicone needle puller</a> (I don't actually have this one, I was having trouble finding what I have - little pink finger covers that are all grippy) for gripping needles. or just use the back of a mousepad? or something?</li>
</ul>
<h3 id="tool-care">tool care</h3>
<ul>
<li>(need to have for certain blades such as skiving knife) jeweler's rouge for stropping
<ul>
<li>I am not an expert here so I am not making firm recommendations. I got mine from Springfield Leather</li>
</ul>
</li>
</ul>
<h3 id="tooling">tooling</h3>
<ul>
<li>(need to have) swivel knife</li>
<li>(need to have) a beveler. I have a smooth beveler at the moment, but am waiting on a checked beveler in the mail as I think I will like that look better</li>
<li>(need to have) as mentioned previously, mallet or maul</li>
<li>(nice to have) literally any other stamps i guess</li>
<li>(nice to have) templates! it really helps to start out with some designs made for swivel knife. I got a few (both free and paid) from <a href="https://www.dadhands.ca/" target="_blank" rel="external">dadhands</a></li>
</ul>
<h3 id="zippers">zippers</h3>
<ul>
<li>okay so I bought them because they are pretty but these <a href="https://www.buckleguy.com/riri-zipper-continuous-chain-combi-eloxal-teeth-elox/" target="_blank" rel="external">rainbow zippers</a> actually make it so much easier because you can differentiate each tooth from the next!!!</li>
<li>(nice to have) tape such as <a href="https://www.buckleguy.com/double-sided-tape/" target="_blank" rel="external">ted's tape</a></li>
</ul>
<h2 id="resources">resources</h2>
<ul>
<li><a href="https://www.youtube.com/@Corter" target="_blank" rel="external">Corter Leather on YouTube</a></li>
<li><a href="https://www.youtube.com/@Leodis.Leather" target="_blank" rel="external">Leodis Leather on YouTube</a></li>
<li><a href="https://www.youtube.com/@dadhands" target="_blank" rel="external">dadhands on YouTube</a></li>
<li><a href="https://www.youtube.com/@majutworks" target="_blank" rel="external">Maju T Works on YouTube</a></li>
</ul>
<h2 id="retailers">retailers</h2>
<ul>
<li><a href="https://www.buckleguy.com/" target="_blank" rel="external">buckleguy</a> has been super speedy and reliable so far - for sure my favorite</li>
<li><a href="https://www.springfieldleather.com/" target="_blank" rel="external">springfield leather</a></li>
<li><a href="https://tandyleather.com/" target="_blank" rel="external">tandy</a></li>
<li><a href="https://www.weaverleathersupply.com/" target="_blank" rel="external">weaver leather supply</a></li>
<li><a href="https://www.longviewleather.com/" target="_blank" rel="external">longview leather (canada)</a></li>
</ul>
</article>
<nav aria-label="pagination">
<ol class="pagination post-pagination">
<li class="older">
<a href="/anarchy-autism/">
<i class="fa-solid fa-hand-point-left" aria-hidden="true"></i> anarchy autism
</a>
</li>
<li class="newer">
<a href="/leather-chest-harness/">
leather chest harness <i class="fa-solid fa-hand-point-right" aria-hidden="true"></i>
</a>
</li>
</ol>
</nav>
2026-02-20 08:36:56 -08:00
<hr>
<section class="related-posts">
<h2 id="related-posts">related posts</h2>
<ol id="postlist">
<li class="post">
<a class="postlink" href="/brookes-cuff-bracelets/">
<img src="/img/brooke-cuffs.jpg" alt="Olive green leather cuffs with silver spikes and a shearling lining." loading="lazy" decoding="async" width="900" height="1200">
<h2 id="brookes-cuff-bracelets">brooke&#39;s cuff bracelets</h2>
<ul class="postlist-tags">
<li>leather</li>
</ul>
</a>
</li>
<li class="post">
<a class="postlink" href="/mousie/">
<img src="/img/mousie.jpg" alt="A cat in a sunbeam snuggles a little leather mouse-shaped cat toy." loading="lazy" decoding="async" width="1000" height="1499">
<h2 id="mousie">mousie</h2>
<ul class="postlist-tags">
<li>leather</li>
</ul>
</a>
</li>
<li class="post">
<a class="postlink" href="/leather-keychains/">
<img src="/img/leather-keychains.jpg" alt="A picture of multiple leather keychains sitting on a wood table. Many of them are simple rectangle shapes with stitching around the edge; a few are odd wavy or geometric shapes. A few say things like &#39;MOM&#39; or &#39;EGG&#39;." loading="lazy" decoding="async" width="1000" height="1333">
<h2 id="leather-keychains">leather keychains</h2>
<ul class="postlist-tags">
<li>leather</li>
</ul>
</a>
</li>
</ol>
</section>
</heading-anchors>
</main>
<footer>
<ul>
<li>
<a href="/colophon" title="colophon" aria-label="colophon">
colophon
</a>
</li>
<li>
<a href="/" title="go home" aria-label="go home | hello hello from Lee Cattarin in 2026">
hello hello from Lee Cattarin in 2026</a>
</li>
<li>
<a href="https://heckin.technology/inherentlee/leecat.art" title="source code" aria-label="source code" target="_blank" rel="external">
src
</a>
</li>
</ul>
</footer>
2026-02-20 08:36:56 -08:00
<!-- This page `/leatherworking-favorites/` was built on 2026-02-20T16:35:28.464Z -->
<body>
</body></body>