I was asked by a friend if I knew of a way to create a currency switcher with ACF since he was creating a property website, and the plugin he was trying to use wasn’t working and the developer wasn’t very helpful with his response.
So I thought this would be a fun little challenge and I would create my own version.
This uses params in the url to pass the currency to the page.
Adding the Param to WordPress
First we need to add the param currency
so that we can use it within WordPress.
function tct_params( $vars ) {
$vars[] .= 'currency';
return $vars;
}
add_filter( 'query_vars', 'tct_params' );
Currency Price Switcher
We next need to create a function that will change the price and currency based on our chosen option. To do this, we first get the price field. My field was called price
however change that to the name of your field. This can be used on both a single post template and in repeater or easy posts.
function tct_currency_price($type=null){
$price = get_field('price'); // Replace with name of your custom field
$currency = sanitize_text_field( get_query_var( 'currency' ) );
switch($type){
case 'price':
switch ($currency) {
case 'USD':
$price = round($price * 1.3915,2);
return '$'.$price;
break;
case 'EUR':
$price = round($price * 1.17122,2);
return '€'.$price;
break;
default:
return '£'.$price;
break;
}
default:
return empty($currency) ? 'GBP' : $currency;
break;
}
}
I am from the UK, so I created this with
GBP/£
as the default currency. You may want to swap this around to work for you.
I used this website to find the conversion price for the currency.
To use it, select dynamic data -> PHP return value.
Function name = tct_currency_price
Argument = price
By passing the word price
into the argument it will return us the actual price.
If we don’t pass an argument in, then it will return us the currency code. For example GBP, USD, EUR etc. If there is no currency param, it defaults to GBP. This is used for the dropdown.
Currency Dropdown
There are two ways you can create this. In the video example, I used the composite elements button dropdown, however I also created a version without the composite elements, incase you don’t have them.
Composite Elements Dropdown
Trigger Button
We can use the previous function we wrote before to get the currency code.
Select the text and use Dynamic Data -> PHP Return Value
Function name = tct_currency_price
(No Argument)
This will pull the current currency into that field.
Dropdown Options
Next I created a function that returns the correct URL depending on your currency that you add.
function tct_currency_url($currency=''){
$currency = !empty($currency) ? $currency : 'GBP';
return get_permalink() . '?currency='.$currency;
}
First we need to add all the currencies that you want to be able to switch between.
Duplicate the row, label it the currency code.
For each dropdown option, you need to add the dynamic link using PHP Return Value.
Function name = tct_currency_url
Argument = USD
Swap the argument with the correct currency code. If none, it defaults to GBP
.
Make sure you add the class
.currency-switcher
to all the dropdown options.
Default Select Dropdown
The other method is using a normal html dropdown. This uses the default browser styling.
Add a codeblock, and add the following inside PHP/HTML
:
<select class="currency-switcher" id="currency-switcher" name="currency" size="1" onchange="window.location.href=this.value;">
<option value="<?php the_permalink(); ?>?currency=GBP">GBP</option>
<option value="<?php the_permalink(); ?>?currency=USD">USD</option>
<option value="<?php the_permalink(); ?>?currency=EUR">EUR</option>
</select>
Add or remove the currency options as you need.
The Javascript
We now need to add the javascript:
jQuery( document ).ready(function() {
const queryString = window.location.search;
const urlParams = new URLSearchParams(queryString);
const currency = urlParams.get('currency')
const getUrl = window.location;
const baseUrl = getUrl.host + "/";
window.addEventListener("click", function(e) {
const href = e.target.getAttribute("href");
let element = e.target.classList.contains('currency-switcher');
if((href.includes(baseUrl) || href.charAt(0) === '/') && (!element) ) {
location.href = href + '?currency='+currency;
e.preventDefault();
}
});
// Only need to add this if you are using the default select dropdown
jQuery("#currency-switcher > option").each(function() {
if(currency === this.text){
//console.log(this.text + ' ' + this.value);
this.selected = true;
}
});
// End of default dropdown
});
Theres a lot going on here. Let’s break it down:
const queryString = window.location.search;
const urlParams = new URLSearchParams(queryString);
const currency = urlParams.get('currency')
const getUrl = window.location;
const baseUrl = getUrl.host + "/";
This gets the url and finds the param currency
and gets the value attached to it.
We also then get the host name. This is the name of your website. mydomain.com
for example.
window.addEventListener("click", function (e) {
const href = e.target.getAttribute("href");
let element = e.target.classList.contains("currency-switcher");
console.log(element);
if ((href.includes(baseUrl) || href.charAt(0) === "/") && element == false) {
location.href = href + "?currency=" + currency;
e.preventDefault();
}
});
We are adding an event listener to any click, getting the link href. Then checking if that element has the class of currency-switcher
.
Using an if
statement we are able to check that the link href contains our baseURL that we set above, or that the href starts with a /
this is how we know the domain is an internal link and not an outbound link to amazon.com
for example. Then the last check is to make sure that the element doesn’t have the class currency-switcher
as this will cause the dropdown links to have the param twice.
We now use e.preventDefault()
to stop the link redirecting as we are going to be adding our own params to the end of the link before we redirect. All we are doing is concatenating the currency from the current URL to the new URL that we are going to.
jQuery("#currency-switcher > option").each(function () {
if (currency === this.text) {
//console.log(this.text + " " + this.value);
this.selected = true;
}
});
This code is only needed if you are using the default select dropdown
as it sets the active currency code as the selected option.
Thats it!
I hope this helps. It was a fun challenge to build.