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.assets.field;
35
36 import info.magnolia.cms.security.Permission;
37 import info.magnolia.cms.security.PermissionUtil;
38 import info.magnolia.cms.util.PathUtil;
39 import info.magnolia.context.MgnlContext;
40 import info.magnolia.dam.app.ui.field.upload.AssetUploadReceiver;
41 import info.magnolia.event.EventBus;
42 import info.magnolia.i18nsystem.SimpleTranslator;
43 import info.magnolia.jcr.util.NodeTypes;
44 import info.magnolia.jcr.util.NodeUtil;
45 import info.magnolia.objectfactory.Components;
46 import info.magnolia.ui.api.action.ActionDefinition;
47 import info.magnolia.ui.api.context.UiContext;
48 import info.magnolia.ui.api.event.ChooseDialogEventBus;
49 import info.magnolia.ui.api.overlay.OverlayCloser;
50 import info.magnolia.ui.api.overlay.OverlayLayer.ModalityLevel;
51 import info.magnolia.ui.api.view.View;
52 import info.magnolia.ui.dialog.actionarea.ActionListener;
53 import info.magnolia.ui.dialog.actionarea.renderer.ActionRenderer;
54 import info.magnolia.ui.form.field.upload.UploadReceiver;
55 import info.magnolia.ui.form.field.upload.basic.BasicUploadProgressIndicator;
56 import info.magnolia.ui.framework.action.AbstractRepositoryAction;
57 import info.magnolia.ui.framework.overlay.ViewAdapter;
58 import info.magnolia.ui.vaadin.integration.jcr.JcrNodeItemId;
59 import info.magnolia.ui.workbench.event.SelectionChangedEvent;
60
61 import java.util.Set;
62
63 import javax.inject.Inject;
64 import javax.inject.Named;
65 import javax.jcr.RepositoryException;
66
67 import com.vaadin.ui.Button;
68 import com.vaadin.ui.Button.ClickEvent;
69 import com.vaadin.ui.CssLayout;
70 import com.vaadin.ui.NativeButton;
71 import com.vaadin.ui.UI;
72 import com.vaadin.v7.ui.Upload;
73 import com.vaadin.v7.ui.Upload.FailedEvent;
74 import com.vaadin.v7.ui.Upload.FailedListener;
75 import com.vaadin.v7.ui.Upload.FinishedEvent;
76 import com.vaadin.v7.ui.Upload.FinishedListener;
77 import com.vaadin.v7.ui.Upload.ProgressListener;
78 import com.vaadin.v7.ui.Upload.StartedEvent;
79 import com.vaadin.v7.ui.Upload.StartedListener;
80 import com.vaadin.v7.ui.Upload.SucceededEvent;
81 import com.vaadin.v7.ui.Upload.SucceededListener;
82
83
84
85
86 public class UploadAssetActionRenderer implements ActionRenderer {
87
88 private UiContext layer;
89
90 private Upload upload;
91
92 private UploadReceiver receiver;
93
94 private ProgressPopup progressIndicator;
95
96 private OverlayCloser progressIndicatorCloseHandle;
97
98 private final SimpleTranslator i18n;
99
100
101
102
103
104 @Deprecated
105 public UploadAssetActionRenderer(UiContext layer, SimpleTranslator i18n) {
106 this.layer = layer;
107 this.i18n = i18n;
108 receiver = Components.newInstance(AssetUploadReceiver.class, i18n);
109 }
110
111 @Inject
112 public UploadAssetActionRenderer(UiContext layer, SimpleTranslator i18n, @Named(ChooseDialogEventBus.NAME)EventBus eventBus) {
113 this.layer = layer;
114 this.i18n = i18n;
115 receiver = Components.newInstance(AssetUploadReceiver.class, i18n);
116 eventBus.addHandler(SelectionChangedEvent.class, new SelectionChangedEvent.Handler() {
117 @Override
118 public void onSelectionChanged(SelectionChangedEvent event) {
119 Set<Object> itemIds = event.getItemIds();
120 if (itemIds == null || itemIds.isEmpty()) {
121 return;
122 }
123 try {
124 JcrNodeItemId nodeItemId = (JcrNodeItemId) itemIds.iterator().next();
125 javax.jcr.Node node = MgnlContext.getJCRSession(nodeItemId.getWorkspace()).getNodeByIdentifier(nodeItemId.getUuid());
126 boolean uploadAllowed = itemIds.size() == 1;
127 if (uploadAllowed) {
128 uploadAllowed = NodeUtil.isNodeType(node, NodeTypes.Folder.NAME) || NodeUtil.getAncestors(node).isEmpty();
129
130 uploadAllowed &= PermissionUtil.isGranted(node, Permission.WRITE)
131 && PermissionUtil.isGranted(node.getSession(), PathUtil.createPath(node.getPath(), AbstractRepositoryAction.DEFAULT_NEW_ITEM_NAME), Permission.WRITE);
132 }
133 upload.setEnabled(uploadAllowed);
134 } catch (RepositoryException e) {
135 upload.setEnabled(false);
136 }
137 }
138 });
139 }
140
141 @Override
142 public View start(final ActionDefinition action, final ActionListener listener) {
143 this.upload = new Upload(action.getLabel(), receiver) {
144 @Override
145 public void setCaption(String caption) {
146 setButtonCaption(caption);
147 }
148 };
149
150 this.upload.addStartedListener(new StartedListener() {
151 @Override
152 public void uploadStarted(StartedEvent event) {
153 UI.getCurrent().setPollInterval(1000);
154 progressIndicator = new ProgressPopup(upload, i18n);
155 progressIndicatorCloseHandle = layer.openOverlay(new ViewAdapter(progressIndicator), ModalityLevel.NON_MODAL);
156 progressIndicator.progressIndicator.setProgress(0);
157 progressIndicator.progressIndicator.setVisible(true);
158 }
159 });
160
161 this.upload.addFinishedListener(new FinishedListener() {
162 @Override
163 public void uploadFinished(FinishedEvent event) {
164 UI.getCurrent().setPollInterval(-1);
165 progressIndicatorCloseHandle.close();
166 }
167 });
168
169 this.upload.addProgressListener(new ProgressListener() {
170 @Override
171 public void updateProgress(long readBytes, long contentLength) {
172 progressIndicator.progressIndicator.refreshLayout(readBytes, contentLength, receiver.getFileName());
173 }
174 });
175
176
177 this.upload.addFailedListener(new FailedListener() {
178 @Override
179 public void uploadFailed(FailedEvent event) {
180 progressIndicatorCloseHandle.close();
181 }
182 });
183
184 this.upload.addSucceededListener(new SucceededListener() {
185 @Override
186 public void uploadSucceeded(SucceededEvent event) {
187 listener.onActionFired(action.getName(), upload.getReceiver());
188 }
189 });
190
191 this.upload.setImmediate(true);
192 return new ViewAdapter(upload);
193 }
194
195
196 private static class ProgressPopup extends CssLayout {
197
198 public BasicUploadProgressIndicator progressIndicator;
199
200 private ProgressPopup(final Upload upload, final SimpleTranslator i18n) {
201
202 addStyleName("direct-upload-progress-indicator");
203 addStyleName("upload-image-field");
204 CssLayout indicatorWrapper = new CssLayout();
205 indicatorWrapper.addStyleName("in-progress");
206 addComponent(indicatorWrapper);
207 String inProgressCaption = "field.upload.basic.uploading.file";
208 String inProgressRatioCaption = "field.upload.basic.uploaded.file";
209 this.progressIndicator = new BasicUploadProgressIndicator(inProgressCaption, inProgressRatioCaption, i18n);
210 indicatorWrapper.addComponent(progressIndicator);
211 Button cancelButton = new NativeButton(null, new Button.ClickListener() {
212 @Override
213 public void buttonClick(ClickEvent event) {
214 if (upload.isUploading()) {
215 upload.interruptUpload();
216 }
217 }
218 });
219 cancelButton.addStyleName("cancel");
220 indicatorWrapper.addComponent(cancelButton);
221 }
222 }
223 }