I have created a phtml template and I have hook it up with a custom uiComponent model. Then I use knockout to bind model data into the template.
This is working fine at the moment, the problem is I can't pass data from PHP into the JS module I have created.
This is what I have so far :
My layout.xml file to display the phtml template :
<block class="Vendor\Module\Block\Customer\Form" name="vendor_module_template" template="Vendor_Module::template.phtml">
<arguments>
<argument name="jsLayout" xsi:type="array">
<item name="types" xsi:type="array"/>
<item name="components" xsi:type="array">
<item name="custom_component" xsi:type="array">
<item name="component" xsi:type="string">Vendor_Module/js/component</item>
<item name="config" xsi:type="array">
<item name="template" xsi:type="string">path/to/template</item><!-- I can't access this from js -->
<item name="var1" xsi:type="string">some-value</item><!-- I can't access this from js -->
<item name="var2" xsi:type="string">some-other-value</item><!-- I can't access this from js -->
</item>
</item>
</item>
</argument>
</arguments>
</block>
Then I have my phtml template :
<div data-block="refer-friend" data-bind="scope: 'custom_component'">
<form style="display: none;" data-bind="visible: true">
<ul data-bind="foreach: friends, visible: friends().length > 0" class="hidden">
<li>
Email
<input type="text" name="email" data-bind="value: email, disable: isSent" />
</li>
<li>
<p data-bind="if: isSent"><?= __('Sent'); ?></p>
</li>
<li>
<button data-bind="disable: isSent">
<!-- ko if: isSent -->
<!-- ko i18n: 'Re-Send' --><!-- /ko -->
<!-- /ko -->
<!-- ko ifnot: isSent -->
<!-- ko i18n: 'Send' --><!-- /ko -->
<!-- /ko -->
</button>
</li>
</ul>
</form>
</div>
<script type="text/x-magento-init">
{
"[data-block='refer-friend']": {
"Magento_Ui/js/core/app": <?= $block->getJsLayout();?>
}
}
</script>
And then finally my component.js file
define([
'uiComponent',
'jquery',
'ko',
'underscore'
], function (Component, $, ko, _) {
'use strict';
function Friend(data) {
this.email = ko.observable(data.email);
this.isSent = ko.observable(data.isSent);
};
return Component.extend({
friends: ko.observableArray(),
/**
* @override
*/
initialize: function () {
console.log(this.options) ;
this.friends.push(new Friend({email : 'friend1@example.com', isSent : true}));
this.friends.push(new Friend({email : 'friend2@example.com', isSent : false}));
},
});
});
This is all working fine except the fact that I can't access the configuration options I set from the layout xml file.
How can this be done?
Also, I would like to use a knockout html template, which I have seen in the core that they also set from the layout xml but this is not working either when I try it.
Thanks in advance !
Best Answer
You were so close, you're just missing
this._super();
from the initialize function.this._super();
will call the same function it's called in but belonging to the parent, so in this case it will call the initialize function of it's parent (probablyComponent
). If we ran it inside a function namedtest
it would call thetest
function of it's parent component.To check how to access everything passed through to the component console log
this
.