NOTE: Apart from
(and even then it's questionable, I'm Scottish). These are machine translated in languages I don't read. If they're terrible please contact me.
You can see how this translation was done in this article.
Sunday, 15 September 2024
//Less than a minute
Tässä kohdassa käytän HTMX Laaja-alaisesti tämä on superhelppo tapa saada sivustosi tuntemaan olosi vastaanottavaisemmaksi ja sujuvammaksi ilman, että sinun tarvitsee kirjoittaa paljon JavaScriptia.
HUOMAUTUS: En ole täysin tyytyväinen tähän vielä, HTMX:ssä on elementtejä, jotka tekevät tästä hankalaa
HTMX:n käyttö ASP.NET Coren kanssa on aikamoinen unelma, olen kirjoittanut tästä aiemmin tämä postaus...................................................................................................................................... Sivustosi "HTMX:ää" on todella helppo "tehdä", ja se on hyvä tapa saada sivustosi tuntemaan olosi vastaanottavaisemmaksi.
Osana viimeisintä kierrostani HTMX:n avulla päätin tehdä mahdollisimman monta linkkiä tällä sivustolla käyttää HTMX:ää. Joten esimerkiksi jos klikkaat "Koti"-painiketta, se käyttää nyt HTMX:ää sivun sisällön lataamiseen.
Saavutan tämän yksinkertaisesti lisäämällä joitakin ominaisuuksia linkin tagiin, kuten näin:
<a asp-action="IndexPartial" asp-controller="Home" hx-swap="show:window:top" hx-target="#contentcontainer" hx-boost="true" class="mr-auto sm:mr-6">
<div class="svg-container">
<img src="/img/logo.svg" asp-append-version="true" width="180px" height="30px" alt="logo" :class="{ 'img-filter-dark': isDarkMode }"/>
</div>
</a>
Tässä näette, että lisään... hx-swap
attribuutti kertoo HTMX:n vaihtavan kohde-elementin sisällön palvelimelta palautetun sisällön kanssa.
HUOMAUTUS: ÄLÄ käytä hx-pushurlia, koska tämä saa selaimen lataamaan sivun takanappiin kahdesti.
Erytropoietiini hx-target
Attribuutti kertoo HTMX:lle, mihin palvelimelta palautettu sisältö laitetaan. Tässä tapauksessa se on #contentcontainer
elementti (jossa kaikki sivun sisältö on ladattu).
Lisään myös: hx-swap="show:window:top
joka tekee ikkunan kääröstä sivun yläosan, kun sisältöä vaihdetaan.
C#-osa on melko yksinkertainen, se vain kopioi normaalin Index-menetelmäni, mutta lataa sen sijaan osittaisen näkymän. Koodi on alla. Jälleen tämä käyttää HTMX.NET Havaitsemaan hx-request
Header and return the partial view. Normaalin näkymän palauttamiseen on myös mahdollisuus, jos pyyntö ei ole HTMX-pyyntö.
[Route("/IndexPartial")]
[OutputCache(Duration = 3600, VaryByHeaderNames = new[] { "hx-request" })]
[ResponseCache(Duration = 300, VaryByHeader = "hx-request",
Location = ResponseCacheLocation.Any)]
[HttpGet]
public async Task<IActionResult> IndexPartial()
{
ViewBag.Title = "mostlylucid";
if(!Request.IsHtmx()) return RedirectToAction("Index");
var authenticateResult = await GetUserInfo();
var posts = await BlogService.GetPagedPosts(1, 5);
posts.LinkUrl = Url.Action("Index", "Home");
var indexPageViewModel = new IndexPageViewModel
{
Posts = posts, Authenticated = authenticateResult.LoggedIn, Name = authenticateResult.Name,
AvatarUrl = authenticateResult.AvatarUrl
};
return PartialView("_HomePartial", indexPageViewModel);
}
Tuloksena on, että tämä linkki (ja muut samaa tekniikkaa käyttävät) lataa AJAX-pyyntöjä ja sisältö vaihdetaan ilman koko sivun uudelleenlatausta. Näin vältät ärsyttävän "valon välähdyksen", kun sivu latautuu uudelleen, koska teemani vaihto toimii.
Joten alla oleva menetelmä voidaan saada toimimaan, mutta se on erittäin hankala ja hieman kiusallinen.
HTMX todella haluaa työskennellä attribuuttipohjaisella lähestymistavalla. Käyttäminen htmx.ajax
on tavallaan "jos kaikki muu epäonnistuu" -menetelmä ja tarkoittaa, että pitää sotkea borwserin historiaa.
Valitettavasti selainhistoriaa käytetään pushState
replaceState
sekä popstate
on todella vähän niskakipua (mutta voi olla supervoimakas reunatapauksissa).
Sen sijaan se, mitä nyt teen, vain lisään hx-boost
blogin sisältöä sisältävään lapulle.
<div class="prose prose max-w-none border-b py-2 text-black dark:prose-dark sm:py-2" hx-boost="true" hx-target="#contentcontainer">
@Html.Raw(Model.HtmlContent)
</div>
Tämä näyttää toimivan hyvin. hx-boost
Voidaan soveltaa vanhempien menetelmiin ja soveltaa kaikkiin lapsilinkkeihin. Se on myös tavallisempi HTMX sotkematta historiaa jne.
Harvoissa tilanteissa, joissa et halua käyttää HTMX:ää tietyissä linkeissä, voit vain lisätä hx-boost="false"
linkkiin.
Ongelmana tässä lähestymistavassa oli kuitenkin tämänkaltainen blogilinkkini: HTMX SPA:n kaltaiseen kokemukseen jotka eivät ole "normaaleja" yhteyksiä. Nämä linkit syntyy markdown-palkinnosta; vaikka voisin kirjoittaa MarkDig-laajennuksen lisätäkseni HTMX-attribuutit lenkkeihin, päätin käyttää erilaista lähestymistapaa (koska minulla on jo paljon sisältöä, jota en halua muokata).
Sen sijaan lisäsin Javascript-toiminnon, joka etsii kaikkia tämäntyyppisiä linkkejä ja sitten käyttää htmx.ajax
vaihdoksen tekemiseen. Tämä on pohjimmiltaan se, mitä HTMX tekee joka tapauksessa vain "manuaalisesti".
Kuten näet, tämä on vain yksinkertainen toiminto, joka etsii kaikki linkit div.prose
elementti, joka alkaa /
ja lisää sitten niihin tapahtuman kuuntelijan. Kun linkkiä napsautetaan, tapahtuma estetään, URL poistetaan ja sen jälkeen htmx.ajax
Funktio kutsutaan URL-osoitteella ja päivitettävällä kohde-elementillä.
(function(window) {
window.blogswitcher =() => {
const blogLinks = document.querySelectorAll('div.prose a[href^="/"]');
// Iterate through all the selected blog links
blogLinks.forEach(link => {
link.addEventListener('click', function(event) {
event.preventDefault();
let link = event.currentTarget;
let url = link.href;
htmx.ajax('get', url, {
target: '#contentcontainer', // The container to update
swap: 'innerHTML', // Replace the content inside the target
}).then(function() {
history.pushState(null, '', url);
window.scrollTo({
top: 0,
behavior: 'smooth' // For a smooth scrolling effect
});
});
});
});
};
})(window);
Kun vaihto on tehty, työnnän uuden URL-osoitteen selaimen historiaan ja selaa sivun yläreunaan. Käytän tätä lähestymistapaa muutamaan paikkaan (kuten hakuun) antaakseni mukavan voimaisen pehmeän kokemuksen.
Tämän tyyppisen sovelluksen takapainike voi olla ongelmallinen; monet "sopivat" SPA:t joko poistavat takapainikkeen käytöstä tai sietävät tätä väärää käytöstä. Halusin kuitenkin varmistaa, että takanappi toimii odotetusti.
Huomautus: Jotta takanappi toimisi odotetusti, meidän on myös kuunneltava popState
tapahtuma. Tapahtuma käynnistyy, kun käyttäjä navigoi takaisin tai eteenpäin selainhistoriassa. Kun tämä tapahtuma käynnistyy, voimme ladata sisällön nykyiseen URL-osoitteeseen.
window.addEventListener("popstate", (event) => {
// When the user navigates back, reload the content for the current URL
event.preventDefault();
let url = window.location.href;
// Perform the HTMX AJAX request to load the content for the current state
htmx.ajax('get', url, {
target: '#contentcontainer',
swap: 'innerHTML'
}).then(function () {
// Scroll to the top of the page
window.scrollTo({
top: 0,
behavior: 'smooth'
});
});
});
Tässä koodissa estämme oletusselaimen popstate-käyttäytymisen event.preventDefault()
puhelu. Sen jälkeen poistamme nykyisen URL-osoitteen window.location.href
Omistus ja suorita HTMX AJAX -pyyntö sisällön lataamisesta nykytilaa varten. Kun sisältö on ladattu, selataan sivun yläosaan.
Kuten edellä mainittiin, et voi myös käyttää hx-pushurl
Koska tämä saa selaimen lataamaan sivun backpainikella kahdesti.
Kuten ehkä arvasit, olen jonkin verran HTMX:n fani, yhdistettynä ASP.NET Coreen ja Alppien murskaamiseen.Js:n avulla Devs pystyy luomaan todella mukavan käyttökokemuksen mahdollisimman pienellä vaivalla. Tärkein asia, josta pidän enemmän kuin "täysin muodostuneiden" asiakaspuolen kehysten, kuten React / Angular jne., kaltaisista asioista, on se, että se antaa minulle yhä täyden palvelimenpuolisen renderointiputken ASP.NET Corella, mutta SPA:n "tunteen". Alpine.js mahdollistaa yksinkertaisen asiakasvuorovaikutteisuuden, joka on hyvin yksinkertainen ominaisuus, jonka lisäsin äskettäin, oli tehdä kategorioistani "piilotettuja", mutta laajenna klikkauksella.
Alpine.js:n käyttö tähän tarkoittaa, että ylimääräistä JavaScriptia ei tarvita.
<div class="mb-8 mt-6 border-neutral-400 dark:border-neutral-600 border rounded-lg" x-data="{ showCategories: false }">
<h4
class="px-5 py-1 bg-neutral-500 bg-opacity-10 rounded-lg font-body text-primary dark:text-white w-full flex justify-between items-center cursor-pointer"
x-on:click="showCategories = !showCategories"
>
Categories
<span>
<i
class="bx text-2xl"
:class="showCategories ? 'bx-chevron-up' : 'bx-chevron-down'"
></i>
</span>
</h4>
<div
class="flex flex-wrap gap-2 pt-2 pl-5 pr-5 pb-2"
x-show="showCategories"
x-cloak
x-transition:enter="max-h-0 opacity-0"
x-transition:enter-end="max-h-screen opacity-100"
x-transition:leave="max-h-screen opacity-100"
x-transition:leave-end="max-h-0 opacity-0"
>
@foreach (var category in ViewBag.Categories)
{
<partial name="_Category" model="category"/>
}
</div>
</div>
Tässä näet, että käytän x-data
attribuutti uuden Alpine.js-tietoobjektin luomiseen, tässä tapauksessa showCategories
...................................................................................................................................... Tämä on boolean, joka kietoutuu yhteen, kun h4
elementtiä klikataan. Erytropoietiini x-on:click
Attribuuttia käytetään kytkemään naksahdustapahtuma toiminnolle.
Luokkien luettelossa I sitten käyttää x-show
Attribuutti, jolla näytetään tai piilotetaan luettelo kategorioista, joiden arvo perustuu showCategories
...................................................................................................................................... Käytän myös x-transition
Attribuutti, joka lisää mukavan liukuvan vaikutuksen, kun kategoriat näytetään tai piilotetaan.
Erytropoietiini x-cloak
Ominaisuus käytetään estämään kategorioiden "flicker" näyttäminen ennen JavaScriptin käyttöä.
Minulla on pieni CSS-kurssi, joka on määritelty tätä varten:
[x-cloak] { display: none !important; }
Siinä se, lyhyt artikkeli siitä, miten HTMX:ää käytetään, sekä kohta Alppien.j:iä, jotta sivustosi tuntisi itsensä reagoivammaksi ja "SPA-maiseksi". Toivon, että pidit tätä hyödyllisenä, jos sinulla on kysyttävää tai kommentteja, voit jättää ne alle.