Add new homepage: top animation and first block

This commit is contained in:
Daniele Tonon
2024-04-05 13:34:24 +02:00
parent 1af2550e9f
commit bf2ca24a41
26 changed files with 504 additions and 290 deletions

245
about.templ Normal file
View File

@@ -0,0 +1,245 @@
package main
templ aboutTemplate(params AboutParams) {
<!DOCTYPE html>
<html class="theme--default font-light">
<meta charset="UTF-8"/>
<head>
<title>njump - the nostr static gateway</title>
<meta name="description" content=""/>
@headCommonTemplate(params.HeadParams)
</head>
<body class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black">
@topTemplate(params.HeadParams)
<div class="mx-auto sm:mt-8 block px-4 sm:flex sm:items-center sm:justify-center sm:px-0">
<div class="w-full max-w-screen-2xl justify-between gap-10 overflow-visible print:w-full sm:flex sm:w-11/12 sm:px-4 md:w-10/12 lg:w-9/12">
<div>
<h2 class="text-2xl text-strongpink">What is njump?</h2>
<p class="my-3 leading-5">
<i>njump</i> is a HTTP
<a class="underline" href="https://github.com/nostr-protocol/nostr">
Nostr
</a>
gateway that allows you to browse profiles, notes and relays; it is
an easy way to preview a resource and then open it with your
preferred client. The typical use of <i>njump</i> is to share a
resource outside the Nostr world, where the
<code>nostr:</code> schema is not (yet) working.
</p>
<p class="my-3 leading-5">
<i>njump</i> currently lives under { s.Domain }, you can reach it
appending a Nostr
<a
class="underline"
href="https://github.com/nostr-protocol/nips/blob/master/19.md"
>
NIP-19
</a>
entity (<code>npub</code>, <code>nevent</code>, <code>naddr</code>,
etc) after the domain:
<span class="rounded bg-lavender px-1 dark:bg-garnet">
{ s.Domain }/&lt;nip-19-entity&gt;
</span>.
</p>
<p class="my-3 leading-5">
For example, here's
<a
class="underline"
href="/npub1sn0wdenkukak0d9dfczzeacvhkrgz92ak56egt7vdgzn8pv2wfqqhrjdv9"
>
a user profile
</a>,
<a
class="underline"
href="/nevent1qqstnl4ddmhc0kzqpj7p543pvq9nvppc4laewc9x5ppucz7aagsa4dspzemhxue69uhhyetvv9ujumn0wd68ytnzv9hxgqgewaehxw309ac8junpd45kgtnxd9shg6npvchxxmmdqyv8wumn8ghj7un9d3shjtnndehhyapwwdhkx6tpdsds02v2"
>
a note
</a>
and a
<a
class="underline"
href="/naddr1qqxnzd3cxqmrzv3exgmr2wfeqy08wumn8ghj7mn0wd68yttsw43zuam9d3kx7unyv4ezumn9wshszyrhwden5te0dehhxarj9ekk7mf0qy88wumn8ghj7mn0wvhxcmmv9uq3zamnwvaz7tmwdaehgu3wwa5kuef0qy2hwumn8ghj7un9d3shjtnwdaehgu3wvfnj7q3qdergggklka99wwrs92yz8wdjs952h2ux2ha2ed598ngwu9w7a6fsxpqqqp65wy2vhhv"
>
long blog post
</a>
.
</p>
<h2 class="text-xl text-strongpink">
Try it now, jump to some Nostr content
</h2>
<div
class="my-3 mb-8 rounded-lg bg-zinc-100 p-4 pb-3 dark:bg-neutral-900 sm:p-6 sm:pb-4"
>
<form
_="on submit halt the event's default then go to url `/${event.target.code.value}`"
>
<div
class="flex flex-wrap items-center justify-center sm:flex-nowrap sm:justify-normal"
>
<div class="mb-1.5 text-xl sm:mb-0">{ s.Domain }/</div>
<input
name="code"
placeholder="paste a npub / nprofile / nevent / ..."
autofocus
class="ml-0 w-full basis-full rounded-lg border-0 bg-white p-2 text-base text-gray-700 placeholder:text-gray-300 focus:outline-0 dark:bg-zinc-900 dark:text-neutral-50 dark:placeholder:text-gray-400 sm:ml-1 sm:basis-11/12 sm:rounded-s-lg"
/>
<button
class="ml-0 w-full basis-full rounded-lg border-0 bg-strongpink p-2 text-base uppercase text-white sm:-ml-4 sm:basis-2/12 sm:rounded-s-lg"
>
View
</button>
</div>
</form>
<div class="mt-3 text-center text-sm sm:mt-1 sm:text-left">
or pick
<a
class="underline"
href="/random"
_="on click halt the event then fetch /random with method:'POST' then tell <input[name='code'] /> set @value to result"
>
some random content
</a>
</div>
</div>
<p class="my-3 leading-5">
There are several reasons to choose <i>njump</i> when sharing Nostr
content outside of Nostr:
</p>
<h2 class="mt-7 text-2xl text-strongpink">Clean, fast and solid</h2>
<p class="my-3 leading-5">
Pages by <i>njump</i> are extremely lightweight and fast to load
because there isn't any client side javascript involved; they are
minimalistic with the right attention to typography, focusing the
content without unnecessary details. Furthermore they are cached, so
when sharing a page you can expect the other part will load it
without any glitch in a fraction of second: the perfect tool to
onboard new users!
</p>
<h2 class="mt-7 text-2xl text-strongpink">Good preview</h2>
<p class="my-3 leading-5">
<i>njump</i> renders everything on the server-side, so it is able to
generate useful rich previews that work on Telegram, Discord,
Twitter and other places.
</p>
<p class="my-3 leading-5">
When opening the URL directly in a browser, visitors will find
referenced content like images, video and links to referenced Nostr
events displayed in a simple but effective way. It shows the note
parent, allowing the visitor to follow it up and it has custom CSS for
printing or exporting to PDF.
</p>
<h2 class="mt-7 text-2xl text-strongpink">Cooperative (jump-out)</h2>
<p class="my-3 leading-5">
<i>njump</i> is not interested capturing users at all, on the
contrary it invites them to "jump" to the Nostr resource by picking
from a list of web clients or with a <code>nostr:</code> prefix for native
clients. It even remembers the most used one for each visitor and
puts it on the top for fast clicking or tap.
</p>
<p class="my-3 leading-5">
<a class="underline" href="https://github.com/nostr-protocol/nips/blob/master/89.md">NIP-89</a>
support coming!
</p>
<h2 class="mt-7 text-2xl text-strongpink">
Search friendly (jump-in)
</h2>
<p class="my-3 leading-5">
This is crucial: <i>njump</i> pages are static so search engines can
index them, this means that <i>njump</i> can help others to discover
great content on Nostr, jump in and join us! <i>njump</i> is the
only nostr resource that has this explicit goal, if you care that a
good note can be found online use <i>njump</i> to share it, this way
you also help Nostr flourish.
</p>
<h2 class="mt-7 text-2xl text-strongpink">Share NIP-05 profiles</h2>
<p class="my-3 leading-5">
Now you can share your own profile with a pretty
<a
class="underline"
href="https://github.com/nostr-protocol/nips/blob/master/05.md"
>
NIP-05
</a>
inspired permalink:
<span class="rounded bg-lavender px-1 dark:bg-garnet">
{ s.Domain }/&lt;nip-05&gt;
</span>
, for example:
<a class="underline" href="/nvk.org">https://{ s.Domain }/nvk.org</a>
or
<a class="underline" href="/mike@mikedilger.com">
https://{ s.Domain }/mike@mikedilger.com
</a>
.
</p>
<p class="my-3 leading-5">
A profile shows the basic metadata infos, the used "outbox" relays
and the last notes.
</p>
<h2 class="mt-7 text-2xl text-strongpink">
Share on Twitter and Telegram
</h2>
<p class="my-3 leading-5">
Now you can quickly and effortlessly share Nostr notes on Twitter
and Telegram, and maybe on many other "social platforms": just drop
a link, and njump will render the note text using the preview image
as a canvas, to maximize the sharing experience and utility.
<br/>
On Telegram we have also the Instant View to access long content
in-app!
</p>
<h2 class="mt-7 text-2xl text-strongpink">Relays view</h2>
<p class="my-3 leading-5">
You can have a view of the last content posted to a relay using
<span class="rounded bg-lavender px-1 dark:bg-garnet">
{ s.Domain }/r/&lt;relay-host&gt;
</span>
, for example:
<a class="underline" href="/r/nostr.wine">
https://{ s.Domain }/r/nostr.wine
</a>
</p>
<p class="my-3 leading-5">
Some basic infos (
<a
href="https://github.com/nostr-protocol/nips/blob/master/11.md"
>
NIP-11
</a>
) are available; We hope operators will start to make them more
personal and informative so users can have a way to evaluate if/when
to join a relay.
</p>
<h2 class="mt-7 text-2xl text-strongpink">Website widgets</h2>
<div class="my-3 leading-5">
You can embed notes, long form contents and profiles in a web page
with a simple script:
<br/>
<span class="rounded bg-lavender px-1 dark:bg-garnet">
&lt;script src="https://{ s.Domain }/embed/&lt;nip-19-entity&gt;"
/&gt;
</span>
<div class="mt-4 gap-8 sm:flex">
<div class="mb-4 flex-auto sm:mb-0">
<script src="/embed/npub1sn0wdenkukak0d9dfczzeacvhkrgz92ak56egt7vdgzn8pv2wfqqhrjdv9"></script>
</div>
<div class="flex-auto">
<script src="/embed/naddr1qqxnzd3cxqmrzv3exgmr2wfeqy08wumn8ghj7mn0wd68yttsw43zuam9d3kx7unyv4ezumn9wshszyrhwden5te0dehhxarj9ekk7mf0qy88wumn8ghj7mn0wvhxcmmv9uq3zamnwvaz7tmwdaehgu3wwa5kuef0qy2hwumn8ghj7un9d3shjtnwdaehgu3wvfnj7q3qdergggklka99wwrs92yz8wdjs952h2ux2ha2ed598ngwu9w7a6fsxpqqqp65wy2vhhv"></script>
</div>
</div>
</div>
<h2 class="mt-7 text-2xl text-strongpink">Inspector tool</h2>
<p class="my-3 leading-5">
You know, we are all programmers, including our moms, so for every
<i>njump</i> page you can toggle the "Show more details" switch and
inspect the full event JSON. Without installing other tools (like
<a class="underline" href="https://github.com/fiatjaf/nak">nak</a>)
this is probably the fastest way to access that.
</p>
</div>
</div>
</div>
@footerTemplate()
</body>
</html>
}

View File

@@ -11,7 +11,7 @@ templ archiveTemplate(params ArchivePageParams) {
@headCommonTemplate(params.HeadParams) @headCommonTemplate(params.HeadParams)
</head> </head>
<body class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black"> <body class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black">
@topTemplate() @topTemplate(params.HeadParams)
<div class="mx-auto block px-4 sm:flex sm:items-center sm:justify-center sm:px-0"> <div class="mx-auto block px-4 sm:flex sm:items-center sm:justify-center sm:px-0">
<div class="w-full max-w-screen-2xl gap-10 overflow-visible print:w-full sm:flex sm:w-11/12 sm:px-4 md:w-10/12 lg:w-9/12 lg:gap-48vw"> <div class="w-full max-w-screen-2xl gap-10 overflow-visible print:w-full sm:flex sm:w-11/12 sm:px-4 md:w-10/12 lg:w-9/12 lg:gap-48vw">
<div class="relative top-auto flex basis-1/5 sm:max-w-[20%] items-center self-start sm:sticky sm:top-8 sm:mt-8 sm:block sm:items-start"> <div class="relative top-auto flex basis-1/5 sm:max-w-[20%] items-center self-start sm:sticky sm:top-8 sm:mt-8 sm:block sm:items-start">

View File

@@ -24,4 +24,16 @@
margin: 1cm 3cm; margin: 1cm 3cm;
} }
} }
@keyframes blink {
0% { opacity: 1; }
50% { opacity: 0; }
100% { opacity: 1; }
}
/* Apply the animation to the cursor */
.typewriter-cursor {
animation: blink 1s infinite;
color: rgb(222, 222, 222);
}
} }

View File

@@ -11,7 +11,7 @@ templ errorTemplate(params ErrorPageParams) {
<body <body
class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black" class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black"
> >
@topTemplate() @topTemplate(params.HeadParams)
<div class="mx-auto mt-12 w-10/12 text-center lg:w-9/12"> <div class="mx-auto mt-12 w-10/12 text-center lg:w-9/12">
<div class="mx-auto w-4/5 sm:w-3/5"> <div class="mx-auto w-4/5 sm:w-3/5">
<div class="mt-4 text-2xl leading-6"> <div class="mt-4 text-2xl leading-6">

View File

@@ -17,7 +17,7 @@ templ eventPageTemplate(
@headCommonTemplate(head) @headCommonTemplate(head)
</head> </head>
<body class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black"> <body class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black">
@topTemplate() @topTemplate(head)
<div class="mx-auto px-4 sm:flex sm:items-center sm:justify-center sm:px-0"> <div class="mx-auto px-4 sm:flex sm:items-center sm:justify-center sm:px-0">
<div class="w-full max-w-screen-2xl justify-between gap-10 overflow-visible print:w-full sm:flex sm:w-11/12 sm:px-4 md:w-10/12 lg:w-9/12 lg:gap-48vw"> <div class="w-full max-w-screen-2xl justify-between gap-10 overflow-visible print:w-full sm:flex sm:w-11/12 sm:px-4 md:w-10/12 lg:w-9/12 lg:gap-48vw">
<div class="w-full break-words print:w-full sm:w-3/4"> <div class="w-full break-words print:w-full sm:w-3/4">

View File

@@ -1,245 +1,163 @@
package main package main
templ homepageTemplate(params HomePageParams) { templ homepageTemplate(params HomePageParams) {
<!DOCTYPE html> <!doctype html>
<html class="theme--default font-light"> <html class="theme--default font-light">
<meta charset="UTF-8"/> <meta charset="UTF-8" />
<head> <head>
<title>njump - the nostr static gateway</title> <title>njump - the nostr static gateway</title>
<meta name="description" content=""/> <meta name="description" content="" />
@headCommonTemplate(params.HeadParams)
</head> @headCommonTemplate(params.HeadParams)
<body class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black"> <script src="https://unpkg.com/typewriter-effect@latest/dist/core.js"></script>
@topTemplate() </head>
<div class="mx-auto sm:mt-8 block px-4 sm:flex sm:items-center sm:justify-center sm:px-0">
<div class="flex w-full max-w-screen-xl justify-between gap-10 overflow-visible px-1 print:w-full sm:w-9/12 xl:w-3/5"> <body
<div> class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black"
<h2 class="text-2xl text-strongpink">What is njump?</h2> >
<p class="my-3 leading-5"> @topTemplate(params.HeadParams)
<i>njump</i> is a HTTP <div
<a class="underline" href="https://github.com/nostr-protocol/nostr"> class="mx-auto block px-4 sm:flex sm:flex-col sm:items-center sm:justify-center sm:px-0"
Nostr >
</a> <div
gateway that allows you to browse profiles, notes and relays; it is class="sm:w-[72%] print:w-full"
an easy way to preview a resource and then open it with your >
preferred client. The typical use of <i>njump</i> is to share a
resource outside the Nostr world, where the <!-- Title nimation -->
<code>nostr:</code> schema is not (yet) working. <div class="mb-10 sm:mb-20 mt-8 border-l-[0.8rem] border-strongpink pl-4">
</p> <h1 class="font-bold">
<p class="my-3 leading-5"> <div class="text-[3.5em] sm:text-[4em] leading-[1em] text-neutral-300">
<i>njump</i> currently lives under { s.Domain }, you can reach it NOSTR <span class="text-neutral-400">IS</span>
appending a Nostr </div>
<a <div class="text-[3.5em] sm:text-[5em] leading-[1em] break-words" id="tw"></div>
class="underline" <script>
href="https://github.com/nostr-protocol/nips/blob/master/19.md" var tw = document.getElementById('tw')
> new Typewriter(tw, {
NIP-19 strings: [
</a> '',
entity (<code>npub</code>, <code>nevent</code>, <code>naddr</code>, '',
etc) after the domain: 'A PROTOCOL',
<span class="rounded bg-lavender px-1 dark:bg-garnet"> 'MANY PLATFORMS',
{ s.Domain }/&lt;nip-19-entity&gt; 'FREEDOM',
</span>. 'A SOCIAL PLACE',
</p> 'REALLY WEIRD',
<p class="my-3 leading-5"> 'ENERGY',
For example, here's 'UNIVERSAL',
<a 'YOUR HAPPINESS',
class="underline" 'PERMISSIONLESS',
href="/npub1sn0wdenkukak0d9dfczzeacvhkrgz92ak56egt7vdgzn8pv2wfqqhrjdv9" 'HEALTHY',
> 'UNCENSORED',
a user profile 'COOL TO DEVELOP',
</a>, 'YOUR NEXT IDEA',
<a '.......'
class="underline" ],
href="/nevent1qqstnl4ddmhc0kzqpj7p543pvq9nvppc4laewc9x5ppucz7aagsa4dspzemhxue69uhhyetvv9ujumn0wd68ytnzv9hxgqgewaehxw309ac8junpd45kgtnxd9shg6npvchxxmmdqyv8wumn8ghj7un9d3shjtnndehhyapwwdhkx6tpdsds02v2" autoStart: true,
> loop: true,
a note cursorClassName: 'typewriter-cursor'
</a> })
and a </script>
<a </h1>
class="underline" </div>
href="/naddr1qqxnzd3cxqmrzv3exgmr2wfeqy08wumn8ghj7mn0wd68yttsw43zuam9d3kx7unyv4ezumn9wshszyrhwden5te0dehhxarj9ekk7mf0qy88wumn8ghj7mn0wvhxcmmv9uq3zamnwvaz7tmwdaehgu3wwa5kuef0qy2hwumn8ghj7un9d3shjtnwdaehgu3wvfnj7q3qdergggklka99wwrs92yz8wdjs952h2ux2ha2ed598ngwu9w7a6fsxpqqqp65wy2vhhv" </div>
>
long blog post <div
</a> class="sm:w-[72%] sm:gap-10 print:w-full font-extralight"
. >
</p> <!-- Intro -->
<h2 class="text-xl text-strongpink"> <div class="sm:flex sm:gap-20">
Try it now, jump to some Nostr content <div>
</h2> <h2 class="text-4xl text-strongpink">Freedom at risk</h2>
<div <div class="text-xl mt-2">The original principles of the internet, rooted in decentralization, user empowerment, openness, collaboration, and freedom of expression, were not designed to be dominated by centralized control systems led by governments and capitalist markets.</div>
class="my-3 mb-8 rounded-lg bg-zinc-100 p-4 pb-3 dark:bg-neutral-900 sm:p-6 sm:pb-4" <div class="mt-2 text-neutral-500 dark:text-neutral-300">Current social networks such as Twitter, Mastodon, and Secure Scuttlebutt, struggle with challenges of censorship, user bans, server closures, and spam. This underscores the necessity for a decentralized, censorship-resistant, and user-centric social network.</div>
> </div>
<form
_="on submit halt the event's default then go to url `/${event.target.code.value}`" <div class="mt-8 sm:mt-0">
> <h2 class="text-4xl text-strongpink">The Nostr revolution</h2>
<div <div class="text-xl mt-2">Nostr, acronym for “Notes and Other Stuff Transmitted by Relays”, revolutionizes social networking and online communication by eliminating dependency of centralized servers.It employs a client-relay model, where users run clients, and anyone can operate relays.</div>
class="flex flex-wrap items-center justify-center sm:flex-nowrap sm:justify-normal" <div class="mt-2 text-neutral-500 dark:text-neutral-300">This protocol ensures tamperproof communication through cryptographic keys and signatures. By enabling users to establish pathways and publish notes to relays and incentivizing relay operators, Nostr addresses many shortcomings of existing systems.</div>
> </div>
<div class="mb-1.5 text-xl sm:mb-0">{ s.Domain }/</div> </div>
<input
name="code" <!-- Main section -->
placeholder="paste a npub / nprofile / nevent / ..."
autofocus <div id="why-nostr" class="mt-16 mb-12 text-center">
class="ml-0 w-full basis-full rounded-lg border-0 bg-white p-2 text-base text-gray-700 placeholder:text-gray-300 focus:outline-0 dark:bg-zinc-900 dark:text-neutral-50 dark:placeholder:text-gray-400 sm:ml-1 sm:basis-11/12 sm:rounded-s-lg" <div class="text-4xl text-strongpink">Empowering freedom in Nostr</div>
/> <div class="text-2xl">A secure, user-centric protocol and social network</div>
<button </div>
class="ml-0 w-full basis-full rounded-lg border-0 bg-strongpink p-2 text-base uppercase text-white sm:-ml-4 sm:basis-2/12 sm:rounded-s-lg"
> <div class="sm:flex sm:gap-20 mt-8 sm:mt-20 items-center">
View <div class="sm:w-1/2">
</button> <h3 class="text-2xl mb-4 text-strongpink">You own your identity, signed</h3>
</div> <p>Nostr uses a public key system, where your identity is tied to a unique cryptographic key. You have full control over your identity without relying on a central authority. Nostr's protocol eliminates the need for Know Your Customer (KYC) processes. No email, ID, thumbprint, or eyeball scans required. Your privacy is entirely yours to safeguard.</p>
</form> </div>
<div class="mt-3 text-center text-sm sm:mt-1 sm:text-left"> <div class="sm:w-1/2 mt-4 sm:mt-0">
or pick <img class="dark:hidden" src="/njump/static/home/home01.png" />
<a <img class="hidden dark:inline" src="/njump/static/home/home01-dark.png" />
class="underline" </div>
href="/random" </div>
_="on click halt the event then fetch /random with method:'POST' then tell <input[name='code'] /> set @value to result"
> <div class="sm:flex sm:flex-row-reverse sm:gap-20 mt-8 sm:mt-20 items-center">
some random content <div class="sm:w-1/2">
</a> <h3 class="text-2xl mb-4 text-strongpink">You own your data, signed</h3>
</div> <p>Users sign their posts with their cryptographic keys in Nostr. This cryptographic signature ensures the authenticity of your data, and you maintain ownership over it. Each client validates these signatures, ensuring data integrity. Users select relays for data exchange, and relays communicate directly with users, not with each other.</p>
</div> </div>
<p class="my-3 leading-5"> <div class="sm:w-1/2 mt-4 sm:mt-0">
There are several reasons to choose <i>njump</i> when sharing Nostr <img class="dark:hidden" src="/njump/static/home/home02.png" />
content outside of Nostr: <img class="hidden dark:inline" src="/njump/static/home/home02-dark.png" />
</p> </div>
<h2 class="mt-7 text-2xl text-strongpink">Clean, fast and solid</h2> </div>
<p class="my-3 leading-5">
Pages by <i>njump</i> are extremely lightweight and fast to load <div class="sm:flex sm:gap-20 mt-8 sm:mt-20 items-center">
because there isn't any client side javascript involved; they are <div class="sm:w-1/2">
minimalistic with the right attention to typography, focusing the <h3 class="text-2xl mb-4 text-strongpink">You own your audience</h3>
content without unnecessary details. Furthermore they are cached, so <p>In Nostr, you have full control over your audience. Users choose their preferred relay servers and can recommend relays to maintain their follower base, even if they switch relays. Additionally, users can mute other users, words, and contents (if the feature is available), shaping their social media feed according to their preferences.</p>
when sharing a page you can expect the other part will load it </div>
without any glitch in a fraction of second: the perfect tool to <div class="sm:w-1/2 mt-4 sm:mt-0">
onboard new users! <img class="dark:hidden" src="/njump/static/home/home03.png" />
</p> <img class="hidden dark:inline" src="/njump/static/home/home03-dark.png" />
<h2 class="mt-7 text-2xl text-strongpink">Good preview</h2> </div>
<p class="my-3 leading-5"> </div>
<i>njump</i> renders everything on the server-side, so it is able to
generate useful rich previews that work on Telegram, Discord, <div class="sm:flex sm:flex-row-reverse sm:gap-20 mt-8 sm:mt-20 items-center">
Twitter and other places. <div class="sm:w-1/2">
</p> <h3 class="text-2xl mb-4 text-strongpink">You are free to speak</h3>
<p class="my-3 leading-5"> <p>Theres no censorship on Nostr. If users are censored by a relay or a client, they can always opt for different clients and relays which ensures they will be able to freely express themselves. Relay blocking has no impact on a user's ability to publish to other relays or own relays, ensuring freedom of speech.</p>
When opening the URL directly in a browser, visitors will find </div>
referenced content like images, video and links to referenced Nostr <div class="sm:w-1/2 mt-4 sm:mt-0">
events displayed in a simple but effective way. It shows the note <img class="dark:hidden" src="/njump/static/home/home04.png" />
parent, allowing the visitor to follow it up and it has custom CSS for <img class="hidden dark:inline" src="/njump/static/home/home04-dark.png" />
printing or exporting to PDF. </div>
</p> </div>
<h2 class="mt-7 text-2xl text-strongpink">Cooperative (jump-out)</h2>
<p class="my-3 leading-5"> <div class="sm:flex sm:gap-20 mt-8 sm:mt-20 items-center">
<i>njump</i> is not interested capturing users at all, on the <div class="sm:w-1/2">
contrary it invites them to "jump" to the Nostr resource by picking <h3 class="text-2xl mb-4 text-strongpink">You are free to be anonymous</h3>
from a list of web clients or with a <code>nostr:</code> prefix for native <p>Nostr supports user anonymity. Users can choose to be anonymous or use pseudonyms without compromising their ability to participate. Nostr is also available On TOR that prevents tracking of users. Nostr does not have the capacity to provide user data to governments, safeguarding users' freedom of expression from prohibitions or restrictions.</p>
clients. It even remembers the most used one for each visitor and </div>
puts it on the top for fast clicking or tap. <div class="sm:w-1/2 mt-4 sm:mt-0">
</p> <img class="dark:hidden" src="/njump/static/home/home05.png" />
<p class="my-3 leading-5"> <img class="hidden dark:inline" src="/njump/static/home/home05-dark.png" />
<a class="underline" href="https://github.com/nostr-protocol/nips/blob/master/89.md">NIP-89</a> </div>
support coming! </div>
</p>
<h2 class="mt-7 text-2xl text-strongpink"> <div class="sm:flex sm:flex-row-reverse sm:gap-20 mt-8 sm:mt-20 items-center">
Search friendly (jump-in) <div class="sm:w-1/2">
</h2> <h3 class="text-2xl mb-4 text-strongpink">You are free to develop</h3>
<p class="my-3 leading-5"> <p>Nostr encourages development and customization. Users are free to develop on the platform, contributing to the growth and evolution of the network. Anyone can build on Nostr, creating clients, relays, tools, and apps. Users have the freedom to establish payment methods for their features, providing developers with a potential source of revenue.</p>
This is crucial: <i>njump</i> pages are static so search engines can </div>
index them, this means that <i>njump</i> can help others to discover <div class="sm:w-1/2 mt-4 sm:mt-0">
great content on Nostr, jump in and join us! <i>njump</i> is the <img class="dark:hidden" src="/njump/static/home/home06.png" />
only nostr resource that has this explicit goal, if you care that a <img class="hidden dark:inline" src="/njump/static/home/home06-dark.png" />
good note can be found online use <i>njump</i> to share it, this way </div>
you also help Nostr flourish. </div>
</p>
<h2 class="mt-7 text-2xl text-strongpink">Share NIP-05 profiles</h2> </div>
<p class="my-3 leading-5">
Now you can share your own profile with a pretty <!-- Title nimation -->
<a
class="underline" </div>
href="https://github.com/nostr-protocol/nips/blob/master/05.md"
> @footerTemplate()
NIP-05 </body>
</a> </html>
inspired permalink: }
<span class="rounded bg-lavender px-1 dark:bg-garnet">
{ s.Domain }/&lt;nip-05&gt;
</span>
, for example:
<a class="underline" href="/nvk.org">https://{ s.Domain }/nvk.org</a>
or
<a class="underline" href="/mike@mikedilger.com">
https://{ s.Domain }/mike@mikedilger.com
</a>
.
</p>
<p class="my-3 leading-5">
A profile shows the basic metadata infos, the used "outbox" relays
and the last notes.
</p>
<h2 class="mt-7 text-2xl text-strongpink">
Share on Twitter and Telegram
</h2>
<p class="my-3 leading-5">
Now you can quickly and effortlessly share Nostr notes on Twitter
and Telegram, and maybe on many other "social platforms": just drop
a link, and njump will render the note text using the preview image
as a canvas, to maximize the sharing experience and utility.
<br/>
On Telegram we have also the Instant View to access long content
in-app!
</p>
<h2 class="mt-7 text-2xl text-strongpink">Relays view</h2>
<p class="my-3 leading-5">
You can have a view of the last content posted to a relay using
<span class="rounded bg-lavender px-1 dark:bg-garnet">
{ s.Domain }/r/&lt;relay-host&gt;
</span>
, for example:
<a class="underline" href="/r/nostr.wine">
https://{ s.Domain }/r/nostr.wine
</a>
</p>
<p class="my-3 leading-5">
Some basic infos (
<a
href="https://github.com/nostr-protocol/nips/blob/master/11.md"
>
NIP-11
</a>
) are available; We hope operators will start to make them more
personal and informative so users can have a way to evaluate if/when
to join a relay.
</p>
<h2 class="mt-7 text-2xl text-strongpink">Website widgets</h2>
<div class="my-3 leading-5">
You can embed notes, long form contents and profiles in a web page
with a simple script:
<br/>
<span class="rounded bg-lavender px-1 dark:bg-garnet">
&lt;script src="https://{ s.Domain }/embed/&lt;nip-19-entity&gt;"
/&gt;
</span>
<div class="mt-4 gap-8 sm:flex">
<div class="mb-4 flex-auto sm:mb-0">
<script src="/embed/npub1sn0wdenkukak0d9dfczzeacvhkrgz92ak56egt7vdgzn8pv2wfqqhrjdv9"></script>
</div>
<div class="flex-auto">
<script src="/embed/naddr1qqxnzd3cxqmrzv3exgmr2wfeqy08wumn8ghj7mn0wd68yttsw43zuam9d3kx7unyv4ezumn9wshszyrhwden5te0dehhxarj9ekk7mf0qy88wumn8ghj7mn0wvhxcmmv9uq3zamnwvaz7tmwdaehgu3wwa5kuef0qy2hwumn8ghj7un9d3shjtnwdaehgu3wvfnj7q3qdergggklka99wwrs92yz8wdjs952h2ux2ha2ed598ngwu9w7a6fsxpqqqp65wy2vhhv"></script>
</div>
</div>
</div>
<h2 class="mt-7 text-2xl text-strongpink">Inspector tool</h2>
<p class="my-3 leading-5">
You know, we are all programmers, including our moms, so for every
<i>njump</i> page you can toggle the "Show more details" switch and
inspect the full event JSON. Without installing other tools (like
<a class="underline" href="https://github.com/fiatjaf/nak">nak</a>)
this is probably the fastest way to access that.
</p>
</div>
</div>
</div>
@footerTemplate()
</body>
</html>
}

View File

@@ -11,7 +11,7 @@ templ otherTemplate(params OtherPageParams) {
@headCommonTemplate(params.HeadParams) @headCommonTemplate(params.HeadParams)
</head> </head>
<body class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black"> <body class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black">
@topTemplate() @topTemplate(params.HeadParams)
<div class="mx-auto block px-4 sm:flex sm:items-center sm:justify-center sm:px-0"> <div class="mx-auto block px-4 sm:flex sm:items-center sm:justify-center sm:px-0">
<div class="flex w-full max-w-screen-2xl justify-between gap-10 overflow-visible px-4 print:w-full sm:w-11/12 md:w-10/12 lg:w-9/12 lg:gap-48vw"> <div class="flex w-full max-w-screen-2xl justify-between gap-10 overflow-visible px-4 print:w-full sm:w-11/12 md:w-10/12 lg:w-9/12 lg:gap-48vw">
<div class="w-full break-words print:w-full md:w-10/12 lg:w-9/12"> <div class="w-full break-words print:w-full md:w-10/12 lg:w-9/12">

View File

@@ -59,6 +59,8 @@ type DetailsParams struct {
} }
type HeadParams struct { type HeadParams struct {
IsHome bool
IsAbout bool
IsProfile bool IsProfile bool
NaddrNaked string NaddrNaked string
NeventNaked string NeventNaked string
@@ -86,6 +88,10 @@ type HomePageParams struct {
LastNotes []string LastNotes []string
} }
type AboutParams struct {
HeadParams
}
type ArchivePageParams struct { type ArchivePageParams struct {
HeadParams HeadParams

View File

@@ -38,7 +38,7 @@ templ profileTemplate(params ProfilePageParams) {
@headCommonTemplate(params.HeadParams) @headCommonTemplate(params.HeadParams)
</head> </head>
<body class="mb-16 bg-white text-gray-600 print:text-black dark:bg-neutral-900 dark:text-neutral-50"> <body class="mb-16 bg-white text-gray-600 print:text-black dark:bg-neutral-900 dark:text-neutral-50">
@topTemplate() @topTemplate(params.HeadParams)
<div class="mx-auto px-4 sm:flex sm:items-center sm:justify-center sm:px-0"> <div class="mx-auto px-4 sm:flex sm:items-center sm:justify-center sm:px-0">
<div class="w-full max-w-screen-2xl justify-between gap-10 overflow-visible print:w-full sm:flex sm:w-11/12 sm:px-4 md:w-10/12 lg:w-9/12 lg:gap-48vw"> <div class="w-full max-w-screen-2xl justify-between gap-10 overflow-visible print:w-full sm:flex sm:w-11/12 sm:px-4 md:w-10/12 lg:w-9/12 lg:gap-48vw">
<header <header

View File

@@ -35,7 +35,7 @@ templ relayTemplate(params RelayPageParams) {
<body <body
class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black" class="mb-16 bg-white text-gray-600 dark:bg-neutral-900 dark:text-neutral-50 print:text-black"
> >
@topTemplate() @topTemplate(params.HeadParams)
<div class="mx-auto px-4 sm:flex sm:items-center sm:justify-center sm:px-0"> <div class="mx-auto px-4 sm:flex sm:items-center sm:justify-center sm:px-0">
<div <div
class="w-full max-w-screen-2xl justify-between gap-10 overflow-visible px-4 print:w-full sm:flex md:w-10/12 lg:w-9/12 lg:gap-48vw" class="w-full max-w-screen-2xl justify-between gap-10 overflow-visible px-4 print:w-full sm:flex md:w-10/12 lg:w-9/12 lg:gap-48vw"

15
render_about.go Normal file
View File

@@ -0,0 +1,15 @@
package main
import (
"net/http"
)
func renderAbout(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Cache-Control", "max-age=3600")
err := aboutTemplate(AboutParams{
HeadParams: HeadParams{IsAbout: true, IsProfile: false},
}).Render(r.Context(), w)
if err != nil {
log.Error().Err(err).Msg("error rendering tmpl")
}
}

View File

@@ -37,6 +37,11 @@ func renderEvent(w http.ResponseWriter, r *http.Request) {
return return
} }
if code == "about" {
renderAbout(w, r)
return
}
if strings.HasPrefix(code, "nostr:") { if strings.HasPrefix(code, "nostr:") {
// remove the "nostr:" prefix // remove the "nostr:" prefix
http.Redirect(w, r, "/"+code[6:], http.StatusFound) http.Redirect(w, r, "/"+code[6:], http.StatusFound)

View File

@@ -7,7 +7,7 @@ import (
func renderHomepage(w http.ResponseWriter, r *http.Request) { func renderHomepage(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Cache-Control", "max-age=3600") w.Header().Set("Cache-Control", "max-age=3600")
err := homepageTemplate(HomePageParams{ err := homepageTemplate(HomePageParams{
HeadParams: HeadParams{IsProfile: false}, HeadParams: HeadParams{IsHome: true, IsProfile: false},
}).Render(r.Context(), w) }).Render(r.Context(), w)
if err != nil { if err != nil {
log.Error().Err(err).Msg("error rendering tmpl") log.Error().Err(err).Msg("error rendering tmpl")

BIN
static/home/home01-dark.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 113 KiB

BIN
static/home/home01.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 112 KiB

BIN
static/home/home02-dark.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 119 KiB

BIN
static/home/home02.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 119 KiB

BIN
static/home/home03-dark.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 100 KiB

BIN
static/home/home03.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 100 KiB

BIN
static/home/home04-dark.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 122 KiB

BIN
static/home/home04.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 122 KiB

BIN
static/home/home05-dark.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 121 KiB

BIN
static/home/home05.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 120 KiB

BIN
static/home/home06-dark.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 148 KiB

BIN
static/home/home06.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 149 KiB

View File

@@ -1,51 +1,64 @@
package main package main
templ topTemplate() { templ topTemplate(params HeadParams) {
<header class="items-center p-4 pb-6 text-sm print:block sm:flex sm:text-base"> <header class="items-center p-4 pb-6 print:block flex flex-row text-base">
<a
href="https://nostr.com" <div class="hidden sm:block sm:w-[14%]">
class="text-md text-right text-sm print:hidden md:basis-1/6"
target="_blank"
>What is <span class="text-strongpink">Nostr</span>?</a>
<div class="hidden">
<a href="/npubs-archive/">Nostr npubs archive</a>
<a href="/relays-archive/">Nostr relays archive</a>
</div> </div>
<div
class="print:hidden; relative float-right h-4 w-4 cursor-pointer rounded-full text-gray-100 dark:text-gray-700 sm:fixed sm:right-4 sm:top-4 sm:float-none" <div class="w-[90%] sm:w-[72%] sm:text-right">
_="on click tell <html /> toggle between .theme--dark and .theme--default then get your @class then get it[0].split('--')[1].split(' ')[0] then set localStorage.theme to it <div class="hidden">
on load tell <html /> get localStorage.theme then if it is 'dark' add .theme--dark then remove .theme--default else if it is not 'default' then get window.matchMedia('(prefers-color-scheme: dark)').matches then if it is true add .theme--dark then remove .theme--default end" <a href="/npubs-archive/">Nostr npubs archive</a>
> <a href="/relays-archive/">Nostr relays archive</a>
<svg </div>
aria-hidden="true"
data-prefix="fas" if !(params.IsHome) {
class="block dark:hidden" <a href="/" class="mr-4">Why <span class="text-strongpink">Nostr</span>?</a>
role="img" }
xmlns="http://www.w3.org/2000/svg" if !(params.IsAbout) {
viewBox="0 0 512 512" <a href="/about">What is <span class="text-strongpink">Njump</span>?</a>
}
</div>
<div class="w-[10%] sm:w-[14%]">
<div
class="print:hidden; relative float-right h-4 w-4 cursor-pointer rounded-full text-gray-100 dark:text-gray-700 sm:fixed sm:right-4 sm:top-4 sm:float-none"
_="on click tell <html /> toggle between .theme--dark and .theme--default then get your @class then get it[0].split('--')[1].split(' ')[0] then set localStorage.theme to it
on load tell <html /> get localStorage.theme then if it is 'dark' add .theme--dark then remove .theme--default else if it is not 'default' then get window.matchMedia('(prefers-color-scheme: dark)').matches then if it is true add .theme--dark then remove .theme--default end"
> >
<path <svg
fill="currentColor" aria-hidden="true"
d="M283.211 512c78.962 0 151.079-35.925 198.857-94.792 7.068-8.708-.639-21.43-11.562-19.35-124.203 23.654-238.262-71.576-238.262-196.954 0-72.222 38.662-138.635 101.498-174.394 9.686-5.512 7.25-20.197-3.756-22.23A258.156 258.156 0 0 0 283.211 0c-141.309 0-256 114.511-256 256 0 141.309 114.511 256 256 256z" data-prefix="fas"
></path> class="block dark:hidden"
</svg> role="img"
<svg xmlns="http://www.w3.org/2000/svg"
aria-hidden="true" viewBox="0 0 512 512"
data-prefix="fas" >
class="hidden dark:block" <path
role="img" fill="currentColor"
xmlns="http://www.w3.org/2000/svg" d="M283.211 512c78.962 0 151.079-35.925 198.857-94.792 7.068-8.708-.639-21.43-11.562-19.35-124.203 23.654-238.262-71.576-238.262-196.954 0-72.222 38.662-138.635 101.498-174.394 9.686-5.512 7.25-20.197-3.756-22.23A258.156 258.156 0 0 0 283.211 0c-141.309 0-256 114.511-256 256 0 141.309 114.511 256 256 256z"
viewBox="0 0 512 512" ></path>
> </svg>
<path <svg
fill="currentColor" aria-hidden="true"
d="M256 160c-52.9 0-96 43.1-96 96s43.1 96 96 96 96-43.1 96-96-43.1-96-96-96zm246.4 80.5l-94.7-47.3 33.5-100.4c4.5-13.6-8.4-26.5-21.9-21.9l-100.4 33.5-47.4-94.8c-6.4-12.8-24.6-12.8-31 0l-47.3 94.7L92.7 70.8c-13.6-4.5-26.5 8.4-21.9 21.9l33.5 100.4-94.7 47.4c-12.8 6.4-12.8 24.6 0 31l94.7 47.3-33.5 100.5c-4.5 13.6 8.4 26.5 21.9 21.9l100.4-33.5 47.3 94.7c6.4 12.8 24.6 12.8 31 0l47.3-94.7 100.4 33.5c13.6 4.5 26.5-8.4 21.9-21.9l-33.5-100.4 94.7-47.3c13-6.5 13-24.7.2-31.1zm-155.9 106c-49.9 49.9-131.1 49.9-181 0-49.9-49.9-49.9-131.1 0-181 49.9-49.9 131.1-49.9 181 0 49.9 49.9 49.9 131.1 0 181z" data-prefix="fas"
></path> class="hidden dark:block"
</svg> role="img"
xmlns="http://www.w3.org/2000/svg"
viewBox="0 0 512 512"
>
<path
fill="currentColor"
d="M256 160c-52.9 0-96 43.1-96 96s43.1 96 96 96 96-43.1 96-96-43.1-96-96-96zm246.4 80.5l-94.7-47.3 33.5-100.4c4.5-13.6-8.4-26.5-21.9-21.9l-100.4 33.5-47.4-94.8c-6.4-12.8-24.6-12.8-31 0l-47.3 94.7L92.7 70.8c-13.6-4.5-26.5 8.4-21.9 21.9l33.5 100.4-94.7 47.4c-12.8 6.4-12.8 24.6 0 31l94.7 47.3-33.5 100.5c-4.5 13.6 8.4 26.5 21.9 21.9l100.4-33.5 47.3 94.7c6.4 12.8 24.6 12.8 31 0l47.3-94.7 100.4 33.5c13.6 4.5 26.5-8.4 21.9-21.9l-33.5-100.4 94.7-47.3c13-6.5 13-24.7.2-31.1zm-155.9 106c-49.9 49.9-131.1 49.9-181 0-49.9-49.9-49.9-131.1 0-181 49.9-49.9 131.1-49.9 181 0 49.9 49.9 49.9 131.1 0 181z"
></path>
</svg>
</div>
</div> </div>
</header> </header>
<script type="text/hyperscript"> <script type="text/hyperscript">
on beforeprint from window tell <html /> remove .theme--dark add .theme--default on beforeprint from window tell <html /> remove .theme--dark add .theme--default
on afterprint from window tell <html /> add .theme--dark remove .theme--default on afterprint from window tell <html /> add .theme--dark remove .theme--default
</script> </script>
} }