This is my function:
function bbc2html($content) {
$search = array (
'/(\[b\])(.*?)(\[\/b\])/',
'/(\[u\])(.*?)(\[\/u\])/',
'/(\[i\])(.*?)(\[\/i\])/',
'/(\[youtube\])(.*?)(\[\/youtube\])/'
);
$replace = array (
'<b>$2</b>',
'<u>$2</u>',
'<i>$2</i>',
'<div style="width: 25rem;">
<div data-source="'.getYoutubeVideoID('$2').'" data-type="youtube">
<p >As soon as you click on the button you accept that cookies from YouTube to be loaded</p>
<input type="button" value="OK">
<a href="$2" type="button" target="_blank" ><i ></i>direct link</a>
</div>
<div style="display: none;">
<iframe src="" border="0" data-scaling="true" data-format="16:9" style="height: 0px;"></iframe>
</div>
</div>'
);
return preg_replace($search, $replace , $content);
}
function getYoutubeVideoID($link):string{
$baseUrl = parse_url($link, PHP_URL_HOST);
if($baseUrl == "youtu.be"){
$urlParts = explode('/',$link);
$id = end($urlParts);
} elseif (preg_match('/(youtube.com)/i',$baseUrl)) {
if(preg_match('/(youtube.com\/watch\?v=)/i',$link)){
$urlParts = explode('?v=',$link);
$id = end($urlParts);
} elseif(preg_match('/(youtube.com\/)/i',$link)) {
$urlParts = explode('/',$link);
$id = end($urlParts);
} else {
return "";
}
} else {
return "";
}
return $id;
}
I want to pass the variable ($2, contains the link to the youtube video) to the function (getYoutubeVideoID, returns only the id of the video), but it just pass '$2' instead of the link.
Example: [youtube] https://www.youtube.com/watch?v=LXb3EKWsInQ [/youtube]
This should be replaced with:
<div style="width: 25rem;">
<div data-source="LXb3EKWsInQ" data-type="youtube">
<p >As soon as you click on the button you accept that cookies from YouTube to be loaded</p>
<input type="button" value="OK">
<a href="https://www.youtube.com/watch?v=LXb3EKWsInQ" type="button" target="_blank" ><i ></i>direct link</a>
</div>
<div style="display: none;">
<iframe src="" border="0" data-scaling="true" data-format="16:9" style="height: 0px;"></iframe>
</div>
</div>
CodePudding user response:
The standard preg_replace
doesn't allow you to execute a function on the replacement values, you can only pass literals with replacement placeholders.
You can get around this in multiple ways, however preg_replace_callback
with that specific case might be the easiest to read. In the following code I also took the liberty of combining your first three shortcodes into a single one that uses a back-reference. I also removed captures that you we're using (for no good reason except to help me debug).
<?php
var_dump(bbc2html('[b]stuff[/b][youtube]abc[/youtube]'));
function getYoutubeVideoID($id)
{
// Just a demo function
return '!!'.$id.'!!';
}
function bbc2html($content)
{
$search = '/\[(b|u|i)]([^\[]*)\[\/\1]/';
$replace = '<$1>$2</$1>';
$newContent = preg_replace($search, $replace, $content);
return preg_replace_callback(
'/\[youtube](.*?)\[\/youtube]/',
static function ($matches) {
return '<div style="width: 25rem;">
<div data-source="'.getYoutubeVideoID($matches[1]).'" data-type="youtube">
<p >As soon as you click on the button you accept that cookies from YouTube to be loaded</p>
<input type="button" value="OK">
<a href="$2" type="button" target="_blank" ><i ></i>direct link</a>
</div>
<div style="display: none;">
<iframe src="" border="0" data-scaling="true" data-format="16:9" style="height: 0px;"></iframe>
</div>
</div>';
},
$newContent
);
}
Demo: https://3v4l.org/0hkQj