# Creating a Magento Widget

The Magento Developer Docs have a [great guide](https://devdocs.magento.com/guides/v2.4/ext-best-practices/tutorials/custom-widget.html) for creating a widget. Lets walk through what you need to do to create a new widget to later make it work with Scandi.

## Create the Widget Block

Create a Block class for the widget. It needs to extend `Template` and implement the `BlockInterface`. Other than that, the only thing we need to do is specify the `_template` the widget uses.

{% code title="app/code/ScandiTutorials/CustomWidget/Block/Widget/NewsletterWidget.php" %}

```php
<?php declare(strict_types=1);

namespace ScandiTutorials\\CustomWidget\\Block\\Widget;

use Magento\\Framework\\View\\Element\\Template;
use Magento\\Widget\\Block\\BlockInterface;

class NewsletterWidget extends Template implements BlockInterface
{
    protected $_template = "widget/newsletter_widget.phtml";
}
```

{% endcode %}

But we haven't created the template yet! So let's do that next. If you were writing the template for Magento, you would need to render all the elements needed for the widget.

However, since all the Scandi rendering logic happens on the frontend using React, the template can be much simpler. The template merely needs to render a single element to specify the widget type.

This is also where we "send" all the widget parameters to the frontend. Let's say our widget will have a single String parameter, the title. We can get that parameter with `$block->escapeHtml($block->getData('title'))` and assign it to the `data-title` attribute:

{% code title="app/code/ScandiTutorials/CustomWidget/view/frontend/templates/widget/newsletter\_widget.phtml" %}

```php
<?php
/** ScandiTutorials\\CustomWidget\\Block\\Widget\\NewsletterWidget $block */
?>
<widget type="newsletter" data-title="<?= $block->escapeHtml($block->getData('title')) ?>"></widget>
```

{% endcode %}

You may realize that `widget` is not a real element type, and both attributes are custom too. This is ok, because all the HTML will get parsed on the frontend to render a custom React element.

For now, we haven't implemented any rendering on the frontend yet. So if you create a test page with this widget and view it, you won't see it. However, if you check the CMS content response received from the server, you'll see that the widget is there!

```javascript
{
  "data": {
    "cmsPage": {
      "title": "test",
      "content": "<widget type=\\"newsletter\\" data-title=\\"hello world\\"></widget>\\n",
      "page_width": "default",
      "content_heading": "",
      "meta_title": "",
      "meta_description": "",
      "meta_keywords": ""
    }
  }
}
```
