Commit 01034db2 by Matjaz Gregoric

Support for dynamic generation of target zones and image.

Instead of providing a custom image, the author can now specify the
number of columns and rows and a single zone size and zones arranged
in a grid of chosen size will be automatically generated, as well as
the background image.
parent dac6ba40
...@@ -335,12 +335,12 @@ class DragAndDropBlock( ...@@ -335,12 +335,12 @@ class DragAndDropBlock(
""" """
js_templates = loader.load_unicode('/templates/html/js_templates.html') js_templates = loader.load_unicode('/templates/html/js_templates.html')
# Get a 'html_id' string that is unique for this block. # Get an 'id_suffix' string that is unique for this block.
# We append it to HTML element ID attributes to ensure multiple instances of the DnDv2 block # We append it to HTML element ID attributes to ensure multiple instances of the DnDv2 block
# on the same page don't share the same ID value. # on the same page don't share the same ID value.
# We avoid using ID attributes in preference to classes, but sometimes we still need IDs to # We avoid using ID attributes in preference to classes, but sometimes we still need IDs to
# connect 'for' and 'aria-describedby' attributes to the associated elements. # connect 'for' and 'aria-describedby' attributes to the associated elements.
id_suffix = self.location.html_id() # pylint: disable=no-member id_suffix = self._get_block_id()
js_templates = js_templates.replace('{{id_suffix}}', id_suffix) js_templates = js_templates.replace('{{id_suffix}}', id_suffix)
context = { context = {
'js_templates': js_templates, 'js_templates': js_templates,
...@@ -407,6 +407,18 @@ class DragAndDropBlock( ...@@ -407,6 +407,18 @@ class DragAndDropBlock(
'result': 'success', 'result': 'success',
} }
def _get_block_id(self):
"""
Return unique ID of this block. Useful for HTML ID attributes.
Works both in LMS/Studio and workbench runtimes:
- In LMS/Studio, use the location.html_id method.
- In the workbench, use the usage_id.
"""
if hasattr(self, 'location'):
return self.location.html_id() # pylint: disable=no-member
else:
return unicode(self.scope_ids.usage_id)
@staticmethod @staticmethod
def _get_max_items_per_zone(submissions): def _get_max_items_per_zone(submissions):
""" """
......
...@@ -286,13 +286,20 @@ ...@@ -286,13 +286,20 @@
} }
.xblock--drag-and-drop .drag-container .target .zone p { .xblock--drag-and-drop .drag-container .target .zone p {
width: 100%;
font-family: Arial; font-family: Arial;
font-size: 16px; font-size: 16px;
font-weight: bold; font-weight: bold;
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
padding: 10px;
margin: 0;
display: flex;
align-items: center;
justify-content: center;
text-align: center; text-align: center;
margin-top: auto;
margin-bottom: auto;
} }
/*** FEEDBACK ***/ /*** FEEDBACK ***/
......
...@@ -93,7 +93,16 @@ ...@@ -93,7 +93,16 @@
margin: 10px 0 0 0; margin: 10px 0 0 0;
} }
.xblock--drag-and-drop--editor .target-image-form input { .xblock--drag-and-drop--editor .target-image-form .background-image-type {
display: block;
margin-bottom: 8px;
}
.xblock--drag-and-drop--editor .target-image-form .background-auto {
margin-top: 20px;
}
.xblock--drag-and-drop--editor .target-image-form input[type="text"] {
width: 50%; width: 50%;
} }
.xblock--drag-and-drop--editor .target-image-form textarea { .xblock--drag-and-drop--editor .target-image-form textarea {
...@@ -104,6 +113,11 @@ ...@@ -104,6 +113,11 @@
display: block; display: block;
} }
.xblock--drag-and-drop--editor .target-image-form .background-auto .autozone-layout,
.xblock--drag-and-drop--editor .target-image-form .background-auto .autozone-size {
width: 4em;
}
.xblock--drag-and-drop--editor input, .xblock--drag-and-drop--editor input,
.xblock--drag-and-drop--editor textarea { .xblock--drag-and-drop--editor textarea {
box-sizing: border-box; box-sizing: border-box;
......
...@@ -91,18 +91,76 @@ ...@@ -91,18 +91,76 @@
</header> </header>
<div class="tab-content"> <div class="tab-content">
<form class="target-image-form"> <form class="target-image-form">
<label class="h4" for="background-url-{{id_suffix}}"> <fieldset>
<span>{% trans "Background URL" %}</span> <legend class="h4">{% trans "Background Image" %}</legend>
</label> <label class="background-image-type">
<input class="background-url" <input type="radio" name="background-image-type-{{id_suffix}}" value="manual" />
id="background-url-{{id_suffix}}" {% trans "Provide custom image" %}
type="text" </label>
aria-describedby="background-url-{{id_suffix}}" /> <label class="background-image-type">
</label> <input type="radio" name="background-image-type-{{id_suffix}}" value="auto" />
<button type="button" class="btn">{% trans "Change background" %}</button> {% trans "Generate image automatically" %}
<div id="background-url-description-{{id_suffix}}" class="form-help"> </label>
{% trans "For example, 'http://example.com/background.png' or '/static/background.png'." %} </fieldset>
</div> <fieldset class="background-manual">
<label class="h4" for="background-url-{{id_suffix}}">
<span>{% trans "Background URL" %}</span>
</label>
<input class="background-url"
id="background-url-{{id_suffix}}"
type="text"
aria-describedby="background-url-description-{{id_suffix}}" />
</label>
<button type="button" class="btn">{% trans "Change background" %}</button>
<div id="background-url-description-{{id_suffix}}" class="form-help">
{% trans "For example, 'http://example.com/background.png' or '/static/background.png'." %}
</div>
</fieldset>
<fieldset class="background-auto">
<fieldset>
<legend class="h4">{% trans "Zone Layout" %}</legend>
<label class="sr" for="autozone-cols-{{id_suffix}}">
{% trans "Number of columns" %}
</label>
<input id="autozone-cols-{{id_suffix}}"
class="autozone-layout autozone-layout-cols"
type="text"
aria-describedby="autozone-layout-description-{{id_suffix}}" />
<span>&times;</span>
<label class="sr" for="autozone-rows-{{id_suffix}}">
{% trans "Number of rows" %}
</label>
<input id="autozone-rows-{{id_suffix}}"
class="autozone-layout autozone-layout-rows"
type="text"
aria-describedby="autozone-layout-description-{{id_suffix}}" />
<div id="autozone-layout-description-{{id_suffix}}" class="form-help">
{% trans "Number of columns and rows." %}
</div>
</fieldset>
<fieldset>
<legend class="h4">{% trans "Zone Size" %}</legend>
<label class="sr" for="autozone-zone-width-{{id_suffix}}">
{% trans "Zone width" %}
</label>
<input id="autozone-zone-width-{{id_suffix}}"
class="autozone-size autozone-size-width"
type="text"
aria-describedby="autozone-size-description-{{id_suffix}}" />
<span>&times;</span>
<label class="sr" for="autozone-zone-height-{{id_suffix}}">
{% trans "Zone height" %}
</label>
<input id="autozone-zone-height-{{id_suffix}}"
class="autozone-size autozone-size-height"
type="text"
aria-describedby="autozone-size-description-{{id_suffix}}" />
<div id="autozone-size-description-{{id_suffix}}" class="form-help">
{% trans "Size of a single zone in pixels." %}
</div>
</fieldset>
<button type="button" class="btn">{% trans "Generate image and zones" %}</button>
</fieldset>
<label class="h4"> <label class="h4">
<span>{% trans "Background description" %}</span> <span>{% trans "Background description" %}</span>
<textarea required class="background-description" <textarea required class="background-description"
......
...@@ -172,3 +172,21 @@ ...@@ -172,3 +172,21 @@
</div> </div>
</fieldset> </fieldset>
</script> </script>
<script class="autozone-tpl" type="text/html">
<svg xmlns="http://www.w3.org/2000/svg" width="{{width}}" height="{{height}}">
<rect x="0" y="0" width="100%" height="100%" fill="#fff" />
{{#each zones}}
<rect x="{{x}}"
y="{{y}}"
width="{{width}}"
height="{{height}}"
fill="#f7f7f7"
rx="10"
ry="10"
stroke="#d6d6d6"
stroke-width="2"
stroke-dasharray="3,3" />
{{/each}}
</svg>
</script>
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment