I have a HelperList in Prestashop (1.6) with a few columns/rows. One of the columns is an anchor element (a href), and I need to show it like that in the list, but Prestashop escapes the value and represents it as a literal string.
How can I show an actual anchor element in one of the columns of a HelperList?
Plus: I'd like to not have to override PS classes nor copy the entire template just to change a single line of code. I do know how to do it using either of those ways, but I'm looking for something less "aggressive".
You can use this trick:
$fields_list = array(
'your_link' => array(
'title' => $this->l('Your title'),
'type' => 'bool',
'float' => true, // a trick - prevents from html escaping
// else code
),
);
Related
I'm trying to combine two data into one column. I already managed to combine two data in one column. But my problem is I don't know how to do a break line to separate the data. I have tried this way but doesn't work.
This is my code
'NAME_PROG_ENG'.'REMARKS' => ['label' => "Programme Name",'value' => function ($data) {return ($data->NAME_PROG_ENG)."\r\n".nl2br("Previously known as: ".($data->REMARKS));}],
I think you refer to GridView component.
Some explanation:
'NAME_PROG_ENG'.'REMARKS' =>
the array index is the model field name, you can't combine 2 columns just by concatenating the column name. In this way you just define a column in the grid wich is not connected to the model. This is not an error, is just to notice that this does not give you the expected result.
'value' => function ($data) {return ($data->NAME_PROG_ENG)."\r\n".nl2br("Previously known as: ".($data->REMARKS));}
Between $data->NAME_PROG_ENG and $data->REMARKS you put a "\r\n" which is fine, but you apply nl2br() function only to the second part of the string.
Now about Gridview. Text are automatically converted to entities, this is a security feature to avoid script injection from user input. If you plan to use input from an untrusted user, ensure that you clean it using htmlpurifier before saving it in database or before showing it (in your 'value'=>... function)
https://www.yiiframework.com/search?language=en&version=2.0&type=guide&q=htmlpurifier
You can bypass html entity conversion by specifies the output format as raw in grid column option
'format'=>'raw'
So you column definition should be something like
'prog_and_remark_combined' => [
'format' => 'raw',
'label' => "Programme Name",
'value' => function ($data) {
return nl2br(
$data->NAME_PROG_ENG .
"\r\nPreviously known as: " .
$data->REMARKS
);
}
],
Gridview allow a short notation
https://www.yiiframework.com/doc/api/2.0/yii-grid-gridview#$columns-detail
which is like this
<column name>:<fomat>:<label>
your code can be as follow as well
'prog_and_remark_combined:raw:Programme Name' => [
'value' => function ($data) {
return nl2br(
$data->NAME_PROG_ENG .
"\r\nPreviously known as: " .
$data->REMARKS
);
}
],
Last note, if the fields does not contain new line to be converted, just concatenate them without using nltobr() function
return $data->NAME_PROG_ENG . "<br>Previously known as: " . $data->REMARKS
I have a Kartik gridview in YII2 and I need to be able to put HTML into the label (not header, I'll come to that) of a column.
My column definition is as such
[
'attribute' => 'picked_percent',
'format' => 'raw',
'label' => 'P<span class="responsive">icked</span>',
],
But if I do this, it outputs
P<span class="drawn_head">icked </span>
I can change label to header and it looks fine but I need it to be clickable and it isn't when I change it to header.
I've also tried changing the format from raw to HTML and that makes no difference.
Any help is much appreciated.
If you want the label to not be encoded you need to add this config option in the column definition array:
'encodeLabel' => false
I'm trying to display some HTML encoded strings as pure HTML in a column positioned in Yii2 GridView. The string that comes from the database looks like this:
Testing <span class='test'>HTML</span>
If I just display it using HTML decode Html::decode($theStringAbove); then I get this in the column:
Testing <span class='test'>HTML</span>
However, what I'm aiming at is simply getting Testing HTML and having the span tag around the HTML word in the code but not displayed as a string.
I've tried setting different values to the format attribute such as raw, url and html to no success. I also have no problem writing a custom function to return the correct output next to the value attribute, it's just that I can't figure out how to get to the output I need. Any suggestions are welcome, thank you!
EDIT: Here's a small code snippet if that's helpful:
[ 'format' => 'raw',
'value' => function($model) { return Html::decode($model->text); },
'label' => Yii::t('app', 'Some Label')]
The database output is probably encoded twice so instead of
Testing <span class='test'>HTML</span>
it's
Testing <span class='test'>HTML</span>
Try to decode it twice like:
'value' => function ($model) {
return Html::decode(Html::decode($model->replace));
}
I have a Year field in a form and I am using FormHelper.
echo $this->Form->input('year', [
'type' => 'year',
'minYear' => date('Y')-10,
'maxYear' => date('Y')
]);
The table file validator looks like:
->add('year', 'valid', ['rule' => 'numeric'])
->allowEmpty('year')
I have a very similar input in another app that seems to work fine. I set the MySql column to int(5) to match what I had working elsewhere.
Checking debugkit it shows the "year" input as an array while the other inputs are strings. If I remove the validation rule it throws an illegal array to string conversion, so I assume this is where the error is.
Any help is greatly appreciated.
I have just tested with your above code and it is working fine for me. Try to delete the cache and check it once more.
Creates a select element populated with the years from minYear to maxYear. Additionally, HTML attributes may be supplied in $options. If $options['empty'] is false, the select will not include an empty option:
empty - If true, the empty select option is shown. If a string, that
string is displayed as the empty element.
orderYear - Ordering of
year values in select options. Possible values ‘asc’, ‘desc’. Default
‘desc’ value The selected value of the input.
maxYear The max year to
appear in the select element.
minYear The min year to appear in the
select element.
Try this one:
<?php
echo $this->Form->year('exp_date', [
'minYear' => date('Y')-10,
'maxYear' => date('Y'),
'id' => 'cc-year',
'class' => 'form-control',
'empty' => false,
'orderYear' => 'asc'
]);
?>
Official Documentation: CookBook - Creating Year Inputs
Normally a widget is used by calling CController::widget() on an instance of CController, typically $this in a view.
But if I'm writing a static method, a helper, say, then I don't have access to an instance of CController. So how do I use a widget?
Let's say further that this helper method is invoked in the eval()’ed expression in a CDataColumn's value property. That poor expression has almost no context at all. How should the helper use a widget?
EDIT: Code example
As requested, a view example:
$this->widget('zii.widgets.grid.CGridView', array(
'dataProvider' => $model->search(),
'columns' => array(
array(
'name' => 'attrName',
'value' => '--USE WIDGET HERE--',
),
)
));
This answer doesn't answer the question in general but in the specific case—how to access the controller and use a widget in the context of the evaluated expression of CDataColumn::$value—you can use this:
$this->widget('zii.widgets.grid.CGridView', array(
'dataProvider' => $model->search(),
'columns' => array(
array(
'name' => 'attrName',
'value' => function ($data, $row, $column) {
$controller = $column->grid->owner;
$controller->widget(/* ... etc ... */);
},
),
)
));
The trick was discovering that CDataColumn::renderDataCellContent() uses CComponent::evaluateExpression(), which injects the component instance into the callback as the last parameter. In this case that omponent is the CDataColumn, which references the controller as shown.
I don't like writing PHP expressions as string literals so I'm pleased to find this option.
A comment on http://www.yiiframework.com/doc/api/1.1/CDataColumn#value-detail shows another way to us a widget in a column value that I haven't tried.
This one is working solution for calling widgets in static methods in Yii
Yii::app()->controller->widget('widget');
There's no direct way to call a widget out of controller because you shouldn't do so. It's all about MVC. Widgets are only needed and/or useful in views, and views are only accessed via controllers. That's the theory.
I guess you're approaching the problem mistakenly. A proper, MVC-friendly way to do what your're trying to do involves using renderPartial(). You know: you a have certain content and you want to decorate it (in your case you want to imbibe it inside a widget, right?) before displaying it to final user; so, from the view, you call renderPartial(). It will send your data to a file where it will properly decorated. renderPartial() returns the content properly formatted and now you can display it in the view.
Unfortunately, in your particular case, you're working with grid view (right?) and, at least from my point of view, it makes the things a bit harder. In order to decorate content for a CGridColumn-subclass element (like CDataColumn), you need to override the renderDataCellContent() method. Check it out here: http://www.yiiframework.com/doc/api/1.1/CDataColumn#renderDataCellContent-detail