Render an element from multiple dimension array in Twig Opencart - twig

I have the following HTML code in a twig view file
<input type="text"
name="myArray[{{ nthRow }}][description][{{ language.language_id }}][name]"
value="{{ myArray.description.language_id.name }}"
class="form-control" />
this is the print_r of the array which is being sent to the twig file
Array (
[0] => Array (
[var1] => safds
[var2] => 0
[var3] => 1000
[description] => Array ( [1] => Array ( [name] => bla bla ) )
)
)
how can I reach the name element of the array??

How about myArray[nthRow].description[language.language_id].name
so the twig code may look like this
<input type="text"
name="myArray[{{ nthRow }}][description][{{ language.language_id }}][name]"
value="{{ myArray[nthRow].description[language.language_id].name }}"
class="form-control" />

I have solved it, it should be like this,
<input type="text"
name="myArray[{{ nthRow }}][description][{{ language.language_id }}][name]"
value="{{ myArray.description[language.language_id].name }}"
class="form-control"
/>

Related

Setting echo $_GET inside of a form

I have the following set up below.
My issue is I'm not sure how to convert an inline echo $_GET. Is it just the same as {{ fn( echo $_GET['units'] === 'Miles' ? 'selected' : null ) }}??
<form method="get" action="{{ post.link }}">
<div>
<span>Find a Store within</span>
<input name="proximity" type="number" placeholder="15" value="<?php echo $_GET['proximity'] ?>" />
<select name="units">
<option value="Miles" <?php echo $_GET['units'] === 'Miles' ? 'selected' : null; ?>>Miles</option>
<option value="K" <?php echo $_GET['units'] === 'K' ? 'selected' : null; ?>>Km</option>
</select>
<span>from</span>
<input name="origin" type="text" placeholder="Your Address" value="<?php echo $_GET['origin'] ?>" />
</div>
<div>
<input type="submit" value="Search" />
Reset
</div>
</form>
Thanks to #DarkBee for pointing the above out: Passing PHP global variables via Twig/Timber
To access $_POST variables, use this:
{{ request.post.name_of_var }}
To access $_GET variables, use this:
{{ request.get.name_of_var }}
So that would make this:
<input name="origin" type="text" placeholder="Your Address" value="<?php echo $_GET['origin'] ?>" />
Be this:
<input name="origin" type="text" placeholder="Your Address" value="{{ request.get.origin}}

Mustache template only sending first word of input to server

I'm using a form to capture information from a list and save it to a new table on my database. When the restaurant name is more than one word, i.e. New York, it will ignore everything after the first word adding only the first word to the database. Is there a way to fix this?
View:
{{#allRestaurantsData}}
<div class="listing">
<form action="/restaurants" method="post">
<h2> {{restaurant.name}}
<input type="image" src="../wishlisticon.png" />
</h2>
<img id="image" src="{{restaurant.featured_image}}" width='500' height='300' alt="picture unavailable">
<ul>
<li>Address :{{ restaurant.location.address}}</li>
<li> {{restaurant.location.locality}}</li>
<li>{{restaurant.location.city}}</li>
<li>{{restaurant.location.zip}}</li>
</ul>
<div id="comments">
</div>
<input type="hidden" name="restaurant_id" value={{restaurant.id}}>
<input type="hidden" name="restaurant_name" value={{restaurant.name}}>
<input type="hidden" name="restaurant_city" value={{restaurant.location.city}}>
</form>
</div>
{{/allRestaurantsData}}
Controller:
router.post("/restaurants", restaurantsModel.create, (req, res, next) => {
console.log("Hitting /restaurants", res.locals.listitem);
});
Model:
restaurantsModel.create = (req, res, next) => {
console.log("from restaurants.Model", req.body);
db
.manyOrNone(
"INSERT INTO restaurants (res_id, name, city) VALUES ($1, $2, $3) RETURNING *;",
[
req.body.restaurant_id,
req.body.restaurant_name,
req.body.restaurant_city
]
)
After a lot of trial an error, I found the answer. I changed added quotation marks to the value inputs in the following two line.
<input type="hidden" name="restaurant_name" value="{{restaurant.name}}" >
<input type="hidden" name="restaurant_city" value="{{restaurant.location.city}}">

How can I extract and store and key/value returned by a server response in pharo/smalltalk

In my ZnClient request I get a response from the server which is a HTML format containing key and value that I would like to extract and store for later use. How do I do it in Pharo?
<div id="login_block">
<div class="text-center"><img src="/static/img/logo-mool2016.black.7272bc78ba54.png" width="223" alt=LOGO" onclick="showChooseLogin();"></div>
<h3 class="text-center">Connectez-vous pour accéder à <span class="product-name">Tool Platform</span></h3>
<div id="login_choosen" class="login_block ui-widget-content ui-corner-all">
<form method="post" action="." id="login_form"><input type='hidden' name='csrfmiddlewaretoken' value='fLTzkLA7yhy7YKDvohM0PJstFJJCEk2JinfjOyzCe2NA495QKznLgO1wzi64P2S8' />
<p><label for="id_email">Email :</label> <input class="login" id="id_email" maxlength="75" name="email" type="text" required /></p>
<p><label for="id_password">Password :</label> <input class="login" id="id_password" name="password" type="password" required /></p>
<button type="submit" class="btn btn-connect pull-right">Connexion</button>
</form>
</div>
</div>
You can extract this information using a HTML parser like Soup.
Here's a cut-down working example:
|content soup dict|
content := '
<div>
<form method="post" action="." id="login_form">
<input type="hidden" name="csrfmiddlewaretoken" value="***special***" />
<input class="login" id="id_email" name="email" type="text" required />
</form>
</div>'.
dict := Dictionary new.
soup := Soup fromString: content.
(soup findAllTags: 'input') do: [ :each |
dict at: (each attributeAt: 'name') put: (each attributeAt: 'value') ].
dict now contains the following:
'csrfmiddlewaretoken'->'***special***'
'email'->nil
You can load XMLParserHTML and XPath from the Pharo Catalog. Then this should do the trick:
| xPath htmlDoc inputs input |
"match inputs with token value of the name attrite"
xPath := '//input[#name="csrfmiddlewaretoken"]' asXPath.
"parse your html"
htmlDoc := (XMLHTMLParser on: htmlString) parseDocument.
"match all inputs with the token"
inputs := xPath in: htmlDoc.
"assuming there is only 1 element like that"
input := inputs first.
"get the value attribute from the element"
^ input attributeAt: 'value'.

How to print string if variable is empty

I have the following HTML/TWIG:
<input type="text" id="username" name="_username" value="{{ last_username }}" />
Now I'd like to use value="Username" if last_username is empty. But I also don't want to make an if for this. So, could I do something like:
<input type="text" id="username" name="_username" value="{{ last_username or 'Username'}}" />
I know that I could set a default value on the logic side of my application - not sure what would be better practice
Use the default filter
<input type="text" id="username" name="_username" value="{{ last_username | default('Username') }}" />

wrap checkboxes with custom html in Twig template using form entity fieldtype (Symfony3)

I would like to wrap the checkboxes with custom HTML in twig template when Symfony3 renders the form.
Instead of this:
<input type="checkbox" id="form_role_1" name="form[role][]" value="1" />
<label for="form_role_1">ROLE 1</label>
<input type="checkbox" id="form_role_2" name="form[role][]" value="2" />
<label for="form_role_2">ROLE 2</label>
<input type="checkbox" id="form_role_3" name="form[role][]" value="3" />
<label for="form_role_3">ROLE 3</label>
I would like to get something like this:
<div class="input-group">
<input type="checkbox" id="form_role_1" name="form[role][]" value="1" />
<label for="form_role_1">ROLE 1</label>
</div>
<div class="input-group">
<input type="checkbox" id="form_role_2" name="form[role][]" value="2" />
<label for="form_role_2">ROLE 2</label>
</div>
<div class="input-group">
<input type="checkbox" id="form_role_3" name="form[role][]" value="3" />
<label for="form_role_3">ROLE 3</label>
</div>
in the controller action:
$form = $this->createForm(RolesFormType::class, $roles);
$form->handleRequest($request);
return $this->render(
'role/edit_roles.html.twig',
array(
'form' => $form->createView()
)
);
in the form type:
class RolesFormType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder
->add('role', EntityType::class, array(
'label' => 'form.elements.roles',
'class' => 'RoleBundle\Entity\Role',
'choice_label' => 'role_name',
'expanded' => true,
'multiple' => true
));
}
}
the classic template looks like this:
<div class="container-fluid">
<div class="row">
{{ form_start(form, {'method': "POST"}) }}
<div class="col-md-12">
<div class="form-group">
{{ form_errors(form.role) }}
{{ form_widget(form.role, {}) }}
</div>
</div>
{{ form_rest(form) }}
{{ form_end(form) }}
</div>
</div>
I tried it this way in the twig template, but only the labels were rendered:
<div class="container-fluid">
<div class="row">
{{ form_start(form, {'method': "POST"}) }}
<div class="col-md-12">
{% for role in form.role %}
<div class="input-group">
{{ form_label(role) }}
{{ form_widget(role) }}
</div>
{% endfor %}
</div>
{{ form_rest(form) }}
{{ form_end(form) }}
</div>
</div>
Is ii possible without creating a new field type?
solution
concerning #xabbuh's answer I found the solution at How to Customize Form Rendering in Symfony 3
I created a folder in my Bundle:
src/RoleBundle/Resources/views/form
and I put a new file (fields.html.twig) into it with this content
{%- block choice_widget_expanded -%}
<div {{ block('widget_container_attributes') }}>
{%- for child in form %}
<div class="input-group">
{{- form_widget(child) -}}
{{- form_label(child, null, {translation_domain: choice_translation_domain}) -}}
</div>
{% endfor -%}
</div>
{%- endblock choice_widget_expanded -%}
In the meantime I found another question which deals with this problem:
Overriding symfony radio widget
You can customise the rendering of your form using a custom form theme. You can so either on the project level or even do that just for a particular form (see How to Customize Form Rendering and How to Work with Form Themes for more information).
Your example looks like you need to override the choice_widget and choice_label
When I play with symfony is not very skilled, I don't often use this accepted solution to solve it
view:
<label class="layui-form-label">所属地市:</label>
<div class="layui-inline">
<select name="{{ form.cityId.vars.full_name }}" lay-verify="" id="{{ form.cityId.vars.id }}" lay-filter="case_city">
<option value="0">请选择</option>
{% if citylist is not empty %}
{% for list in citylist %}
<option value="{{ list.id is defined ? list.id : 0 }}">{{ list.areaName is defined ? list.areaName : '' }}</option>
{% endfor %}
{% endif %}
</select>
</div>
controller:
$caseReg = new CaseRegister();
$form = $this->createForm('Alarm\Component\Form\CaseRegisterType', $caseReg);
$form->handleRequest($request);
$citylist = $this->getDoctrine()->getRepository('AlarmComponent:OfficeArea')->findBy(array('pid'=>0,'status'=>0));
$caseType = $this->getDoctrine()->getRepository('AlarmComponent:CaseType')->findBy(array('status'=>0));
if ($form->isSubmitted()) {
$em = $this->getDoctrine()->getManager();
$param = $request->request->get('alarm_component_caseregister');
if($param['receiveId'] == 0)
{
$case = new CaseType();
$case->setCaseName($param['receiveName']);
$em->persist($case);
$em->flush($case);
$caseReg->setReceiveId($case->getId());
$caseReg->setReceiveName($case->getCaseName());
}
if($param['cityId'] != 0)
{
$city = $this->getDoctrine()->getRepository('AlarmComponent:OfficeArea')->find($param['cityId']);
$caseReg->setCityId($city);
}
if($param['subofficeId'] != 0)
{
$suboffice = $this->getDoctrine()->getRepository('AlarmComponent:OfficeArea')->find($param['subofficeId']);
$caseReg->setSubofficeId($suboffice);
}
$em->persist($caseReg);
$em->flush($caseReg);
return $this->redirectToRoute('case_register_index');
}
return $this->render('AlarmWebBundle:BackendBat\CaseRegister:new.html.twig', array(
'caseReg' => $caseReg,
'form' => $form->createView(),
'citylist' => $citylist,
'casetype' => $caseType
));
It is also can solve my problem, but when I was late to optimize this or they must be altered. But I hope this answer can solve your current problem.

Resources