blocks.py 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155
  1. from django import forms
  2. from wagtail.blocks import (
  3. CharBlock,
  4. ChoiceBlock,
  5. FloatBlock,
  6. ListBlock,
  7. RichTextBlock,
  8. StreamBlock,
  9. StructBlock,
  10. )
  11. from wagtail.contrib.table_block.blocks import TableBlock
  12. from wagtail.contrib.typed_table_block.blocks import TypedTableBlock
  13. from wagtail.embeds.blocks import EmbedBlock
  14. from wagtail.images.blocks import ImageBlock
  15. from bakerydemo.base.blocks import (
  16. BlockQuote,
  17. HeadingBlock,
  18. get_image_api_representation,
  19. )
  20. class CustomImageBlock(ImageBlock):
  21. def get_api_representation(self, value, context=None):
  22. data = super().get_api_representation(value, context)
  23. data["image"] = get_image_api_representation(value)
  24. return data
  25. class RecipeStepBlock(StructBlock):
  26. text = RichTextBlock(features=["bold", "italic", "link"])
  27. difficulty = ChoiceBlock(
  28. widget=forms.RadioSelect,
  29. choices=[("S", "Small"), ("M", "Medium"), ("L", "Large")],
  30. default="S",
  31. )
  32. class Meta:
  33. template = "blocks/recipe_step_block.html"
  34. icon = "tick"
  35. class RecipeStreamBlock(StreamBlock):
  36. """
  37. Define the custom blocks that `StreamField` will utilize
  38. """
  39. heading_block = HeadingBlock(group="Content")
  40. paragraph_block = RichTextBlock(
  41. icon="pilcrow", template="blocks/paragraph_block.html", group="Content"
  42. )
  43. block_quote = BlockQuote(group="Content")
  44. table_block = TableBlock(
  45. group="Content",
  46. description="A table of data with plain text cells",
  47. preview_value={
  48. "first_row_is_table_header": "True",
  49. "data": [
  50. ["Bread type", "Origin"],
  51. ["Anpan", "Japan"],
  52. ["Crumpet", "United Kingdom"],
  53. ["Roti buaya", "Indonesia"],
  54. ],
  55. },
  56. )
  57. typed_table_block = TypedTableBlock(
  58. [
  59. ("text", CharBlock()),
  60. ("numeric", FloatBlock()),
  61. ("rich_text", RichTextBlock()),
  62. ("image", CustomImageBlock()),
  63. ],
  64. group="Content",
  65. description=(
  66. "A table of data with cells that can include "
  67. "text, numbers, rich text, and images"
  68. ),
  69. preview_value={
  70. "caption": "Nutritional information for 100g of bread",
  71. "columns": [
  72. {"type": "rich_text", "heading": "Nutrient"},
  73. {"type": "numeric", "heading": "White bread"},
  74. {"type": "numeric", "heading": "Brown bread"},
  75. {"type": "numeric", "heading": "Wholemeal bread"},
  76. ],
  77. "rows": [
  78. {
  79. "values": [
  80. '<p><a href="https://en.wikipedia.org/wiki/Protein">'
  81. "Protein</a> <b>(g)</b></p>",
  82. 7.9,
  83. 7.9,
  84. 9.4,
  85. ]
  86. },
  87. {
  88. "values": [
  89. '<p><a href="https://en.wikipedia.org/wiki/Carbohydrate">'
  90. "Carbohydrate</a> <b>(g)</b></p>",
  91. 46.1,
  92. 42.1,
  93. 42,
  94. ]
  95. },
  96. {
  97. "values": [
  98. '<p><a href="https://en.wikipedia.org/wiki/Sugar">'
  99. "Total sugars</a> <b>(g)</b></p>",
  100. 3.4,
  101. 3.4,
  102. 2.8,
  103. ]
  104. },
  105. ],
  106. },
  107. )
  108. image_block = CustomImageBlock(group="Media")
  109. embed_block = EmbedBlock(
  110. help_text="Insert an embed URL e.g https://www.youtube.com/watch?v=SGJFWirQ3ks",
  111. icon="media",
  112. template="blocks/embed_block.html",
  113. group="Media",
  114. preview_value="https://www.youtube.com/watch?v=mwrGSfiB1Mg",
  115. description="An embedded video or other media",
  116. )
  117. ingredients_list = ListBlock(
  118. RichTextBlock(features=["bold", "italic", "link"]),
  119. min_num=2,
  120. max_num=10,
  121. icon="list-ol",
  122. group="Cooking",
  123. preview_value=["<p>200g flour</p>", "<p>1 egg</p>", "<p>1 cup of sugar</p>"],
  124. description=(
  125. "A list of ingredients to use in the recipe "
  126. "with optional bold, italic, and link options"
  127. ),
  128. )
  129. steps_list = ListBlock(
  130. RecipeStepBlock(),
  131. min_num=2,
  132. max_num=10,
  133. icon="tasks",
  134. group="Cooking",
  135. preview_value=[
  136. {"text": "<p>An easy step</p>", "difficulty": "S"},
  137. {"text": "<p>A difficult step</p>", "difficulty": "L"},
  138. {"text": "<p>A medium step</p>", "difficulty": "M"},
  139. ],
  140. description=(
  141. "A list of steps to follow in the recipe, "
  142. "with a difficulty rating for each step"
  143. ),
  144. )