Skip to content
Draft
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
various fixes
  • Loading branch information
dunglas committed Jul 19, 2022
commit f0b954288747d863980e2bca06a423aed7a7de0d
27 changes: 19 additions & 8 deletions src/Collection/Resources/assets/dist/controller.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,10 @@ import { Controller } from '@hotwired/stimulus';
const DEFAULT_ITEMS_SELECTOR = ':scope > :is(div, fieldset)';
var ButtonType;
(function (ButtonType) {
ButtonType["Add"] = "add";
ButtonType["Delete"] = "delete";
ButtonType[ButtonType["Add"] = 0] = "Add";
ButtonType[ButtonType["Delete"] = 1] = "Delete";
})(ButtonType || (ButtonType = {}));
class controller extends Controller {
class default_1 extends Controller {
connect() {
this.connectCollection(this.element);
}
Expand All @@ -16,19 +16,24 @@ class controller extends Controller {
const items = this.getItems(collectionEl);
collectionEl.dataset.currentIndex = items.length.toString();
this.addAddButton(collectionEl);
this.getItems(collectionEl).forEach(itemEl => this.addDeleteButton(collectionEl, itemEl));
this.getItems(collectionEl).forEach((itemEl) => this.addDeleteButton(collectionEl, itemEl));
});
}
getItems(collectionElement) {
return collectionElement.querySelectorAll(collectionElement.dataset.itemsSelector || DEFAULT_ITEMS_SELECTOR);
}
createButton(collectionEl, buttonType) {
const buttonTemplateID = collectionEl.dataset[`${buttonType}ButtonTemplateId`];
var _a;
const attributeName = `${ButtonType[buttonType].toLowerCase()}ButtonTemplateId`;
const buttonTemplateID = (_a = collectionEl.dataset[attributeName]) !== null && _a !== void 0 ? _a : this[`${attributeName}Value`];
if (buttonTemplateID && 'content' in document.createElement('template')) {
const buttonTemplate = document.getElementById(buttonTemplateID);
if (!buttonTemplate)
throw new Error(`element with ID "${buttonTemplateID}" not found`);
return buttonTemplate.content.cloneNode(true);
throw new Error(`template with ID "${buttonTemplateID}" not found`);
const fragment = buttonTemplate.content.cloneNode(true);
if (1 !== fragment.children.length)
throw new Error('template with ID "${buttonTemplateID}" must have exactly one child');
return fragment.firstElementChild;
}
const button = document.createElement('button');
button.type = 'button';
Expand Down Expand Up @@ -67,5 +72,11 @@ class controller extends Controller {
itemEl.appendChild(deleteButton);
}
}
default_1.values = {
addButtonTemplateId: "",
disableAddButton: false,
deleteButtonTemplateId: "",
disableDeleteButton: false,
};

export { controller as default };
export { default_1 as default };
23 changes: 18 additions & 5 deletions src/Collection/Resources/assets/src/controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,18 @@ interface CollectionDataset extends DOMStringMap {
}

enum ButtonType {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be a const enum instead, to inline the add and remove string in the emitted JS code instead of emitting an enum object.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I changed the code and using const enum isn't possible anymore (IIRC, const enum causes various issues anyway).

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Another alternative is to use a tagged union 'add' | 'remove', which will then produce more efficient JS code.

Add = 'add',
Delete = 'delete',
Add,
Delete,
}

export default class extends Controller {
static values = {
addButtonTemplateId: "",
disableAddButton: false,
deleteButtonTemplateId: "",
disableDeleteButton: false,
};

connect() {
this.connectCollection(this.element as HTMLElement);
}
Expand All @@ -39,13 +46,19 @@ export default class extends Controller {
}

createButton(collectionEl: HTMLElement, buttonType: ButtonType): HTMLElement {
const buttonTemplateID = collectionEl.dataset[`${buttonType}ButtonTemplateId`];
const attributeName = `${ButtonType[buttonType].toLowerCase()}ButtonTemplateId`;
const buttonTemplateID = collectionEl.dataset[attributeName] ?? (this as any)[`${attributeName}Value`];
if (buttonTemplateID && 'content' in document.createElement('template')) {
// Get from template
const buttonTemplate = document.getElementById(buttonTemplateID) as HTMLTemplateElement | null;
if (!buttonTemplate) throw new Error(`element with ID "${buttonTemplateID}" not found`);
if (!buttonTemplate)
throw new Error(`template with ID "${buttonTemplateID}" not found`);

const fragment = (buttonTemplate.content.cloneNode(true) as DocumentFragment);
if (1 !== fragment.children.length)
throw new Error('template with ID "${buttonTemplateID}" must have exactly one child');

return buttonTemplate.content.cloneNode(true) as HTMLElement;
return fragment.firstElementChild as HTMLElement;
}

// If no template is provided, create a raw HTML button
Expand Down
6 changes: 3 additions & 3 deletions src/Collection/Tests/app/Kernel.php
Original file line number Diff line number Diff line change
Expand Up @@ -69,15 +69,15 @@ protected function configureRoutes(RoutingConfigurator $routes): void
$routes->import('@WebProfilerBundle/Resources/config/routing/wdt.xml')->prefix('/_wdt');
$routes->import('@WebProfilerBundle/Resources/config/routing/profiler.xml')->prefix('/_profiler');

$routes->add('form', '/')->controller('kernel::form');
$routes->add('form', '/{type<^basic|template$>?basic}')->controller('kernel::form');
}

public function getProjectDir(): string
{
return __DIR__;
}

public function form(Request $request, Environment $twig, FormFactoryInterface $formFactory): Response
public function form(Request $request, Environment $twig, FormFactoryInterface $formFactory, string $type): Response
{
$form = $formFactory->create(GameType::class);

Expand All @@ -88,7 +88,7 @@ public function form(Request $request, Environment $twig, FormFactoryInterface $
}

return new Response(
$twig->render('form.html.twig', ['form' => $form->createView()])
$twig->render("{$type}_form.html.twig", ['form' => $form->createView()])
);
}
}
1 change: 1 addition & 0 deletions src/Collection/Tests/app/assets/app.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,5 +12,6 @@ import Controller from "@symfony/ux-collection/dist/controller.js";

const application = Application.start();
application.register("symfony--ux-collection--collection", Controller);
application.register("collection", Controller);

console.log('test app initialized');
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{% extends 'base.html.twig' %}

{% block body %}
<div data-controller="symfony--ux-collection--collection">
<div data-controller="symfony--ux-collection--collection" >
{{ form(form) }}
</div>
{% endblock %}
15 changes: 15 additions & 0 deletions src/Collection/Tests/app/templates/template_form.html.twig
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
{% extends 'base.html.twig' %}

{% block body %}
<template id="addButton">
<button type="button">My add button</button>
</template>

<template id="deleteButton">
<button type="button">My delete button</button>
</template>

<div data-controller="symfony--ux-collection--collection" data-symfony--ux-collection--collection-add-button-template-id-value="addButton" data-symfony--ux-collection--collection-delete-button-template-id-value="deleteButton">
{{ form(form) }}
</div>
{% endblock %}