Render file with shortcode into a wordpress plugin - php

I am relatively new to php and wordpress and I would like to know how I can render a php file without the include statement.
For example if I have two files plugin.php and component.php
plugin.php
<?php
add-shortcode('myshortcode', 'myshortcode-func');
function myshortcode-func()
// magic function that loads
$result = LOAD('component.php');
return $result;
}
?>
component.php
<div>
<img scr="<?php getimage() ?>" />
</div>
NB
I don't want to use include because I think it screws the rendering and insert the page in the flow when called.
Thanks for you help !

You can use an output buffer:
function myFunc(){
ob_start();
include('component.php');
return ob_get_clean();
}

How to:
$php = file_get_contents("component.php");
eval($php);
eval is very dangerous though and shouldn't be used in production.
If this is for production, I'd recommend using hooks/filters (see wordpress source code). This lets you execute blocks of code on the fly, but is more constrained.

Related

How to render template through route without any frameworks

I am creating a basic routing system for a bespoke CMS and I am wanting to do this completely in raw PHP without frameworks. So far, I have the routing down, with GET and POST methods working correctly.
Here is my index.php file
<?php
include_once 'Request.php';
include_once 'Router.php';
$router = new Router(new Request);
$router->get('/', function() {
return <<<HTML
<h1>Hello world</h1>
HTML;
});
$router->get('/profile', function($request) {
return <<<HTML
<h1>Profile</h1>
HTML;
});
$router->get('/data', function($request) {
return json_encode($request->getBody());
});
As you can see, for the routes '/' and '/profile' I am returning some HTML code using heredoc. This is okay but will eventually fill up this file really quickly.
Is there a way to render a template (from inside a subfolder for example) in the space of the 'return html code'?
I assume your second parameter for the get method is a callback function that will be triggered in the function if the route matches? If that's the case I don't see why you return the HTML as it isn't used anywhere. You might want to echo() or print() instead.
If you want to return the code and output it later, you need to save the return value into a variable.
No matter which path you choose, you could use another include() and just put the relevant code into a separate file for each path if you want to make your main script more readable.
I'd also recommend to use require_once instead of include_once in the top as there's no point in continuing execution if these class files are missing.

PHP buffer included file as anonymous function

I have a kind of template file that may be called filename.php:
<h1>
<?= $test . ' world'; ?>
</h1>
<p>
Some text
</p>
Then I have a function in an index.php file that looks like this?
<?php
function test($args) {
$test = $args;
include 'filename.php';
}
test('Hello');
test('Hello');
test('Hello');
This code works. It output the included data 3 times.
I can also use output buffering to get the output as a string if I want. However, that's not exactly what I want.
Problem
I can't figure out a way to only need to include the filename.php one time (now it's loaded 3 times). Because it accepts arguments it can't be returned as string. It needs to be returned as an anonymous function, I guess. Then I could buffer my template and still use it with new values.
Any creative ideas are welcome.

How to properly embed HTML code in PHP function

For a Wordpress plugin, I made a function that contains a big HTML portion (following WP docs, I used ob_start and ob_get_clean to insert it):
function myShortcode() {
ob_start();?>
<!-- here a lot of HTML -->
<?php
return ob_get_clean();
}
I would like to put the HTML outside this function and include or require it.
Is this possible? Is there something I should be aware of? Is it preferable file_get_contents? Any other tip is appreciated, thanks in advance
You can move your html to separate file and then include it as simple php file after ob_start()... Yes it will work, just make sure your view.php template partial is Echoing that html, i.e. You may have html outside of php tags e.g.
File view.php
<?php //Template code starts ?>
ALL HTML HERE
<?php // Template code ends ?>
And your current function in current plugin php file will become:
function myShortcode() {
ob_start();
include(PLUGIN_DIR_PATH/templates/view.php);
return ob_get_clean();
}

Generating PDFs from template files using wkhtmltopdf

I need to generate PDF files from HTML templates and plan on using wkhtmltopdf to do that. Inside the HTML templates, I need to be able to use PHP logic to adjust what the template will render. Take this HTML template for example:
<p>Dear <?php echo $firstname; ?>,</p>
<p>Thanks for signing up. You've invited these people along with you:</p>
<ul>
<?php foreach ($invitees as $invitee): ?>
<li><?php echo $invitee; ?></li>
<?php endforeach; ?>
</ul>
<p>Regards,</p>
<p>Chris White</p>
I have no problem being able to pass a HTML template file to wkhtmltopdf but I don't know how to get the PHP logic inside it to run correctly and be able to return the resulting template. I came across this blog post while Googling but the author uses Smarty as a template language: https://davejamesmiller.com/blog/php-html-pdf-conversion-using-wkhtmltopdf
Using Smarty would solve my problem but I don't want to bring in a library to do this when I can just use plain old PHP. Basically, I need a way to pass in variables to the HTML template (in this case $firstname and $invitees), have it execute the PHP code inside the template and then return the resulting template after the PHP has been executed.
Any ideas?
Just save your file as php (for example template.php) and implement there the logic you need.
I did the same also with wkhtmltopdf and it worked great.
I also passed some variables over GET to the template to really get the correct report as pdf.
To save the file I used the PHP session id and saved the file to a folder with write permissions for www-data (Linux) and started the download automatically via Javascript.
I had the same need and I did it like that. Don t really know if my code will help you but why not.
First I used composer to get https://github.com/mikehaertl/phpwkhtmltopdf.
lets say you have a php file " content.php "
<?php
echo "<html>";
echo "<h1>test</h1>";
echo "<html>";
?>
your index.php will be :
<?php
require "vendor/autoload.php";
ob_start();
require('content.php'); //The php file
$content = ob_get_clean();
$pdf = new \mikehaertl\wkhtmlto\Pdf($content);
if (!$pdf->send()) {
throw new Exception('OMG WHY : '.$pdf->getError());
}
If you're not using any template engine, can't u just call your template.php file with some params ?
Something like
$wkhtml2pdf->html2pdf('template.php?firstname=Foo');
(I have no idea how wkhtml2pdf works, this code is just for you to understand the logic)
and in your template.php file :
<p>Dear <?php echo $_GET['firstname']; ?>,</p>

PHP use function as return;?

I'm using include(); to load certain parts of my page, but sometimes if I'm working on a specific area I want the include(); function to terminate somewhere within that included file, so I use return; and everything following that line will not be included when include(); is called on that file. I can't use die(); because sometimes I have other files needed to be included as well.
Now, I want to be able to control that return; function in terms of what other users see, for instance - I'd like to limit what types of users can see beyond that return; line within the included file. I want admin level users to be able to see beyond that point but not regular users. So I use some kind of if() { } statement to check the user type. Sometimes I want only myself to be able to view the content after the return; line, and I then add if($ip != $my_ip) return;.
The problem is that I have to manually write this stuff, but since I use it often I'd like to write a function that I can pass to what users I want to let bypass the return; part. So I setup a terminate(); function, something like this:
function terminate($param) {
// if statement
{
return;
}
}
But the return; line in that function only returns within that function, it doesn't have any effect on the file that called that function. So in other words, the return; line in my terminate(); function won't actually do the return; I need to stop the include(); function going beyond it.
So how do I stop the include(); command on my file going beyond a certain point with a function and have it not interrupt the remaining code after stopping an include();?
Edit: as a temp fix, I'm using this:
if(terminate($param)) return;
So after passing my parameters to the function if it returns true (stop the include();), it will return; on the file I'm including. So it works that way, I'm just wondering if it's possible to just have a terminate($param); command that will fire the return; command on the file that called that function without having to wrap it around in an if() statement?..
In general, most of the modern projects, which are trying to use clean templates with only HTML, that are obeying the MVC architecture, etc, are using conditions in their templates. There's nothing wrong in it. If you are template looks clean.
<div class="content">
<span class="subcontent"> some content </span>
<?php if ($app->UserController->hasPermissions($_SESSION['id'])): ?>
<span class="admincontent"> Admin Content </span>
<?php endif; ?>
</div>
This kind of code is considered OK. Your view DO have conditions and loops. You cannot avoid them. Also it does not look that clean if you have
<div class="content">
<span class="subcontent"> some content </span>
someFunction();
<span class="admincontent"> Admin Content </span>
</div>
Which will also hide all the content till the end of the file. And it's hard to manage it. It's not impossible still. You can use output buffer for that:
Let's say you have:
functions.php
<?php session_start(); $_SESSION['user_id'] = 1; //fictive session code ?>
<?php
function hasPermissions() {
if ($_SESSION['user_id'] != 1) {
ob_end_clean();
}
}
?>
<?php ob_start(); ?>
end.php
<?php $ob = ob_get_contents();?>
<?php ob_end_clean(); ?>
<?= $ob; ?>
Template.php
<?php include("functions.php"); ?>
<p>included content</p>
<?php hasPermissions(); ?>
<p> included content 2 </p>
<?php include("end.php"); ?>
so, if you are with session id = 1, and running Template.php file, the output will be:
included content
included content 2
Else it will output
included content

Categories