Call static function in Twig - twig

I am pretty new to Twig. I have a class called Session and a static function called get I want to return the content of Session::get('user_name'). Is it even possible without modifying anything?
I tried {{ constant('Namespace\\Session::get("user_name")') }} and {{ Session.get('user_name') }} but it doesn't seem to work.

You could use Twig Extension like below:
class CustomExtension extends \Twig_Extension {
public function getFunctions() {
return array(
new \Twig_SimpleFunction('static_call', array($this, 'staticCall')),
);
}
function staticCall($class, $function, $args = array()) {
if (class_exists($class) && method_exists($class, $function)) {
return call_user_func_array(array($class, $function), $args);
}
return null;
}
}
Usage in in twig:
{{ static_call('AppBundle\\Entity\\YourEntity', 'GetSomething', ['var1', 'var2']) }}

I found the answer. I simply added the following code right after new Twig_Enviroment($twig_loader)
$twig = new Twig_Environment($twig_loader);
$twig->addFunction('_call', new Twig_Function_Function(
function($class, $function, $arguments = array())
{
return call_user_func(array($class, $function), $arguments);
})
);
In Twig
{{ _call('Session', 'get', 'user_name')|raw }}

Related

Builder could not be converted to string

Need help, I want to sum one column in codeigniter4 but I get this error:
Error: object of class CodeIgniter\Database\MySQLi\Builder could not be converted to string
This is my model:
public function tot_crew_wni_arr() {
return $this->db->table('tbl_est_arr')->selectSum('crew_wni_arr');
}
at controller
$data = array(
'tot_crew_wni_arr' => $this->Model_home->tot_crew_wni_arr(),
);
return view('layout/v_wrapper', $data);
This is my view:
<h3><?= $tot_crew_wni_arr ?></h3>
Your model function should look something like this:
public function tot_crew_wni_arr() {
$db = \Config\Database::connect();
$builder = $db->table('tbl_est_arr');
return $builder->selectSum('crew_wni_arr')->get();
}

Overwrite backend template in bolt.cms

I am trying to overwrite a template file located in vendor/bolt/bolt/app/view/twig/editcontent/fields/_block.twig (I want to replace the "block selection" dropdown). Regarding to #1173, #1269, #5588, #3768 and #5102 this is not supported by default so I have to write a extension for this. So I tried this:
BackendBlockSelectionExtension:
namespace Bundle\Site;
use Bolt\Filesystem\Adapter\Local;
use Bolt\Filesystem\Filesystem;
use Silex\Application;
use Bolt\Extension\SimpleExtension;
class BackendBlockSelectionExtension extends SimpleExtension
{
public function getServiceProviders()
{
return [
$this,
new BackendBlockSelectionProvider(),
];
}
}
BackendBlockSelectionProvider:
namespace Bundle\Site;
use Bolt\Filesystem\Adapter\Local;
use Bolt\Filesystem\Filesystem;
use Silex\Application;
use Silex\ServiceProviderInterface;
class BackendBlockSelectionProvider implements ServiceProviderInterface
{
public function register(Application $app)
{
$side = $app['config']->getWhichEnd();
if ($side == 'backend') {
$path = __DIR__ . '/App/templates/Backend';
$filesystem = $app['filesystem'];
$filesystem->mountFilesystem('bolt', new Filesystem(new Local($path)));
$app['twig.loader.bolt_filesystem'] = $app->share(
$app->extend(
'twig.loader.bolt_filesystem',
function ($filesystem, $app) {
$path = __DIR__ . 'src/App/templates/Backend/';
$filesystem->prependPath($path, 'bolt');
return $filesystem;
}
)
);
}
}
public function boot(Application $app)
{
}
}
This seems to do the job, but I got an error I don't understand at all: The "bolt://app/theme_defaults" directory does not exist.
So my final question is: Does anyone have some example code how to overwrite/modify vendor/bolt/bolt/app/view/twig/editcontent/fields/_block.twig without touching the vendor folder?
This should be much simplier than this.
In your extension class overwrite protected function registerTwigPaths() function like this:
protected function registerTwigPaths()
{
if ($this->getEnd() == 'backend') {
return [
'view' => ['position' => 'prepend', 'namespace' => 'bolt']
];
}
return [];
}
private function getEnd()
{
$backendPrefix = $this->container['config']->get('general/branding/path');
$end = $this->container['config']->getWhichEnd();
switch ($end) {
case 'backend':
return 'backend';
case 'async':
// we have async request
// if the request begin with "/admin" (general/branding/path)
// it has been made on backend else somewhere else
$url = '/' . ltrim($_SERVER['REQUEST_URI'], $this->container['paths']['root']);
$adminUrl = '/' . trim($backendPrefix, '/');
if (strpos($url, $adminUrl) === 0) {
return 'backend';
}
default:
return $end;
}
}
Now you can crete a view directory in your extensions directory in which you can define templates in structure like in Bolt's default. I would start with copy and overwrite.

Groovy TemplateEngine - function for markup creation

I'm a JS programmer trying to write some Groovy code (with no Java background at all). I need to write some templates using Groovy, so I created a function in order to avoid repetition. My goal is to be able to pass html objects to the function (for example: p(), div(), span() and so on), but is isn't working as I expected:
The function
void addon ( addonType, mainHolder, content ) {
div( class: "addon " + addonType ) {
div( class: "addon-main" ) {
div( class: "addon-main-holder" ) {
yieldUnescaped mainHolder
}
}
div( class: "addon-content" ) {
yieldUnescaped content
}
}
}
Doesn't works:
[...]
body {
addon( 'addon-warning', p('Lorem Ipsum'), p('Dolor sit amet consectetur') )
}
[...]
Works:
[...]
body {
addon( 'addon-warning', '<p>Lorem Ipsum</p>', '<p>Dolor sit amet consectetur</p>') )
}
[...]
I tried some variations, using yield rather than yieldUnescaped, but no success. Is it possible? Any help would be much appreciated.
Assuming you want to pass in further DSL-based tags into your addon function, I'd pass closure to that function instead. This is an simplified, self containing version (which makes it bit harder to read, as the template is in a string; take a look at the XXX comments):
import groovy.text.markup.*
def config = new TemplateConfiguration()
def engine = new MarkupTemplateEngine(config)
def template = engine.createTemplate('''
html {
body {
addon("Hello World", { // XXX: pass a closure
p("Lorem Ipsum")
p("Lorem Ipsum")
p("Lorem Ipsum")
})
}
}
void addon(title, content) {
h1(title)
div {
content() // XXX call the closure
}
}
''')
Writable output = template.make([:])
println output
// => <html><body><h1>Hello World</h1><div><p>Lorem Ipsum</p><p>Lorem Ipsum</p><p>Lorem Ipsum</p></div></body></html>

Grav CMS: Output message in the Debug Bar from native PHP

I'm working on a custom Twig filter which resizes your images to a set width (and auto height).
{# TWIG CODE #}
{% set imgpath = page.header.custom.bgimage|first.path %}
<div class="thumb" style="background-image: url({{ url(imgpath|resize(240)) }})"></div>
It works great so far, but I encountered some errors when the ordering of the pages is changed. I'd like to use the Grav Debug Bar for debugging, since it's very convenient and keeps the code clean.
Inside Twig, you can simply use {{ dump(message) }}.
Unfortunately the resizing process happens inside native PHP, so I need a way to output messages from PHP to the Grav Debug Bar.
As stated inside the Docs, you can use $grav['debugger']->addMessage($this).
This throws an error when calling the resize Twig filter:
Twig_Error_Runtime
An exception has been thrown during the rendering of a template ("Undefined variable: grav").
Why is the variable $grav undefined?
<?php namespace Grav\Common;
use \Grav\Common\Grav;
use \Grav\Common\Page\Page;
use \RocketTheme\Toolbox\ResourceLocator\UniformResourceLocator;
use \Eventviva\ImageResize;
include_once getcwd().'/user/plugins/resizer/lib/ImageResize.php';
class TwigResizerFilters extends \Twig_Extension
{
private $grav;
public function __construct() {
$this->grav = Grav::instance();
}
public function getName() {
return 'TwigResizeFilters';
}
public function getFilters() {
return [
new \Twig_SimpleFilter( 'resize', [$this, 'resizeImage'] )
];
}
public function resizeImage($mediapath, $maxWidth = 1920) {
if (file_exists($mediapath)) {
// if file exists
if ($currImg = getimagesize($mediapath)) {
// if is image
if (preg_match('(jpg|jpeg|png)', $currImg['mime'])) {
// if file format correct
$resizedFolder = 'images/resized/';
// calculate exact img dimensions for proper naming
$maxHeight = floor(($maxWidth/$currImg[0]) * $currImg[1]);
if (!file_exists($resizedFolder)) {
// create folder if it does not exist
mkdir($resizedFolder, 0777, true);
}
// create filename
$resizedExtension = '.'.pathinfo($mediapath, PATHINFO_EXTENSION);
$resizedFilename = basename($mediapath, $resizedExtension).'#'.$maxWidth.'x'.$maxHeight.$resizedExtension;
if (file_exists($resizedFolder.$resizedFilename)) {
// if file already has been cached, just potput
return $resizedFolder.$resizedFilename;
} else {
// if not cached, resize to desired size
$image = new ImageResize($mediapath);
$image->resize($maxWidth, $maxHeight);
$image->save($resizedFolder.$resizedFilename);
return $resizedFolder.$resizedFilename;
}
} else {
$grav['debugger']->addMessage("File type of ".$mediapath." is not supported.");
}
} else {
$grav['debugger']->addMessage($mediapath." is not an image.");
}
} else {
$grav['debugger']->addMessage("File ".$mediapath." does not exist.");
}
}
private function mergeConfig( Page $page ) {
$defaults = (array) $this->grav['config']->get('plugins.resizer');
if ( isset($page->header()->resizer) ) {
$this->grav['config']->set('plugins.resizer', array_merge($defaults, $page->header()->resizer));
}
}
}

Moodle 2.7 - Update core_renderer.php not applying changes - Custom menu

I am developing a custom theme based on bootstrap for moodle 2.7. I am adding a simple class to the custom menu function (render_custom_menu) on line 80. I simply addded the navbar-right class that is applied to the standard menu shown in both code blocks below.
Custom menu:
protected function render_custom_menu(custom_menu $menu) {
global $CFG, $USER;
// TODO: eliminate this duplicated logic, it belongs in core, not
// here. See MDL-39565.
$content = '<ul class="nav navbar-nav navbar-right">';
foreach ($menu->get_children() as $item) {
$content .= $this->render_custom_menu_item($item, 1);
}
return $content.'</ul>';
}
Standard Menu:
protected function render_user_menu(custom_menu $menu) {
global $CFG, $USER, $DB;
$addusermenu = true;
$addlangmenu = true;
$langs = get_string_manager()->get_list_of_translations();
if (count($langs) < 2
or empty($CFG->langmenu)
or ($this->page->course != SITEID and !empty($this->page->course->lang))) {
$addlangmenu = false;
}
if ($addlangmenu) {
$language = $menu->add(get_string('language'), new moodle_url('#'), get_string('language'), 10000);
foreach ($langs as $langtype => $langname) {
$language->add($langname, new moodle_url($this->page->url, array('lang' => $langtype)), $langname);
}
}
if ($addusermenu) {
if (isloggedin()) {
$usermenu = $menu->add(fullname($USER), new moodle_url('#'), fullname($USER), 10001);
$usermenu->add(
'<span class="glyphicon glyphicon-off"></span>' . get_string('logout'),
new moodle_url('/login/logout.php', array('sesskey' => sesskey(), 'alt' => 'logout')),
get_string('logout')
);
$usermenu->add(
'<span class="glyphicon glyphicon-user"></span>' . get_string('viewprofile'),
new moodle_url('/user/profile.php', array('id' => $USER->id)),
get_string('viewprofile')
);
$usermenu->add(
'<span class="glyphicon glyphicon-cog"></span>' . get_string('editmyprofile'),
new moodle_url('/user/edit.php', array('id' => $USER->id)),
get_string('editmyprofile')
);
} else {
$usermenu = $menu->add(get_string('login'), new moodle_url('/login/index.php'), get_string('login'), 10001);
}
}
$content = '<ul class="nav navbar-nav navbar-right">';
foreach ($menu->get_children() as $item) {
$content .= $this->render_custom_menu_item($item, 1);
}
return $content.'</ul>';
}
I'm not sure why this change is not taking effect. Anyone have experience with this and how to solve it. I'm sure I'm overlooking something very simple.
FYI: I have purged the moodle cache many times, reset the server and cleared the history in the browser.
Thanks!

Resources