strona główna
artykuły i recenzje
poradniki
galeria zdjęć
fotoblog

Wordpress: nawigacja między wpisami (następny, poprzedni post)

Dodano: Wtorek, 26 sierpnia 2008, godzina 11:59:26
Kategoria: Wordpress

Podczas ostatnich prac nad nowym wyglądem strony napotkałem szereg problemów związanych z budową własnej skórki do silnika Wordpress. Sporo z nich wymagało ingerencji bezpośrednio w kod źródłowy skryptu, co oczywiście nie jest najlepszą metodą wprowadzania własnych rozwiązań. Dlaczego? Powód jest prosty, otóż przy aktualizacji całego silnika będziemy zmuszeni do odnajdywania naszych zmian w kodzie i wprowadzania ich na nowo.

Najlepszą metodą na wykonanie drobniutkiej modyfikacji bez ingerencji w rdzeń jest wykorzystanie pliku functions.php, który znajduje się (może ale nie musi, zależy to od wybranej skórki, jeżeli go brakuje, to tworzymy nowy) w katalogu wp-content/themes/nazwa_twojej_skórki/. Plik ten jest ładowany przez silnik Wordpressa podczas generowania strony.

Przy budowaniu działu fotoblog potrzebowałem prostej nawigacji między postami (wpisami) w dziale. Zamysł był taki, żeby na stronie głównej działu pokazywał się tylko jeden, najnowszy wpis (ostatni) wraz z linkiem do poprzedniego. Niestety, jeżeli normalnie mamy ustawione wyświetlanie więcej niż jednego posta na stronę działu (można to ustawić w panelu administracyjnym: Administracja > Ustawienia > Wyświetlanie), to wykonanie tego w normalny sposób (zmieniając zapytanie o pobranie danych funkcją query_posts(), tak żeby pobrać tylko jeden wpis i potem wypluć go w standardowej pętli “while (have_posts()) : the_post();” i skorzystać z wbudowanych funkcji do nawigacji na stronach działów: next_posts_link i previous_posts_link) kończy się zazwyczaj błędem podczas nawigowania między stronami w dziale (błąd 404 np. na stronie 3 i następnych). Walczyłem z tym problemem całkiem długo i spróbowałem różnych rozwiązań zamieszczanych m.in. na forum wsparcia dla Wordpress. Niestety, podejrzewam, że przez zastosowanie wtyczki wykluczającej wyświetlanie się postów z różnych kategorii na stronie głównej (wtyczka o nazwie Ultimate Category Exclusion), nie mogłem dojść do ładu i składu z tym bałaganem…

Zrobiłem to trochę inaczej: do pobrania na stronie głównej działu fotoblog (strona główna tej kategorii jest w mojej skórce generowana przez inny plik, stąd też wygląda inaczej i mogę wprowadzać w niej zmiany niezależnie od innych kategorii, które generowane są przez standardowy plik) ostatniego postu wykorzystałem funkcję: query_posts (wywołana z atrybutami category_name=fotoblog&posts_per_page=1 - czyli jeden post z kategorii o nazwie fotoblog) i następnie w standardowej pętli wyświetliłem potrzebną zawartość wpisu (tytuł, treść, itp.). Do tego dołożyłem link do poprzedniego wpisu w tym dziale korzystając z get_posts():

<?php global $post;
$myposts = get_posts('numberposts=1&offset=1&category_name=fotoblog');
foreach($myposts as $post) :
?>
<a href="<?php the_permalink(); ?>">&laquo; <?php the_title(); ?></a>
<?php endforeach; ?>

Małe wyjaśnienie przekazanych parametrów do funkcji: offset=1 oznacza, że nie ma być brany pod uwagę najnowszy post w wybranej kategorii. Pozostałe dwa argumenty są chyba jasne. the_permalink() zwraca link do pobranego posta, a the_title() jego tytuł. W resztę nie będę się zagłębiać.

Stronę główną działu już mamy: wyświetla nam ostatni wpis z linkiem do wpisu poprzedniego. Po jego kliknięciu jesteśmy przenoszeni do strony wyświetlającej pojedynczy, pełny wpis (standardowo pojedynczy wpis jest generowany przez plik single.php z katalogu skórki, u mnie jest to inny plik ze względu na zmianę wyglądu w przypadku ładowania postu z kategorii fotoblog, jak załadować inne pliki w zależności od kategorii wpisu itp. opiszę innym razem).

Ostatnią rzeczą jest przygotowanie nawigacji już na stronie pojedynczego wpisu (nie działu głównego) należącego do działu fotoblog. Wordpress oferuje dwie gotowe funkcje: previous_post_link i next_post_link, które standardowo zwracają (niestety korzystając z funkcji echo) link do poprzedniego/następnego postu w chronologicznej kolejności. Funkcje te można wywołać (ważne! trzeba je wywoływać w standardowej pętli Wordpressa, tzw. The Loop) z różnymi parametrami (dokumentacja Template Tags: previous post link, next_post_link).

Żeby otrzymać link do wpisu z tego samego działu, co post który aktualnie wyświetlamy, w postaci tytułu (tytuł wpisu poprzedniego/następnego z linkiem do niego) wywołujemy funkcje w sposób następujący:

previous_post_link(’%link’, ‘%title’, TRUE, ”)
next_post_link(’%link’, ‘%title’, TRUE, ”)

Niestety przez zastosowanie echo nie mamy kontroli nad tym czy otrzymamy link czy po prostu funkcja nie zwróci niczego. Jeżeli ktoś po prostu wyświetla linka bez żadnego formatowania, to nie powinno mu to przeszkadzać. Gorzej w przypadku gdy chcemy wyświetlić nawigację w postaci obrazka z linkiem do następnego/poprzedniego wpisu lub wyświetlamy linki w formatowanych blokach (tak jak ja - potrzebuję wiedzieć czy link zostanie wygenerowany żeby zbudować odpowiedni układ bloków <div>, tj. wyświetlić dwa bloki lub tylko jeden i z odpowiednim formatowaniem). W efekcie możemy otrzymać obrazek lub blok… bez linka.

Tutaj z pomocą przychodzi nam plik functions.php z katalogu naszej skórki. Deklaracja standardowa wspomnianych dwóch funkcji wygląda następująco (znajdują się one w pliku link-template.php w katalogu wp-include w głównym folderze instalacji Wordpressa, pominąłem atrybuty w nawiasach dla czytelności). Jak widać poniżej, to właśnie funkcja adjacent_post_link zwraca dane przez echo, poniżej także jej deklaracja:

function previous_post_link(...) {
adjacent_post_link(...);
}
function next_post_link(...) {
adjacent_post_link(...);
}
function adjacent_post_link(...) {
[ ... ]
echo apply_filters( "{$adjacent}_post_link", $format, $link );
}

Oczywiście, moglibyśmy po prostu zmienić w oryginalnym pliku formę zwracania danych przez funkcję adjacent_post_link. Jednak dla zachowania porządku zrobimy to inaczej.

Kopiujemy wszystkie 3 deklaracje (całe!) i wklejamy je do naszego pliku functions.php z drobnymi zmianami, jak poniżej (ważne żeby otoczyć zawartość tego pliku <?php …tutaj nasze funkcje… ?> i nie pozostawić pustych znaków na jego początku lub końcu):

function previous_post_link2(...) {
return adjacent_post_link(...);
}
function next_post_link2(...) {
return adjacent_post_link(...);
}
function adjacent_post_link2(...) {
[ ... ]
return apply_filters( "{$adjacent}_post_link", $format, $link );
}

Od teraz mamy dostęp do dwóch nowych funkcji next_post_link2 oraz previous_post_link2 (możemy nazwać je oczywiście inaczej, wedle naszych potrzeb, jednak lepiej żeby nazwy te były unikalne i nie wykorzystywane przez silnik Wordpressa), działające identycznie jak te standardowe z tą różnicą, że zwracają wynik przez wartość, a nie przez echo. Teraz wykorzystując nowe funkcje mamy możliwość sprawdzenia czy link do poprzedniego/następnego postu istnieje (może nie istnieć jeżeli wyświetlamy np. ostatni/pierwszy post w dziale). U mnie wygląda to mniej więcej tak (pominąłem kod z elementami <div> i warunkami if w PHP, jest to przykład linka do poprzedniego postu w tym samym dziale):

<php
$PoprzedniPostLink = previous_post_link2('%link','&laquo; %title',TRUE,'');
if ($poprzedni_wpis_link != "") echo $PoprzedniPostLink;
?>

Efekt możecie zobaczyć w moim dziale fotoblog w jednym z wpisów.

Mam nadzieję, że komuś powyższe informacje się przydały. Zaznaczam, że nie jestem programistą, stąd też terminologia i pewne zwroty dla wprawnych znawców PHP mogą się wydać śmieszne lub nawet błędne (w razie czego proszę o poprawienie mnie w komentarzach). Moja wiedza na temat PHP jest wyłącznie efektem hobbystycznych zainteresowań tym językiem :).

» 1 komentarz «

Rky
Dodany: Poniedziałek, 15 listopada 2010 o godzinie: 11:42:15

ale przekozacki tutorial. bardzo dziekuje, meczylem sie z glupimi linkami prev/next az tu taka perelka i po polsku, potrebowalem troche innego efektu koncowego, czyli wyrzucania postu next/prev z wybranej przez uzytkownika kategorii wczesniej gdzie posty maja po kilka kategorii kazdy.

» dodaj komentarz «





» Komentarze dodane przez niezarejestrowanych użytkowników muszą być zatwierdzone przez moderatora


» kategorie wpisów

Co nowego na stronie (wpisów: 43)
Dzikie.NET (wpisów: 16)
Humor (wpisów: 46)
Inne (wpisów: 34)
Kapsle Tymbark (wpisów: 29)
Moje projekty i pomysły (wpisów: 43)
Narzekam na… (wpisów: 16)
Nowości w galerii (wpisów: 12)
Nowości, ciekawostki (wpisów: 595)
O mnie (wpisów: 36)
Wordpress (wpisów: 1)
Zabawki (wpisów: 9)
Zdjęcie bez komentarza (wpisów: 91)
Zdjęcie z komentarzem (wpisów: 23)
Strony w domenie tech-blog.pl wykorzystują pliki cookies w celach statystycznych, analizy oglądalności oraz na potrzeby wyświetlania reklam. Jeżeli nie wyrażasz na to zgody, zmień ustawienia wykorzystywanej przeglądarki internetowej. Więcej informacji na stronie Polityka prywatności i cookies (ciasteczka).

» archiwum wpisów

styczeń 2014 (wpisów: 2)
grudzień 2013 (wpisów: 6)
listopad 2013 (wpisów: 27)
październik 2013 (wpisów: 21)
wrzesień 2013 (wpisów: 27)
sierpień 2013 (wpisów: 8)
lipiec 2013 (wpisów: 8)
czerwiec 2013 (wpisów: 6)
maj 2013 (wpisów: 16)
kwiecień 2013 (wpisów: 17)
marzec 2013 (wpisów: 18)
luty 2013 (wpisów: 22)
styczeń 2013 (wpisów: 19)
grudzień 2012 (wpisów: 20)
listopad 2012 (wpisów: 33)
październik 2012 (wpisów: 25)
wrzesień 2012 (wpisów: 15)
maj 2012 (wpisów: 1)
kwiecień 2012 (wpisów: 1)
marzec 2012 (wpisów: 1)
styczeń 2012 (wpisów: 2)
grudzień 2011 (wpisów: 1)
listopad 2011 (wpisów: 7)
październik 2011 (wpisów: 4)
wrzesień 2011 (wpisów: 1)
sierpień 2011 (wpisów: 3)
lipiec 2011 (wpisów: 2)
czerwiec 2011 (wpisów: 3)
maj 2011 (wpisów: 1)
marzec 2011 (wpisów: 3)
luty 2011 (wpisów: 5)
styczeń 2011 (wpisów: 5)
grudzień 2010 (wpisów: 6)
listopad 2010 (wpisów: 2)
październik 2010 (wpisów: 1)
wrzesień 2010 (wpisów: 4)
sierpień 2010 (wpisów: 2)
lipiec 2010 (wpisów: 4)
kwiecień 2010 (wpisów: 4)
marzec 2010 (wpisów: 12)
luty 2010 (wpisów: 4)
styczeń 2010 (wpisów: 1)
listopad 2009 (wpisów: 1)
październik 2009 (wpisów: 1)
wrzesień 2009 (wpisów: 1)
sierpień 2009 (wpisów: 3)
lipiec 2009 (wpisów: 2)
czerwiec 2009 (wpisów: 6)
kwiecień 2009 (wpisów: 1)
marzec 2009 (wpisów: 25)
luty 2009 (wpisów: 9)
styczeń 2009 (wpisów: 13)
grudzień 2008 (wpisów: 7)
listopad 2008 (wpisów: 11)
październik 2008 (wpisów: 1)
wrzesień 2008 (wpisów: 9)
sierpień 2008 (wpisów: 49)
lipiec 2008 (wpisów: 2)
czerwiec 2008 (wpisów: 39)
maj 2008 (wpisów: 52)
kwiecień 2008 (wpisów: 49)
marzec 2008 (wpisów: 58)
luty 2008 (wpisów: 38)
styczeń 2008 (wpisów: 12)
grudzień 2007 (wpisów: 16)
listopad 2007 (wpisów: 2)
październik 2007 (wpisów: 8)
wrzesień 2007 (wpisów: 16)
sierpień 2007 (wpisów: 7)
lipiec 2007 (wpisów: 3)
czerwiec 2007 (wpisów: 3)
maj 2007 (wpisów: 11)
kwiecień 2007 (wpisów: 11)
marzec 2007 (wpisów: 16)
luty 2007 (wpisów: 9)
styczeń 2007 (wpisów: 13)
grudzień 2006 (wpisów: 5)
listopad 2006 (wpisów: 4)
październik 2006 (wpisów: 13)
wrzesień 2006 (wpisów: 15)
sierpień 2006 (wpisów: 8)
lipiec 2006 (wpisów: 5)
czerwiec 2006 (wpisów: 39)
maj 2006 (wpisów: 38)
All rights reserved Copyright 2006-2012 Piotr Dymacz