1
0
forked from ctmesh/web

20 Commits

Author SHA1 Message Date
b23bff5d67 remove legacy wardrive app instead 2026-03-02 13:57:54 -05:00
8b500c4aea old wardrive app now legacy, reorder home for MeshCore prominence 2026-03-02 10:05:52 -05:00
ff5f94d9fd Fix dashes 2026-02-17 21:01:29 -05:00
183fad5ca4 Stage changes to MeshCore resources, mark old wardrive app as legacy, and change verbiage. Will hotlink to mobile apps once published on MeshMapper's website. 2026-02-17 20:57:05 -05:00
a7fdf8fea5 update wardrive apps, add Discord link centralized redirect, cosmetic fixes to external links 2026-02-10 19:02:34 -05:00
0fe6f5f757 fixes 2026-02-10 15:48:08 -05:00
627c970374 fixes 2026-02-10 15:46:37 -05:00
027b481290 mobile padding, external link arrows on resource pages 2026-02-10 15:35:33 -05:00
a386b37258 alignment of discord button contents 2026-02-10 15:21:56 -05:00
0a48f589e0 minor cosmetic 2026-02-10 14:20:17 -05:00
a6c3b70282 fix code block styling and copy button 2026-02-10 14:17:52 -05:00
89cdaf0791 add a small header on resources pages, forward/back chevron to resources/back buttons 2026-02-10 14:13:15 -05:00
81ea6a8005 slight margin increase between sections 2026-02-10 14:01:00 -05:00
a7dabace24 change footer text, add footer to resources pages 2026-02-10 13:52:24 -05:00
adf5e83991 add gitignore 2026-02-10 13:46:06 -05:00
e4527ce9b1 cleanup 2026-02-10 13:45:41 -05:00
6cc2f95fd4 maybe adjusted workflow to push to staging automatically 2026-02-10 13:40:00 -05:00
dad112a5f8 fix deploy workflow to not push our staging site to prod :D 2026-02-10 13:36:07 -05:00
bc23226733 changes & fixes. fewer buttons, fix scrolling issue with page top cut off, rejigger resources pages with resources on top, other minor cosmetics. 2026-02-10 13:33:37 -05:00
6acb31e2a9 Merge pull request 'Several improvements to the webpage with updated resources' (#1) from jared/web:feature/update-website into staging
Reviewed-on: https://git.ctmesh.org/ctmesh/web/pulls/1
2026-02-10 18:28:50 +00:00
6 changed files with 296 additions and 139 deletions

View File

@ -17,4 +17,4 @@ jobs:
with: with:
apiToken: ${{ secrets.CF_API_TOKEN }} apiToken: ${{ secrets.CF_API_TOKEN }}
accountId: ${{ secrets.CF_ACCOUNT_ID }} accountId: ${{ secrets.CF_ACCOUNT_ID }}
command: pages deploy /tmp/deploy --project-name=ctmesh-org command: pages deploy /tmp/deploy --project-name=ctmesh-org --branch=${{ github.ref_name }}

1
.gitignore vendored Normal file
View File

@ -0,0 +1 @@
.DS_Store

1
_redirects Normal file
View File

@ -0,0 +1 @@
/discord https://discord.gg/m4F328as3K 302

View File

@ -6,14 +6,14 @@
<meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover"> <meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover">
<!-- Site Description & Keywords --> <!-- Site Description & Keywords -->
<meta name="description" content="A Connecticut Meshtastic User Group. Join the local community to connect, share, and explore with fellow enthusiasts."> <meta name="description" content="A Connecticut mesh technologies user group. Join the local community to connect, share, and explore with fellow enthusiasts.">
<meta name="keywords" content="CT Mesh, Meshtastic, Connecticut, CT, community, user group, Discord, map"> <meta name="keywords" content="CT Mesh, Meshtastic, MeshCore, Connecticut, CT, community, mesh networking, user group, Discord, map">
<meta name="author" content="CT Mesh"> <meta name="author" content="CT Mesh">
<link rel="shortcut icon" type="image/x-icon" href="favicon.png?3"> <link rel="shortcut icon" type="image/x-icon" href="favicon.png?3">
<!-- Open Graph / Facebook --> <!-- Open Graph / Facebook -->
<meta property="og:title" content="CT Mesh"> <meta property="og:title" content="CT Mesh">
<meta property="og:description" content="A Connecticut Meshtastic User Group. Join the local community to connect, share, and explore with fellow enthusiasts."> <meta property="og:description" content="A Connecticut mesh technologies user group. Join the local community to connect, share, and explore with fellow enthusiasts.">
<meta property="og:image" content="favicon.png?3"> <meta property="og:image" content="favicon.png?3">
<meta property="og:url" content="https://ctmesh.org"> <meta property="og:url" content="https://ctmesh.org">
<meta property="og:type" content="website"> <meta property="og:type" content="website">
@ -21,7 +21,7 @@
<!-- Twitter --> <!-- Twitter -->
<meta name="twitter:card" content="summary_large_image"> <meta name="twitter:card" content="summary_large_image">
<meta name="twitter:title" content="CT Mesh"> <meta name="twitter:title" content="CT Mesh">
<meta name="twitter:description" content="A Connecticut Meshtastic User Group. Join the local community to connect, share, and explore with fellow enthusiasts."> <meta name="twitter:description" content="A Connecticut mesh technologies user group. Join the local community to connect, share, and explore with fellow enthusiasts.">
<meta name="twitter:image" content="favicon.png?3"> <meta name="twitter:image" content="favicon.png?3">
<!-- Fonts and Icons --> <!-- Fonts and Icons -->
@ -48,7 +48,7 @@
margin: 0; margin: 0;
padding: 0; padding: 0;
width: 100%; width: 100%;
height: 100%; min-height: 100%;
} }
body { body {
font-family: "Roboto", sans-serif; font-family: "Roboto", sans-serif;
@ -78,8 +78,8 @@
border-radius: 30px; border-radius: 30px;
padding: 3em 3em 2em 3em; padding: 3em 3em 2em 3em;
margin: 1em; margin: 1em;
width: min(100%, 900px); width: 90%;
max-width: 900px; max-width: 700px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.15); box-shadow: 0 0 10px rgba(0, 0, 0, 0.15);
color: #000000; color: #000000;
position: relative; position: relative;
@ -122,7 +122,7 @@
.btn { .btn {
display: flex; display: flex;
align-items: center; align-items: center;
gap: 8px; gap: 12px;
background-color: #67EA94; background-color: #67EA94;
color: #000000; color: #000000;
border: none; border: none;
@ -151,9 +151,48 @@
height: 30px; height: 30px;
filter: brightness(0); filter: brightness(0);
} }
.btn-discord { .btn-discord,
background-color: #7289da; .btn-discord:visited {
background-color: #5865F2;
color: #ffffff; color: #ffffff;
justify-content: center;
}
.btn-discord img {
filter: brightness(0) invert(1);
}
.btn-meshcore,
.btn-meshcore:visited {
background-color: #2B3A4E;
color: #ffffff;
}
.btn-meshcore img {
filter: brightness(0) invert(1);
}
a.btn[target="_blank"]::after {
content: "";
width: 16px;
height: 16px;
margin-left: auto;
background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' fill='none' stroke='%23000' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M3.5 8.5L8.5 3.5M5 3.5h3.5V7'/%3E%3C/svg%3E") no-repeat center;
background-size: contain;
flex-shrink: 0;
opacity: 0.4;
}
a.btn:not([target="_blank"])::after {
content: "";
width: 16px;
height: 16px;
margin-left: auto;
background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' fill='none' stroke='%23000' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M4 2.5L8.5 6L4 9.5'/%3E%3C/svg%3E") no-repeat center;
background-size: contain;
flex-shrink: 0;
opacity: 0.4;
}
.btn-discord::after {
display: none;
}
.btn-meshcore::after {
filter: invert(1) !important;
} }
.btn-group { .btn-group {
display: flex; display: flex;
@ -165,11 +204,11 @@
.btn-groups { .btn-groups {
display: flex; display: flex;
flex-direction: column; flex-direction: column;
gap: 1em; gap: 1.5em;
} }
.section-title { .section-title {
margin: 0.5em 0 0; margin: 0.5em 0 0;
padding-top: 0.75em; padding-top: 1em;
font-size: 1rem; font-size: 1rem;
text-transform: uppercase; text-transform: uppercase;
letter-spacing: 0.08em; letter-spacing: 0.08em;
@ -213,10 +252,7 @@
padding-top: calc(env(safe-area-inset-top, 1em)); padding-top: calc(env(safe-area-inset-top, 1em));
} }
.splash-box { .splash-box {
margin-top: 1em;
margin-bottom: 1em;
padding: 2em; padding: 2em;
min-width: 350px;
} }
.top-section { .top-section {
flex-direction: column; flex-direction: column;
@ -232,32 +268,26 @@
} }
.btn-group { .btn-group {
flex-direction: column; flex-direction: column;
align-items: stretch; align-items: center;
} }
.section-title { .section-title {
text-align: center; text-align: center;
} }
.btn { .btn {
width: 100%; width: 340px;
justify-content: center; max-width: 100%;
justify-content: flex-start;
padding: 0.8em 1em; padding: 0.8em 1em;
font-size: 16px; font-size: 16px;
text-align: center; text-align: left;
max-width: 100%;
flex: none; flex: none;
} }
.btn-text {
align-items: center;
}
} }
/* Further adjustments for devices with a viewport width of 480px or less */ /* Further adjustments for devices with a viewport width of 480px or less */
@media (max-width: 480px) { @media (max-width: 480px) {
.splash-box { .splash-box {
padding: 1.5em; padding: 1.5em;
margin: 1em;
width: 90%;
min-width: 250px;
} }
.logo { .logo {
width: 120px; width: 120px;
@ -282,58 +312,18 @@
<img src="logo_sm.png" alt="CT Mesh Logo" class="logo" /> <img src="logo_sm.png" alt="CT Mesh Logo" class="logo" />
<div class="text-content"> <div class="text-content">
<h1>CT Mesh</h1> <h1>CT Mesh</h1>
<p class="sub-header">Connecticut Meshtastic User Group</p> <p class="sub-header">Connecticut Mesh Technologies User Group</p>
<a href="mailto:noah@ctmesh.org" rel="nofollow noindex"><img src="email.svg" alt="Email" /></a> <a href="mailto:noah@ctmesh.org" rel="nofollow noindex"><img src="email.svg" alt="Email" /></a>
</div> </div>
</div> </div>
<div class="btn-groups"> <div class="btn-groups">
<div class="section"> <div class="section">
<div class="btn-group"> <div class="btn-group">
<a href="https://discord.gg/m4F328as3K" target="_blank" class="btn btn-discord"> <a href="/discord" target="_blank" class="btn btn-discord">
<img src="discord.svg" alt="Discord Icon" /> <img src="discord.svg" alt="Discord" />
<div class="btn-text"> <div class="btn-text">
Join our Discord Join our Discord
<small>Join the community</small> <small>Chat with the community</small>
</div>
</a>
</div>
</div>
<div class="section">
<p class="section-title">Meshtastic</p>
<div class="btn-group">
<a href="https://meshtastic.org/" target="_blank" class="btn">
<img src="meshtastic.svg" alt="Meshtastic Icon" />
<div class="btn-text">
Meshtastic
<small>Learn more!</small>
</div>
</a>
<a href="https://malla.ctmesh.org/" target="_blank" class="btn">
<img src="info.svg" alt="Info Icon" />
<div class="btn-text">
Web Dashboard
<small>Network metrics & analytics</small>
</div>
</a>
<a href="https://map.ctmesh.org/?lat=41.734429390721&lng=287.3501586914063&zoom=10" target="_blank" class="btn">
<img src="map.svg" alt="Map Icon" />
<div class="btn-text">
CT Map
<small>Nodes seen by CT Mesh</small>
</div>
</a>
<a href="https://meshtastic.liamcottle.net/?lat=26.58852714730864&lng=285.11718750000006&zoom=2" target="_blank" class="btn">
<img src="globe.svg" alt="Globe Icon" />
<div class="btn-text">
Global Map
<small>Nodes around the world</small>
</div>
</a>
<a href="resources.html" class="btn">
<img src="info.svg" alt="Info Icon" />
<div class="btn-text">
Meshtastic Resources
<small>Channels, MQTT, tools</small>
</div> </div>
</a> </a>
</div> </div>
@ -341,46 +331,58 @@
<div class="section"> <div class="section">
<p class="section-title">MeshCore</p> <p class="section-title">MeshCore</p>
<div class="btn-group"> <div class="btn-group">
<a href="https://meshcore.co.uk/" target="_blank" class="btn"> <a href="https://meshcore.co.uk/" target="_blank" class="btn btn-meshcore">
<img src="meshcore.svg" alt="MeshCore Logo" /> <img src="meshcore.svg" alt="MeshCore" />
<div class="btn-text"> <div class="btn-text">
Official MeshCore Website MeshCore
<small>Project website</small> <small>About the project</small>
</div> </div>
</a> </a>
<a href="https://meshcore-map.ctmesh.org/" target="_blank" class="btn"> <a href="https://meshcore-map.ctmesh.org/" target="_blank" class="btn btn-meshcore">
<img src="map.svg" alt="Map Icon" /> <img src="map.svg" alt="Map" />
<div class="btn-text"> <div class="btn-text">
MeshCore Map Node Map
<small>Live node map</small> <small>Live MeshCore nodes</small>
</div> </div>
</a> </a>
<a href="https://meshcore-wardrive.ctmesh.org/" target="_blank" class="btn"> <a href="meshcore-resources.html" class="btn btn-meshcore">
<img src="map.svg" alt="Map Icon" /> <img src="info.svg" alt="Guides & Tools" />
<div class="btn-text"> <div class="btn-text">
MeshCore Wardrive Guides & Tools
<small>Coverage maps</small> <small>Wardrive, MQTT, setup</small>
</div>
</a>
<a href="https://meshcore-wardrive.ctmesh.org/wardrive" target="_blank" class="btn">
<img src="wheel.svg" alt="Wheel Icon" />
<div class="btn-text">
Wardrive Contribution
<small>Upload wardrive data</small>
</div>
</a>
<a href="meshcore-resources.html" class="btn">
<img src="info.svg" alt="Info Icon" />
<div class="btn-text">
MeshCore Resources
<small>Tools and maps</small>
</div> </div>
</a> </a>
</div> </div>
</div> </div>
</div> </div>
<div class="section">
<p class="section-title">Meshtastic</p>
<div class="btn-group">
<a href="https://meshtastic.org/" target="_blank" class="btn">
<img src="meshtastic.svg" alt="Meshtastic" />
<div class="btn-text">
Meshtastic
<small>About the project</small>
</div>
</a>
<a href="https://map.ctmesh.org/?lat=41.734429390721&lng=287.3501586914063&zoom=10" target="_blank" class="btn">
<img src="map.svg" alt="Map" />
<div class="btn-text">
Node Map
<small>CT Mesh nodes</small>
</div>
</a>
<a href="meshtastic-resources.html" class="btn">
<img src="info.svg" alt="Guides & Tools" />
<div class="btn-text">
Guides & Tools
<small>Channels, MQTT, setup</small>
</div>
</a>
</div>
</div>
<footer class="site-footer"> <footer class="site-footer">
<p><a href="https://ctmesh.org/">CT Mesh</a> is a volunteer-run user group for <a href="https://meshtastic.org" target="_blank">Meshtastic</a> enthusiasts in Connecticut.</p> <p><a href="https://ctmesh.org/">CT Mesh</a> is a volunteer-run user group for mesh technology enthusiasts in Connecticut.</p>
<p><a href="https://creativecommons.org/licenses/by-sa/4.0/" target="_blank" rel="noopener">Content licensed CC BY-SA 4.0</a></p> <p><a href="https://creativecommons.org/licenses/by-sa/4.0/" target="_blank" rel="noopener">Content licensed CC BY-SA 4.0</a></p>
</footer> </footer>
</div> </div>

View File

@ -74,7 +74,7 @@
} }
.note { .note {
background: #F5F5F5; background: #F5F5F5;
border-left: 4px solid #67EA94; border-left: 4px solid #2B3A4E;
border-radius: 8px; border-radius: 8px;
padding: 0.75em 1em; padding: 0.75em 1em;
margin: 0.75em 0 0.5em; margin: 0.75em 0 0.5em;
@ -98,8 +98,8 @@
position: absolute; position: absolute;
top: 0.75em; top: 0.75em;
right: 0.75em; right: 0.75em;
background-color: #67EA94; background-color: #2B3A4E;
color: #000000; color: #ffffff;
border: none; border: none;
border-radius: 10px; border-radius: 10px;
padding: 0.4em 0.75em; padding: 0.4em 0.75em;
@ -112,18 +112,79 @@
align-items: center; align-items: center;
justify-content: center; justify-content: center;
gap: 8px; gap: 8px;
background-color: #67EA94; background-color: #2B3A4E;
color: #000000; color: #ffffff;
border: none; border: none;
padding: 0.75em 1.5em; padding: 0.75em 1.5em;
border-radius: 15px; border-radius: 999px;
cursor: pointer; cursor: pointer;
font-weight: bold; font-weight: bold;
font-size: 15px; font-size: 15px;
text-decoration: none; text-decoration: none;
} }
.back-link { .page-header {
display: flex;
align-items: center;
gap: 0.5em;
text-decoration: none;
margin-bottom: 1.5em;
}
.page-header img {
width: 44px;
height: auto;
}
.page-header span {
font-weight: bold;
font-size: 19px;
color: #2C2D3C;
}
.back-link,
.back-link:visited {
margin-top: 1.5em; margin-top: 1.5em;
color: #ffffff;
display: inline-flex;
align-items: center;
gap: 6px;
}
.back-link::before {
content: "";
width: 16px;
height: 16px;
background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' fill='none' stroke='%23000' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M8 2.5L3.5 6L8 9.5'/%3E%3C/svg%3E") no-repeat center;
background-size: contain;
flex-shrink: 0;
opacity: 0.4;
filter: invert(1);
}
a[target="_blank"]::after {
content: "";
display: inline-block;
width: 12px;
height: 12px;
vertical-align: middle;
background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' fill='none' stroke='%23000' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M3.5 8.5L8.5 3.5M5 3.5h3.5V7'/%3E%3C/svg%3E") no-repeat center;
background-size: contain;
opacity: 0.4;
text-decoration: underline;
}
.btn[target="_blank"]::after,
.copy-btn::after,
.site-footer a::after {
display: none;
}
.site-footer {
margin-top: 2em;
padding-top: 2em;
text-align: center;
font-size: 0.875rem;
color: #2C2D3C;
border-top: 1px solid #ccc;
}
.site-footer a {
text-decoration: none;
}
.site-footer a:hover {
text-decoration: underline;
} }
@media (max-width: 800px) { @media (max-width: 800px) {
body { body {
@ -149,21 +210,25 @@
<body> <body>
<div class="overlay"></div> <div class="overlay"></div>
<div class="content-box"> <div class="content-box">
<a href="index.html" class="page-header">
<img src="logo_sm.png" alt="CT Mesh" />
<span>CT Mesh</span>
</a>
<h1>MeshCore Resources</h1> <h1>MeshCore Resources</h1>
<h2>Community-run Web Tools</h2> <h2>Community-run Web Tools</h2>
<div class="community-tools"> <div class="community-tools">
<p><em>These tools use data reported to our MQTT server by nodes across the state.</em></p> <p><em>These tools use data reported to our MQTT server by nodes across the state.</em></p>
<ul> <ul>
<li><a href="https://meshcore-map.ctmesh.org/" target="_blank">MeshCore Map</a> <strong>NEW!</strong> - live map showing MeshCore nodes</li> <li><a href="https://meshcore-map.ctmesh.org/" target="_blank">MeshCore Map</a> <strong>NEW!</strong> &ndash; live map showing MeshCore nodes</li>
<li><a href="https://meshcore-wardrive.ctmesh.org/" target="_blank">MeshCore Wardriving Map</a> <strong>NEW!</strong> - coverage maps for MeshCore (you can also contribute!). <em>Note: a new app is in testing and may supersede this.</em></li> <li><a href="https://bdl.meshmapper.net/" target="_blank">MeshMapper</a> <strong>NEW!</strong> &ndash; coverage maps for MeshCore. Contribute via <a href="https://apps.apple.com/us/app/meshmapper/id6758073991" target="_blank">iOS</a> and <a href="https://play.google.com/store/apps/details?id=net.meshmapper.app" target="_blank">Android</a> mobile apps!</li>
</ul> </ul>
</div> </div>
<h2>Official Links</h2> <h2>Official Links</h2>
<p><a href="https://meshcore.co.uk/" target="_blank">meshcore.co.uk</a></p> <p><a href="https://meshcore.co.uk/" target="_blank">meshcore.co.uk</a></p>
<p><a href="https://flasher.meshcore.co.uk/" target="_blank">flasher.meshcore.co.uk</a></p> <p><a href="https://flasher.meshcore.co.uk/" target="_blank">flasher.meshcore.co.uk</a></p>
<div class="note"><strong>Note:</strong> the flasher requires WebSerial or Web Bluetooth support in your browser.</div> <div class="note"><strong>Note:</strong> the flasher requires WebSerial or Web Bluetooth support in your browser</div>
<h2>MQTT</h2> <h2>MQTT</h2>
<p>Our MQTT broker is <em>uplink-only</em> and designed for fixed nodes across the state to serve as gateway nodes. Its purpose is not to bridge gaps or extend mesh coverage, but to report local traffic to our own web-based tools for analytical data and metrics to assess the mesh's performance. <strong>This role is best suited for stable, well-placed nodes with reliable coverage.</strong></p> <p>Our MQTT broker is <em>uplink-only</em> and designed for fixed nodes across the state to serve as gateway nodes. Its purpose is not to bridge gaps or extend mesh coverage, but to report local traffic to our own web-based tools for analytical data and metrics to assess the mesh's performance. <strong>This role is best suited for stable, well-placed nodes with reliable coverage.</strong></p>
@ -181,6 +246,10 @@ MCTOMQTT_MQTT3_PASSWORD=large4cats</pre>
</div> </div>
<a class="btn back-link" href="index.html">Back to CT Mesh</a> <a class="btn back-link" href="index.html">Back to CT Mesh</a>
<footer class="site-footer">
<p><a href="https://ctmesh.org/">CT Mesh</a> is a volunteer-run user group for mesh technology enthusiasts in Connecticut.</p>
<p><a href="https://creativecommons.org/licenses/by-sa/4.0/" target="_blank" rel="noopener">Content licensed CC BY-SA 4.0</a></p>
</footer>
</div> </div>
<script> <script>
const copyButtons = document.querySelectorAll("[data-copy-target]"); const copyButtons = document.querySelectorAll("[data-copy-target]");

View File

@ -74,14 +74,17 @@
padding: 0; padding: 0;
line-height: 1.5; line-height: 1.5;
} }
.settings { .code-block {
background: #F5F5F5; background: #F5F5F5;
border-radius: 12px; border-radius: 12px;
padding: 1em; padding: 1em;
border: 1px solid #D0D0D0; border: 1px solid #D0D0D0;
margin: 0.75em 0; margin: 0.75em 0;
position: relative;
} }
.settings code { .code-block pre {
margin: 0;
white-space: pre-wrap;
font-family: monospace; font-family: monospace;
font-size: 0.95em; font-size: 0.95em;
} }
@ -97,6 +100,13 @@
margin-left: 0.5em; margin-left: 0.5em;
vertical-align: middle; vertical-align: middle;
} }
.code-block .copy-btn {
position: absolute;
top: 0.75em;
right: 0.75em;
padding: 0.4em 0.75em;
margin-left: 0;
}
.btn { .btn {
display: inline-flex; display: inline-flex;
align-items: center; align-items: center;
@ -106,7 +116,7 @@
color: #000000; color: #000000;
border: none; border: none;
padding: 0.75em 1.5em; padding: 0.75em 1.5em;
border-radius: 15px; border-radius: 999px;
cursor: pointer; cursor: pointer;
font-weight: bold; font-weight: bold;
font-size: 15px; font-size: 15px;
@ -122,8 +132,74 @@
.community-tools li { .community-tools li {
margin-bottom: 0.5em; margin-bottom: 0.5em;
} }
.note {
background: #F5F5F5;
border-left: 4px solid #67EA94;
border-radius: 8px;
padding: 0.75em 1em;
margin: 0.75em 0 0.5em;
font-size: 0.95em;
}
.page-header {
display: flex;
align-items: center;
gap: 0.5em;
text-decoration: none;
margin-bottom: 1.5em;
}
.page-header img {
width: 44px;
height: auto;
}
.page-header span {
font-weight: bold;
font-size: 19px;
color: #2C2D3C;
}
.back-link { .back-link {
margin-top: 1.5em; margin-top: 1.5em;
display: inline-flex;
align-items: center;
gap: 6px;
}
.back-link::before {
content: "";
width: 16px;
height: 16px;
background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' fill='none' stroke='%23000' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M8 2.5L3.5 6L8 9.5'/%3E%3C/svg%3E") no-repeat center;
background-size: contain;
flex-shrink: 0;
opacity: 0.4;
}
a[target="_blank"]::after {
content: "";
display: inline-block;
width: 12px;
height: 12px;
vertical-align: middle;
background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' fill='none' stroke='%23000' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M3.5 8.5L8.5 3.5M5 3.5h3.5V7'/%3E%3C/svg%3E") no-repeat center;
background-size: contain;
opacity: 0.4;
text-decoration: underline;
}
.btn[target="_blank"]::after,
.copy-btn::after,
.site-footer a::after {
display: none;
}
.site-footer {
margin-top: 2em;
padding-top: 2em;
text-align: center;
font-size: 0.875rem;
color: #2C2D3C;
border-top: 1px solid #ccc;
}
.site-footer a {
text-decoration: none;
}
.site-footer a:hover {
text-decoration: underline;
} }
@media (max-width: 800px) { @media (max-width: 800px) {
body { body {
@ -149,8 +225,24 @@
<body> <body>
<div class="overlay"></div> <div class="overlay"></div>
<div class="content-box"> <div class="content-box">
<a href="index.html" class="page-header">
<img src="logo_sm.png" alt="CT Mesh" />
<span>CT Mesh</span>
</a>
<h1>Meshtastic Resources</h1> <h1>Meshtastic Resources</h1>
<h2>Community-run Web Tools</h2>
<div class="community-tools">
<p><em>These tools use data reported to our MQTT server by nodes across the state.</em></p>
<ul>
<li><a href="https://map.ctmesh.org/?lat=41.6558113360196&lng=287.3377990722657&zoom=10" target="_blank">Meshtastic Map</a> - live map of Meshtastic nodes CT Mesh has heard</li>
<li><a href="https://meshtastic.liamcottle.net/?lat=26.58852714730864&lng=285.11718750000006&zoom=2" target="_blank">Global Map</a> - Meshtastic nodes around the world</li>
<li><a href="https://malla.ctmesh.org/" target="_blank">Malla</a> - deeper packet-level metrics and mesh performance insights fed from MQTT</li>
<li><a href="https://potato.ctmesh.org/" target="_blank">PotatoMesh</a> <strong>NEW!</strong> - packet, chat, node list, and map fed from RF on Box Mountain</li>
<li><a href="https://meshinfo.ctmesh.org/" target="_blank">MeshInfo</a> <em>legacy, partially broken</em> - MQTT gateway setup info, secondary map, graphs, message history, etc.</li>
</ul>
</div>
<h2>Mesh Channels</h2> <h2>Mesh Channels</h2>
<h3>Default (Primary) Channel</h3> <h3>Default (Primary) Channel</h3>
<p><em>Most CT chatter occurs on the default LongFast channel.</em></p> <p><em>Most CT chatter occurs on the default LongFast channel.</em></p>
@ -167,40 +259,32 @@
<p>Our MQTT broker is <em>uplink-only</em> and designed for fixed nodes across the state to serve as gateway nodes. Its purpose is not to bridge gaps or extend mesh coverage, but to report local traffic to our own <a href="https://map.ctmesh.org" target="_blank">map</a> and other web-based tools for analytical data and metrics to assess the mesh's performance. <strong>This role is best suited for stable, well-placed nodes with reliable coverage.</strong> If that describes your setup, follow the steps at on <a href="https://meshinfo.ctmesh.org/" target="_blank">this page</a> to get set up.</p> <p>Our MQTT broker is <em>uplink-only</em> and designed for fixed nodes across the state to serve as gateway nodes. Its purpose is not to bridge gaps or extend mesh coverage, but to report local traffic to our own <a href="https://map.ctmesh.org" target="_blank">map</a> and other web-based tools for analytical data and metrics to assess the mesh's performance. <strong>This role is best suited for stable, well-placed nodes with reliable coverage.</strong> If that describes your setup, follow the steps at on <a href="https://meshinfo.ctmesh.org/" target="_blank">this page</a> to get set up.</p>
<h3>Key Settings</h3> <h3>Key Settings</h3>
<div class="settings"> <div class="code-block">
<p>MQTT &gt; Enabled &gt; ON</p> <pre id="meshtastic-mqtt">MQTT > Enabled > ON
<p>MQTT &gt; Encryption Enabled &gt; ON</p> MQTT > Encryption Enabled > ON
<p>MQTT &gt; Map Report &gt; OFF</p> MQTT > Map Report > OFF
<p>MQTT &gt; Root Topic &gt; <code>msh/US/CT</code></p> MQTT > Root Topic > msh/US/CT
<p>MQTT &gt; Address &gt; <code>mqtt.ctmesh.org</code></p> MQTT > Address > mqtt.ctmesh.org
<p>MQTT &gt; Username &gt; <code>meshdev</code></p> MQTT > Username > meshdev
<p>MQTT &gt; Password &gt; <code>large4cats</code></p> MQTT > Password > large4cats
<p>MQTT &gt; TLS Enabled &gt; OFF</p> MQTT > TLS Enabled > OFF
<p>Channels &gt; Primary Channel &gt; Positions Enabled &gt; ON</p> Channels > Primary Channel > Positions Enabled > ON
<p>Channels &gt; Primary Channel &gt; Approximate Location &gt; (set as desired)</p> Channels > Primary Channel > Approximate Location > (set as desired)
<p>Channels &gt; Primary Channel &gt; MQTT Uplink &gt; ON</p> Channels > Primary Channel > MQTT Uplink > ON
<p>Channels &gt; Primary Channel &gt; MQTT Downlink &gt; OFF</p> Channels > Primary Channel > MQTT Downlink > OFF
<p>Settings &gt; Modules &gt; Neighbor Info &gt; ON</p> Settings > Modules > Neighbor Info > ON
<p>LoRa &gt; Ok to MQTT &gt; ON</p> LoRa > Ok to MQTT > ON</pre>
</div>
<p><strong>Note:</strong> CT Mesh's MQTT server is bridged and uplinks to the MQTT servers for both <a href="https://meshtastic.liamcottle.net" target="_blank">meshtastic.liamcottle.net</a> and <a href="https://meshmap.net" target="_blank">meshmap.net</a>.</p>
<h2>Community-run Web Tools</h2>
<div class="community-tools">
<p><em>These tools use data reported to our MQTT server by nodes across the state.</em></p>
<ul>
<li><a href="https://map.ctmesh.org/?lat=41.6558113360196&lng=287.3377990722657&zoom=10" target="_blank">Meshtastic Map</a> - live map of Meshtastic nodes CT Mesh has heard</li>
<li><a href="https://malla.ctmesh.org/" target="_blank">Malla</a> - deeper packet-level metrics and mesh performance insights fed from MQTT</li>
<li><a href="https://potato.ctmesh.org/" target="_blank">PotatoMesh</a> <strong>NEW!</strong> - packet, chat, node list, and map fed from RF on Box Mountain</li>
<li><a href="https://meshinfo.ctmesh.org/" target="_blank">MeshInfo</a> <em>legacy, partially broken</em> - MQTT gateway setup info, secondary map, graphs, message history, etc.</li>
</ul>
</div> </div>
<div class="note"><strong>Note:</strong> CT Mesh's MQTT server is bridged and uplinks to the MQTT servers for both <a href="https://meshtastic.liamcottle.net" target="_blank">meshtastic.liamcottle.net</a> and <a href="https://meshmap.net" target="_blank">meshmap.net</a></div>
<h2>Infrastructure Nodes</h2> <h2>Infrastructure Nodes</h2>
<p><strong>Important:</strong> Infrastructure roles like <code>ROUTER</code>, <code>REPEATER</code>, <code>ROUTER_CLIENT</code>, or <code>ROUTER_LATE</code> are rarely appropriate. Unless your node is sitting on top of one of the tallest buildings in Hartford with clear line-of-sight across the region, using these roles will hurt more than help. For almost everyone, the correct choice is <code>CLIENT</code>. If you think you've got a node that truly warrants an infrastructure role, reach out first - we'd rather make sure it benefits the mesh than inadvertently weakens it.</p> <p><strong>Important:</strong> Infrastructure roles like <code>ROUTER</code>, <code>REPEATER</code>, <code>ROUTER_CLIENT</code>, or <code>ROUTER_LATE</code> are rarely appropriate. Unless your node is sitting on top of one of the tallest buildings in Hartford with clear line-of-sight across the region, using these roles will hurt more than help. For almost everyone, the correct choice is <code>CLIENT</code>. If you think you've got a node that truly warrants an infrastructure role, reach out first - we'd rather make sure it benefits the mesh than inadvertently weakens it.</p>
<a class="btn back-link" href="index.html">Back to CT Mesh</a> <a class="btn back-link" href="index.html">Back to CT Mesh</a>
<footer class="site-footer">
<p><a href="https://ctmesh.org/">CT Mesh</a> is a volunteer-run user group for mesh technology enthusiasts in Connecticut.</p>
<p><a href="https://creativecommons.org/licenses/by-sa/4.0/" target="_blank" rel="noopener">Content licensed CC BY-SA 4.0</a></p>
</footer>
</div> </div>
<script> <script>
const copyButtons = document.querySelectorAll("[data-copy-target]"); const copyButtons = document.querySelectorAll("[data-copy-target]");