For a long time, I wanted to structure some of my albums based on search results instead of a fixed content. This would enable something like a smart album structure that supports themes (e.g. bridges, mountains, people, etc) where images are shown that are already published in another album.
A week ago, Chumby asked the same question in the Backlight forum. This got me thinking again… and I have found a way to get this to work. It is a bit heavy handed approach since I launch a photo search from the script, parse the resulting html code and embed the result gallery in the target page. It works for me and I didn’t notice significant performance issues. Your mileage may vary. Nevertheless, I hope that eventually a JSON API based approach will provide a more elegant solution!
Note: Some web hosts block URL access to the server that originates from the same server. If this is the case for you, you will not be able to run this code. You should get an error message that indicates a denied access or something along this line.
Now to the php code that belongs into your custom phplugins file and should be placed after
// SET USER FUNCTIONS BELOW
// Some example functions are included below. Feel free to delete or modify unwanted functions.
// ****************************************************************************************************
Following are helper functions that help to keep the code structured, nice and tidy.
// returns true if $page matches current page or any of its
// sub-pages
function dlp_page_match($page) {
if (substr($_SERVER["REQUEST_URI"], 0, strlen($page)) == $page) {
return true;
} else {
return false;
}
}
// Returns the html code for the given url. If an error was
// detected, an array is returned containing the error
// response code:
//
// Error response:
// (
// ['status'] => 'error'
// ['code'] => error number
// ['message'] => error description
// )
function dlp_get_html($url){
$curl = curl_init();
curl_setopt_array($curl, array(
CURLOPT_RETURNTRANSFER => 1,
CURLOPT_URL => $url,
CURLOPT_HTTPHEADER => array('Content-Type: application/json'),
CURLOPT_FAILONERROR => true,
CURLOPT_SSL_VERIFYHOST => 0,
CURLOPT_SSL_VERIFYPEER => 0
));
$posts = curl_exec($curl);
// Was an error detected?
if (curl_errno($curl)>0){
$response = Array();
$response['status'] = 'error';
$response['code'] = curl_getinfo($curl, CURLINFO_RESPONSE_CODE);
$response['message'] = curl_errno($curl).': '.curl_error($curl);
} else {
$response = $posts;
}
curl_close($curl);
return $response;
}
// Returns the gallery code section of the search page for the given
// search query.
function dlp_get_smart_album($query){
// Set search URL, following two lines can be removed if
// the $query string is already websafe.
$query = str_replace(array("+"), "%2B", $query);
$query = str_replace(array(" "), "+", $query);
$url = 'https://mysite.com/backlight/search/?q='.$query;
// Get paging argument
if(isset($_GET['page']) && !empty($_GET['page'])){
$page = intval($_GET['page']);
$url .= "&page=".$page;
}
// Fetch html code
$html = $this->dlp_get_html($url);
if (is_array($html)){
// error detected:
$res = '<pre>' . print_r($html, true) . '</pre>';
} else {
// Remove line breaks
$html = str_replace(array("\n", "\t", "\r"), '', $html);
// Isolate the__gallery code structure
preg_match('/(<div class=\"the__gallery)(.*)(the__gallery -->)/', $html, $p);
$res = $p ? $p[0] : "<em>Didn't get search term match</em>";
}
return $res;
}
The only item that needs to be updated is the site URL in `dlp_get_smart_album` to match your domain!
Now with the helper functions in place, it is just a matter of adding the search functions to the target albums. This means that you have to create albums without any images first. Then add php code to match the target album and add the matching search term.
function album_top(){
if ($this->dlp_page_match('/galleries/theme/moon')){
echo $this->dlp_get_smart_album('moon');
} elseif ($this->dlp_page_match('/galleries/theme/sf_bridges')){
echo $this->dlp_get_smart_album('"san"+"francisco"+"firework"');
}
return false;
}
As I said before, this is a rather brute force attack to use the search feature embedded in album pages. Since two pages need to be rendered, there is definitely a performance impact. Future changes to Backlight might very well break this behavior. You have been warned!
Please note that when using the single-page view, the user is redirected to the album where the image resides!
If you’d like to use this smart album in a regular page, you need to add an empty album in Backlight in order to have the proper css and javascript, and use the ‘main_top’ or ‘main_bottom’ phplugins function.
Update: Search result paging doesn’t work with regular pages. Unless you know that all images fit into one album, I do not recommend using smart albums with pages.
Remember, Backlight provides many cool features and customization options. It’s search features is really intended for image search and not for what I showed here. There is a reason for that, otherwise smart albums would be a standard feature!
If you have questions, please post them in the comment section.
Have fun!
Did you like this post? Did you use the given code? Please consider supporting me by buying me a coffee!
Thanks!
Fantastic work as always, Daniel. Will be implementing this shortly!
Coffee on the way!
Cheers,
Chumby.
Thank you for the coffee, Chumby! Please let me know how this works for you!
Hi Daniel,
Have modified and uploaded the php plugins page and just trying to display the results of a search for “Ben Lomond” under the content on the page:
https://www.tasmanianphotos.com/ben-lomond/
I have created a blank album
https://www.tasmanianphotos.com/tasmania/theme/ben-lomond/
and using the code below (in the plugins file) to try and display the images on the page. Not working at the moment… I must be missing something.
function main_bottom( ){
if ( $this->dlp_page_match(‘/ben-lomond/’) ) {
echo $this->dlp_get_smart_album(‘”ben”+”lomond”‘);
}
}
Have also tried the path to the album…
dlp_page_match(‘/tasmania/theme/ben-lomond/’) – but not working either.
Any help appreciated and thanks again.
Hi Daniel,
Just looking at inserting the smart album onto a page. Am a little confused with what I need to do as per below and what code I need in my main_bottom() function. Can you shed a little more light? Cheers, Chumby
“If you’d like to use this smart album in a regular page, you need to add an empty album in Backlight in order to have the proper css and javascript, and use the ‘main_top’ or ‘main_bottom’ phplugins function.”
Go to Backlight > Designer > Pages and select your page, then Design. Open the Insert Album section, set Insert Album = ON and select your ’empty’ album. That’s it.
Thanks Daniel,
Have completed that step – just need to make sure my main_bottom() code is correct. I have the below. Is this is what is needed for my search on “Ben Lomond”
function main_bottom( ){
if ( $this->dlp_page_match(‘/ben-lomond/’) ) {
echo $this->dlp_get_smart_album(‘”ben”+”lomond”‘);
}
}
Hi Chumby,
Your use of main_bottom() is correct, but I see a javascript error:
Uncaught TypeError: Failed to execute ‘getComputedStyle’ on ‘Window’: parameter 1 is not of type ‘Element’. (23?ppf=on:511)
at HTMLDivElement.
at Function.each (23?ppf=on:2)
at r.fn.init.each (23?ppf=on:2)
at r.fn.init.t.fn.flexImages (23?ppf=on:511)
at 23?ppf=on:512
Are you using the latest backlight version? Do you use the same album template for your empty album as you do for your search page?
Hi Chumby, working on something else, I just discovered that paging doesn’t work with regular pages.
OK, thanks Daniel.
So does that mean a Smart Album can’t be added to a regular page now?
Hi Chumby, you can, but only as long as you don’t need paging. The maximal number of images per page is 500. This can be set in Backlight > Settings > Items Per Page.
Or you can create smart albums in /Galleries, or make a dedicated top-level gallery where you place them.
Hi Daniel, thanks for your patience here. Just can’t get this working.
Here is what I have done for a new simple search – “snug”. There are 19 images (will never have more than 500 images so displaying on a normal page should be fine) that are retuned on a normal search here.
So I …
– Updated settings to allow 500 images to be displayed
– Created a top level gallery – “themes”
– Under this created album set – “smart”
– Under this created album – “snug”
– Create new page -“snug”
– Inserted album -“snug” (beneath content)
– Have update my domain as tasmanianphotos.com
– Have updated my “main_bottom” with “snug” references
– All templates are the same (searching and page)
So my normal search from my site is:
https://www.tasmanianphotos.com/backlight/search/?q=snug
and my page to display smart album on is:
https://www.tasmanianphotos.com/snug/
(which ends up as tasmanianphotos.com/snug/ in the URL bar after pressing return).
I am using cloudfare to manage my https so I am not sure if that is causing problems at all?
The correct number of images (total) is displayed correctly on tasmanianphotos.com/snug/ (19) so it appears the search is working all ok – just no thumnails of images are being displayed.
I tried this without using an album set as well… still had the same result. Nothing displayed.
Can you spot anything I am doing incorrectly here?
Much appreciate the help.
Cheers,
Chumby.
Hi Chumby, I replied to you by email.
Thanks for all the help with this. Have this working fine now. The temporary server DNS error didn’t help!
Great piece of code, Daniel!
Hi Daniel,
All working well on my site… but would like to include a “smart gallery” on my homepage.
Any ideas of what code needs to change for this.. Need to refer to the default index page.
Cheers
Chumby
The home page is like any other page. I don’t think that you would need to do something special, but I haven’t tried it yet.
You might want to use
function dlp_is_home_page() {
if ( $_SERVER[“REQUEST_URI”] == ‘/’ ) {
return 1;
} else {
return 0;
}
}
instead of dlp_page_match().
Thanks Daniel,
I got it working with the below.
Appreciate the help one again!
Cheers
Chumby
function dlp_is_home_page() {
if ($_SERVER[“REQUEST_URI”] == “/”) {
return 1;
} else {
return 0;
}
}
and in function main_bottom( )
// check if we are on the homepage then insert an album
} elseif ($this->dlp_is_home_page()){
echo $this->dlp_get_smart_album(‘%22west+coast%22’);