1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
namespace Drupal\df_tools_media\Plugin\Block; |
4
|
|
|
|
5
|
|
|
use Drupal\Component\Utility\NestedArray; |
6
|
|
|
use Drupal\Core\Block\BlockBase; |
7
|
|
|
use Drupal\Core\Form\FormStateInterface; |
8
|
|
|
use Drupal\media_entity\Entity\Media; |
9
|
|
|
|
10
|
|
|
/** |
11
|
|
|
* Provides the "Media Embed" block. |
12
|
|
|
* |
13
|
|
|
* Copied wholesale from Content Browser. |
14
|
|
|
* @todo Make a contrib module to provide blocks for every Entity Browser... |
15
|
|
|
* |
16
|
|
|
* @Block( |
17
|
|
|
* id = "media_embed", |
18
|
|
|
* admin_label = @Translation("Media Embed"), |
19
|
|
|
* category = @Translation("Embed") |
20
|
|
|
* ) |
21
|
|
|
*/ |
22
|
|
|
class MediaEmbedBlock extends BlockBase { |
23
|
|
|
|
24
|
|
|
/** |
25
|
|
|
* The number of times this block allows rendering the same entity. |
26
|
|
|
* |
27
|
|
|
* @var int |
28
|
|
|
*/ |
29
|
|
|
const RECURSIVE_RENDER_LIMIT = 2; |
30
|
|
|
|
31
|
|
|
/** |
32
|
|
|
* An array of counters for the recursive rendering protection. |
33
|
|
|
* |
34
|
|
|
* @var array |
35
|
|
|
*/ |
36
|
|
|
protected static $recursiveRenderDepth = []; |
37
|
|
|
|
38
|
|
|
/** |
39
|
|
|
* {@inheritdoc} |
40
|
|
|
*/ |
41
|
|
|
public function defaultConfiguration() { |
42
|
|
|
return [ |
43
|
|
|
'view_mode' => '', |
44
|
|
|
'mids' => [], |
45
|
|
|
'uuids' => [], |
46
|
|
|
]; |
47
|
|
|
} |
48
|
|
|
|
49
|
|
|
/** |
50
|
|
|
* {@inheritdoc} |
51
|
|
|
*/ |
52
|
|
|
public function blockForm($form, FormStateInterface $form_state) { |
53
|
|
|
$entities = $form_state->getValue([ |
54
|
|
|
'settings', |
55
|
|
|
'selection', |
56
|
|
|
'mids', |
57
|
|
|
'entities' |
58
|
|
|
], []); |
59
|
|
|
$mids = []; |
60
|
|
|
foreach ($entities as $entity) { |
61
|
|
|
$mids[] = $entity->id(); |
62
|
|
|
} |
63
|
|
|
if (empty($mids)) { |
64
|
|
|
$mids = $this->getDefaultMIDs(); |
65
|
|
|
} |
66
|
|
|
|
67
|
|
|
$form['selection'] = $this->browserForm($mids); |
68
|
|
|
|
69
|
|
|
/** @var \Drupal\Core\Entity\EntityDisplayRepository $entity_display_repository */ |
70
|
|
|
$entity_display_repository = \Drupal::service('entity_display.repository'); |
71
|
|
|
$view_mode_options = $entity_display_repository->getViewModeOptions('media'); |
72
|
|
|
|
73
|
|
|
$form['view_mode'] = [ |
74
|
|
|
'#type' => 'select', |
75
|
|
|
'#options' => $view_mode_options, |
76
|
|
|
'#title' => t('View mode'), |
77
|
|
|
'#default_value' => $this->configuration['view_mode'], |
78
|
|
|
]; |
79
|
|
|
|
80
|
|
|
return $form; |
81
|
|
|
} |
82
|
|
|
|
83
|
|
|
/** |
84
|
|
|
* Constructs parts of the form needed to use Entity Browser. |
85
|
|
|
* |
86
|
|
|
* @param array $mids |
87
|
|
|
* An array of Media IDs. |
88
|
|
|
* |
89
|
|
|
* @return array |
90
|
|
|
* A render array representing Entity Browser components. |
91
|
|
|
*/ |
92
|
|
|
public function browserForm($mids) { |
93
|
|
|
$selection = [ |
94
|
|
|
'#type' => 'container', |
95
|
|
|
'#attributes' => ['id' => 'media-embed-block-browser'], |
96
|
|
|
]; |
97
|
|
|
|
98
|
|
|
$selection['mids'] = [ |
99
|
|
|
'#type' => 'entity_browser', |
100
|
|
|
'#entity_browser' => 'media_browser_in_modal', |
101
|
|
|
'#entity_browser_validators' => [ |
102
|
|
|
'entity_type' => ['type' => 'media'] |
103
|
|
|
], |
104
|
|
|
'#process' => [ |
105
|
|
|
[ |
106
|
|
|
'\Drupal\entity_browser\Element\EntityBrowserElement', |
107
|
|
|
'processEntityBrowser' |
108
|
|
|
], |
109
|
|
|
[get_called_class(), 'processEntityBrowser'], |
110
|
|
|
], |
111
|
|
|
]; |
112
|
|
|
|
113
|
|
|
$order_class = 'media-embed-block-delta-order'; |
114
|
|
|
|
115
|
|
|
$selection['table'] = [ |
116
|
|
|
'#type' => 'table', |
117
|
|
|
'#header' => [ |
118
|
|
|
t('Title'), |
119
|
|
|
t('Type'), |
120
|
|
|
t('Order', [], ['context' => 'Sort order']), |
121
|
|
|
], |
122
|
|
|
'#empty' => t('No media yet'), |
123
|
|
|
'#tabledrag' => [ |
124
|
|
|
[ |
125
|
|
|
'action' => 'order', |
126
|
|
|
'relationship' => 'sibling', |
127
|
|
|
'group' => $order_class, |
128
|
|
|
], |
129
|
|
|
], |
130
|
|
|
]; |
131
|
|
|
|
132
|
|
|
$delta = 0; |
133
|
|
|
$bundle_info = \Drupal::service('entity_type.bundle.info')->getBundleInfo('media'); |
134
|
|
|
|
135
|
|
|
foreach ($mids as $mid) { |
136
|
|
|
/** @var \Drupal\media_entity\Entity\Media $media */ |
137
|
|
|
$media = Media::load($mid); |
138
|
|
|
|
139
|
|
|
$selection['table'][$mid] = [ |
140
|
|
|
'#attributes' => [ |
141
|
|
|
'class' => ['draggable'], |
142
|
|
|
'data-entity-id' => $media->getEntityTypeId() . ':' . $mid, |
143
|
|
|
], |
144
|
|
|
'title' => ['#markup' => $media->label()], |
145
|
|
|
'type' => ['#markup' => $bundle_info[$media->bundle()]['label']], |
146
|
|
|
'_weight' => [ |
147
|
|
|
'#type' => 'weight', |
148
|
|
|
'#title' => t('Weight for row @number', ['@number' => $delta + 1]), |
149
|
|
|
'#title_display' => 'invisible', |
150
|
|
|
'#delta' => count($mids), |
151
|
|
|
'#default_value' => $delta, |
152
|
|
|
'#attributes' => ['class' => [$order_class]], |
153
|
|
|
], |
154
|
|
|
]; |
155
|
|
|
|
156
|
|
|
$delta++; |
157
|
|
|
} |
158
|
|
|
|
159
|
|
|
return $selection; |
160
|
|
|
} |
161
|
|
|
|
162
|
|
|
/** |
163
|
|
|
* AJAX callback: Re-renders the Entity Browser button/table. |
164
|
|
|
*/ |
165
|
|
|
public static function updateCallback(array &$form, FormStateInterface $form_state) { |
166
|
|
|
$trigger = $form_state->getTriggeringElement(); |
167
|
|
|
$parents = array_slice($trigger['#array_parents'], 0, -2); |
168
|
|
|
$selection = NestedArray::getValue($form, $parents); |
169
|
|
|
return $selection; |
170
|
|
|
} |
171
|
|
|
|
172
|
|
|
/** |
173
|
|
|
* Render API callback: Processes the entity browser element. |
174
|
|
|
*/ |
175
|
|
|
public static function processEntityBrowser(&$element, FormStateInterface $form_state, &$complete_form) { |
|
|
|
|
176
|
|
|
$element['entity_ids']['#ajax'] = [ |
177
|
|
|
'callback' => [get_called_class(), 'updateCallback'], |
178
|
|
|
'wrapper' => 'media-embed-block-browser', |
179
|
|
|
'event' => 'entity_browser_value_updated', |
180
|
|
|
]; |
181
|
|
|
return $element; |
182
|
|
|
} |
183
|
|
|
|
184
|
|
|
/** |
185
|
|
|
* {@inheritdoc} |
186
|
|
|
*/ |
187
|
|
|
public function blockSubmit($form, FormStateInterface $form_state) { |
188
|
|
|
$this->configuration['mids'] = []; |
189
|
|
|
$this->configuration['uuids'] = []; |
190
|
|
|
foreach ($form_state->getValue(['selection', 'table'], []) as $mid => $settings) { |
191
|
|
|
$this->configuration['mids'][] = $mid; |
192
|
|
|
} |
193
|
|
|
$this->configuration['view_mode'] = $form_state->getValue('view_mode'); |
194
|
|
|
} |
195
|
|
|
|
196
|
|
|
/** |
197
|
|
|
* {@inheritdoc} |
198
|
|
|
*/ |
199
|
|
|
public function build() { |
200
|
|
|
$build = []; |
201
|
|
|
$view_builder = \Drupal::entityTypeManager()->getViewBuilder('media'); |
202
|
|
|
|
203
|
|
|
foreach ($this->getDefaultMIDs() as $mid) { |
204
|
|
|
/** @var \Drupal\media_entity\Entity\Media $media */ |
205
|
|
|
$media = Media::load($mid); |
206
|
|
|
if ($media && $media->access('view')) { |
207
|
|
|
if (isset(static::$recursiveRenderDepth[$mid])) { |
208
|
|
|
static::$recursiveRenderDepth[$mid]++; |
209
|
|
|
} |
210
|
|
|
else { |
211
|
|
|
static::$recursiveRenderDepth[$mid] = 1; |
212
|
|
|
} |
213
|
|
|
|
214
|
|
|
// Protect ourselves from recursive rendering. |
215
|
|
|
if (static::$recursiveRenderDepth[$mid] > static::RECURSIVE_RENDER_LIMIT) { |
216
|
|
|
return $build; |
217
|
|
|
} |
218
|
|
|
|
219
|
|
|
$build[] = $view_builder->view($media, $this->configuration['view_mode']); |
220
|
|
|
} |
221
|
|
|
} |
222
|
|
|
|
223
|
|
|
return $build; |
224
|
|
|
} |
225
|
|
|
|
226
|
|
|
/** |
227
|
|
|
* Gets the default MIDs for this Block. |
228
|
|
|
* |
229
|
|
|
* @return array |
230
|
|
|
* An array of Media IDs that are currently set in the Block configuration. |
231
|
|
|
*/ |
232
|
|
|
protected function getDefaultMIDs() { |
233
|
|
|
// We optionally support UUIDs being put directly to our configuration, to |
234
|
|
|
// support profiles providing Media Embed Blocks with default config. |
235
|
|
|
if (!empty($this->configuration['uuids'])) { |
236
|
|
|
$mids = \Drupal::entityQuery('media') |
237
|
|
|
->condition('uuid', $this->configuration['uuids'], 'IN') |
238
|
|
|
->execute(); |
239
|
|
|
} |
240
|
|
|
else { |
241
|
|
|
$mids = []; |
242
|
|
|
} |
243
|
|
|
|
244
|
|
|
// Merge in the normal configuration. |
245
|
|
|
$mids += $this->configuration['mids']; |
246
|
|
|
|
247
|
|
|
return $mids; |
248
|
|
|
} |
249
|
|
|
|
250
|
|
|
} |
251
|
|
|
|
This check looks from parameters that have been defined for a function or method, but which are not used in the method body.