1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 package info.magnolia.dam.app.ui.field.upload;
35
36 import info.magnolia.dam.app.ui.field.configuration.PreviewComponentProvider;
37 import info.magnolia.dam.app.ui.field.configuration.ThumbnailComponentProvider;
38 import info.magnolia.dam.app.ui.field.definition.DamUploadFieldDefinition;
39 import info.magnolia.i18nsystem.SimpleTranslator;
40 import info.magnolia.objectfactory.ComponentProvider;
41 import info.magnolia.ui.api.context.UiContext;
42 import info.magnolia.ui.api.overlay.OverlayCloser;
43 import info.magnolia.ui.form.field.upload.basic.BasicUploadField;
44 import info.magnolia.ui.imageprovider.ImageProvider;
45 import info.magnolia.ui.mediaeditor.MediaEditorPresenter;
46 import info.magnolia.ui.mediaeditor.MediaEditorPresenterFactory;
47 import info.magnolia.ui.mediaeditor.event.MediaEditorCompletedEvent;
48 import info.magnolia.ui.vaadin.overlay.MessageStyleTypeEnum;
49
50 import java.io.FileInputStream;
51 import java.io.FileNotFoundException;
52 import java.io.InputStream;
53
54 import org.apache.commons.io.FileUtils;
55 import org.apache.commons.lang.StringUtils;
56 import org.slf4j.Logger;
57 import org.slf4j.LoggerFactory;
58
59 import com.google.common.net.MediaType;
60 import com.vaadin.server.Resource;
61 import com.vaadin.server.StreamResource;
62 import com.vaadin.server.StreamResource.StreamSource;
63 import com.vaadin.shared.ui.label.ContentMode;
64 import com.vaadin.ui.Alignment;
65 import com.vaadin.ui.Button;
66 import com.vaadin.ui.Button.ClickEvent;
67 import com.vaadin.ui.Component;
68 import com.vaadin.ui.CssLayout;
69 import com.vaadin.ui.HorizontalLayout;
70 import com.vaadin.ui.Label;
71 import com.vaadin.ui.Layout;
72 import com.vaadin.ui.NativeButton;
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93 public class DamUploadField<D extends AssetUploadReceiver> extends BasicUploadField<D> {
94 private static final long serialVersionUID = 1L;
95 private static final Logger log = LoggerFactory.getLogger(DamUploadField.class);
96
97
98 private MediaEditorPresenterFactory mediaEditorFactory;
99 private ComponentProvider componentProvider;
100
101 private final SimpleTranslator i18n;
102
103 public DamUploadField(ImageProvider imageProvider, UiContext uiContext, MediaEditorPresenterFactory mediaEditorFactory, ComponentProvider componentProvider, DamUploadFieldDefinition definition, SimpleTranslator i18n) {
104 super(imageProvider, uiContext, definition, i18n);
105
106 populateFromDefinition(definition);
107
108 this.mediaEditorFactory = mediaEditorFactory;
109 this.componentProvider = componentProvider;
110 this.i18n = i18n;
111 }
112
113
114
115
116
117 @Override
118 protected Component getFileDetailSize() {
119 Label label = new Label("", ContentMode.HTML);
120 label.setCaption(i18n.translate(fileDetailSizeCaption));
121 StringBuilder sb = new StringBuilder();
122 if (getValue().isImage()) {
123 sb.append(getValue().getWidth() + " x " + getValue().getHeight() + ", ");
124 }
125 sb.append(FileUtils.byteCountToDisplaySize(getValue().getFileSize()));
126 if (getValue().getDuration() > 0) {
127 sb.append("(x:x min)");
128 }
129
130 label.setValue(sb.toString());
131 return label;
132 }
133
134
135
136
137
138
139 @Override
140 protected Layout createCompletedActionLayout() {
141 if (isReadOnly()) {
142 return new HorizontalLayout();
143 }
144
145 HorizontalLayout actionLayout = new HorizontalLayout();
146 actionLayout.setSizeUndefined();
147 actionLayout.addStyleName("buttons");
148 actionLayout.setSpacing(true);
149
150 if (getValue() != null && !getValue().isEmpty() && getValue().getEditAssetAppConfiguration().hasEditConfig()) {
151 Button edit = createEditButton();
152 actionLayout.addComponent(edit);
153 }
154
155 getUpload().setButtonCaption(getCaption(selectAnotherCaption, null));
156 actionLayout.addComponent(getUpload());
157
158 if (getValue() != null && !getValue().isEmpty()) {
159 Button delete = createDeleteButton();
160 actionLayout.addComponent(delete);
161 actionLayout.setComponentAlignment(delete, Alignment.MIDDLE_LEFT);
162 }
163 return actionLayout;
164 }
165
166
167
168
169
170 private Button createEditButton() {
171 Button editButton = new Button(getCaption(editFileCaption, null));
172 editButton.addClickListener(new Button.ClickListener() {
173 private static final long serialVersionUID = 1L;
174
175 @Override
176 public void buttonClick(ClickEvent event) {
177
178 try {
179 openMediaEditor();
180 } catch (FileNotFoundException fnfe) {
181 log.warn("could not open MediaEditor");
182 uiContext.openAlert(MessageStyleTypeEnum.ERROR, "ERROR", i18n.translate("dam.assets.uploadField.alert.couldNotOpenMediaEditor")
183 + " "
184 + getValue().getEditAssetAppConfiguration().getEditConfig().getMediaEditorId(),
185 "ok", null);
186 }
187 }
188 });
189 editButton.addStyleName("edit");
190 return editButton;
191 }
192
193
194
195
196
197
198
199 private void openMediaEditor() throws FileNotFoundException {
200
201 String presenterById = null;
202 if (getValue().getEditAssetAppConfiguration() == null || !getValue().getEditAssetAppConfiguration().hasEditConfig()) {
203 log.warn("No Media Editor defined for the following mimeType {} ", getValue().getMimeType());
204 return;
205 } else {
206 presenterById = "ui-mediaeditor:" + getValue().getEditAssetAppConfiguration().getEditConfig().getMediaEditorId();
207 log.debug("Will open the following mediaEditor Presenter {}", presenterById);
208 }
209
210 final NativeButton mediaEditorPlaceholder = new NativeButton(i18n.translate("dam.assets.uploadField.button.mediaEditorPlaceholder"));
211 mediaEditorPlaceholder.addStyleName("btn-form btn-form-commit");
212
213 MediaEditorPresenter mediaEditorPresenter = mediaEditorFactory.getPresenterById(presenterById);
214 final InputStream inputStream = new FileInputStream(getValue().getFile());
215 final OverlayCloser overlayCloser = uiContext.openOverlay(mediaEditorPresenter.start(inputStream));
216 mediaEditorPresenter.addCompletionHandler(new MediaEditorCompletedEvent.Handler() {
217 @Override
218 public void onSubmit(MediaEditorCompletedEvent event) {
219 final InputStream is = event.getStream();
220 getValue().updateContent(event.getStream());
221
222 updateDisplay();
223 overlayCloser.close();
224 closeInputStream(inputStream);
225 getPropertyDataSource().setValue(getValue());
226 }
227
228 @Override
229 public void onCancel(MediaEditorCompletedEvent event) {
230 overlayCloser.close();
231 closeInputStream(inputStream);
232 }
233
234 private void closeInputStream(InputStream inputStream) {
235 try {
236 if (inputStream != null) {
237 inputStream.close();
238 }
239 } catch (Exception e) {
240 log.warn("Could not close the InputStream ", e);
241 }
242 }
243 });
244 }
245
246
247
248
249
250
251
252
253 @Override
254 protected Component createThumbnailComponent() {
255
256 CssLayout previewLayout = new CssLayout();
257 previewLayout.addStyleName("file-preview-area");
258 previewLayout.setWidth("150px");
259 previewLayout.setHeight("150px");
260
261 Component image = createPreviewComponent();
262 if (image != null) {
263 image.addStyleName("preview-image");
264 previewLayout.addComponent(image);
265 }
266
267
268 if (getValue().getEditAssetAppConfiguration().hasEditConfig() && !isReadOnly()) {
269 Button editButton = new Button();
270 editButton.addStyleName("edit-button");
271 editButton.setHtmlContentAllowed(true);
272 editButton.setCaption("<span class=\"" + getValue().getEditAssetAppConfiguration().getEditConfig().getIconStyleName() + "\"></span>");
273 editButton.setDescription(getCaption(editFileCaption, null));
274 previewLayout.addComponent(editButton);
275
276
277 editButton.addClickListener(new Button.ClickListener() {
278 private static final long serialVersionUID = 1L;
279
280 @Override
281 public void buttonClick(ClickEvent event) {
282
283 try {
284 openMediaEditor();
285 } catch (FileNotFoundException fnfe) {
286 log.warn("could not open MediaEditor");
287 uiContext.openAlert(MessageStyleTypeEnum.ERROR, "ERROR", i18n.translate("dam.assets.uploadField.alert.couldNotOpenMediaEditor")
288 + " "
289 + getValue().getEditAssetAppConfiguration().getEditConfig().getMediaEditorId(),
290 "ok", null);
291 }
292 }
293 });
294 }
295
296
297 if (getValue().getEditAssetAppConfiguration().hasPreviewConfig()) {
298 Button lightboxButton = new Button();
299 lightboxButton.addStyleName("lightbox-button");
300 lightboxButton.setHtmlContentAllowed(true);
301 lightboxButton.setCaption("<span class=\"" + getValue().getEditAssetAppConfiguration().getPreviewConfig().getIconStyleName() + "\"></span>");
302 lightboxButton.setDescription(i18n.translate(lightboxCaption));
303 previewLayout.addComponent(lightboxButton);
304
305 lightboxButton.addClickListener(new Button.ClickListener() {
306 private static final long serialVersionUID = 1L;
307
308 @Override
309 public void buttonClick(ClickEvent event) {
310
311 Class<? extends PreviewComponentProvider> previewActionClass = getValue().getEditAssetAppConfiguration().getPreviewConfig().getPreviewComponentProviderClass();
312 if (previewActionClass != null) {
313 PreviewComponentProvider implementation = componentProvider.newInstance(previewActionClass);
314 implementation.open(getResource());
315 } else {
316 log.warn("No Preview Defined is defined ");
317 }
318 }
319 });
320 }
321 return previewLayout;
322 }
323
324
325
326
327
328
329 private Component createPreviewComponent() {
330 Class<? extends ThumbnailComponentProvider> thumbnailProviderClass = getValue().getEditAssetAppConfiguration().getThumbnailComponentProviderClass();
331 if (thumbnailProviderClass != null) {
332 ThumbnailComponentProvider implementation = componentProvider.newInstance(thumbnailProviderClass);
333 return implementation.createThumbnailComponent(null, getValue().getFile(), getValue().getMimeType());
334 } else {
335 log.warn("No ThumbnailComponentProvider is defined ");
336 return null;
337 }
338 }
339
340
341
342
343 private Resource getResource() {
344 final StreamSource source = new StreamResource.StreamSource() {
345 private static final long serialVersionUID = 1L;
346
347 @Override
348 public InputStream getStream() {
349 try {
350 return new FileInputStream(getValue().getFile());
351 } catch (FileNotFoundException fnfe) {
352 log.warn("could not found File", fnfe);
353 return null;
354 }
355 }
356 };
357
358 final Resource resource = new StreamResource(source, "") {
359 @Override
360 public String getMIMEType() {
361 return getValue().getMimeType();
362 }
363 };
364
365 return resource;
366 }
367
368 protected void populateFromDefinition(DamUploadFieldDefinition definition) {
369 super.populateFromDefinition(definition);
370 this.setLightboxCaption(definition.getLightboxCaption());
371 this.setEditFileCaption(definition.getEditFileCaption());
372 }
373
374
375
376
377 @Override
378 protected void setCaptionExtension(String mimeType) {
379 if (StringUtils.isNotBlank(mimeType)) {
380 captionExtension = MediaType.parse(mimeType).type();
381 } else if (StringUtils.isNotBlank(getValue().getMimeType())) {
382 captionExtension = MediaType.parse(getValue().getMimeType()).type();
383 }
384 }
385
386 private String lightboxCaption;
387 private String editFileCaption;
388
389
390 public void setLightboxCaption(String lightboxCaption) {
391 this.lightboxCaption = lightboxCaption;
392 }
393
394 public void setEditFileCaption(String editFileCaption) {
395 this.editFileCaption = editFileCaption;
396 }
397
398 }