DiceImageFormFields.jsx 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132
  1. import React from "react";
  2. import { useTranslation } from "react-i18next";
  3. import { Field } from "react-final-form";
  4. import Label from "../../ui/formUtils/Label";
  5. import Hint from "../../ui/formUtils/Hint";
  6. import { ImageField } from "../../mediaLibrary";
  7. import { useItemActions } from "react-sync-board";
  8. import { nanoid } from "nanoid";
  9. const Form = ({ initialValues }) => {
  10. const { t } = useTranslation();
  11. const { batchUpdateItems } = useItemActions();
  12. React.useEffect(() => {
  13. if (!initialValues.images) {
  14. // When selecting multiple images
  15. return;
  16. }
  17. if (initialValues.images.length < initialValues.side) {
  18. // Add emtpy element
  19. batchUpdateItems([initialValues.id], (prevItem) => {
  20. const newItem = { ...prevItem };
  21. newItem.images = [...newItem.images];
  22. newItem.images.push({ id: nanoid(), type: "empty" });
  23. return newItem;
  24. });
  25. }
  26. if (initialValues.images.length > initialValues.side) {
  27. // remove element
  28. batchUpdateItems([initialValues.id], (prevItem) => {
  29. const newItem = { ...prevItem };
  30. newItem.images = newItem.images.slice(0, newItem.images.length);
  31. newItem.images.pop();
  32. return newItem;
  33. });
  34. }
  35. }, [
  36. initialValues.side,
  37. initialValues.images,
  38. initialValues.id,
  39. batchUpdateItems,
  40. ]);
  41. return (
  42. <>
  43. <Label>
  44. {t("Label")}
  45. <Field
  46. name="label"
  47. component="input"
  48. initialValue={initialValues.label}
  49. />
  50. </Label>
  51. <Label>
  52. {t("Width")}
  53. <Field
  54. name="width"
  55. component="input"
  56. initialValue={initialValues.width}
  57. >
  58. {(props) => <input {...props.input} type="number" />}
  59. </Field>
  60. </Label>
  61. <Label>
  62. {t("Height")}
  63. <Field
  64. name="height"
  65. component="input"
  66. initialValue={initialValues.height}
  67. >
  68. {(props) => <input {...props.input} type="number" />}
  69. </Field>
  70. </Label>
  71. <Label>
  72. {t("Roll on move")}
  73. <Field
  74. name="rollOnMove"
  75. component="input"
  76. type="checkbox"
  77. initialValue={initialValues.rollOnMove}
  78. />
  79. <Hint>{t("Check it to roll the dice after each move.")}</Hint>
  80. </Label>
  81. <Label>
  82. {t("Side count")}
  83. <Field
  84. name="side"
  85. component="input"
  86. initialValue={initialValues.side || 6}
  87. >
  88. {(props) => {
  89. const onChange = (newValue) => {
  90. const parsed = parseInt(newValue.target.value, 10);
  91. const nextValue = parsed > 1 ? parsed : 1;
  92. props.input.onChange(nextValue);
  93. };
  94. return (
  95. <input
  96. value={props.input.value}
  97. onChange={onChange}
  98. type="number"
  99. />
  100. );
  101. }}
  102. </Field>
  103. </Label>
  104. {(initialValues.images || []).map(({ id }, index) => {
  105. return (
  106. <Label key={id}>
  107. {t("Dice image {{index}}", { index: index + 1 })}
  108. <Field
  109. name={`images[${index}]`}
  110. initialValue={initialValues.images[index]}
  111. >
  112. {({ input: { value, onChange } }) => {
  113. return <ImageField value={value} onChange={onChange} />;
  114. }}
  115. </Field>
  116. </Label>
  117. );
  118. })}
  119. </>
  120. );
  121. };
  122. export default Form;