1 package org
.argeo
.cms
.widgets
.auth
;
3 import java
.io
.IOException
;
4 import java
.util
.Arrays
;
6 import javax
.security
.auth
.callback
.Callback
;
7 import javax
.security
.auth
.callback
.CallbackHandler
;
8 import javax
.security
.auth
.callback
.NameCallback
;
9 import javax
.security
.auth
.callback
.PasswordCallback
;
10 import javax
.security
.auth
.callback
.TextOutputCallback
;
11 import javax
.security
.auth
.callback
.UnsupportedCallbackException
;
13 import org
.argeo
.util
.LocaleCallback
;
14 import org
.eclipse
.swt
.SWT
;
15 import org
.eclipse
.swt
.events
.KeyEvent
;
16 import org
.eclipse
.swt
.events
.KeyListener
;
17 import org
.eclipse
.swt
.events
.ModifyEvent
;
18 import org
.eclipse
.swt
.events
.ModifyListener
;
19 import org
.eclipse
.swt
.events
.SelectionEvent
;
20 import org
.eclipse
.swt
.events
.SelectionListener
;
21 import org
.eclipse
.swt
.layout
.GridData
;
22 import org
.eclipse
.swt
.widgets
.Combo
;
23 import org
.eclipse
.swt
.widgets
.Composite
;
24 import org
.eclipse
.swt
.widgets
.Control
;
25 import org
.eclipse
.swt
.widgets
.Label
;
26 import org
.eclipse
.swt
.widgets
.Text
;
29 * A composite that can populate itself based on {@link Callback}s. It can be
30 * used directly as a {@link CallbackHandler} or be used by one by calling the
31 * {@link #createCallbackHandlers(Callback[])}.
33 * Supported standard {@link Callback}s are:<br>
35 * <li>{@link PasswordCallback}</li>
36 * <li>{@link NameCallback}</li>
37 * <li>{@link TextOutputCallback}</li>
41 * Supported Argeo {@link Callback}s are:<br>
43 * <li>{@link LocaleCallback}</li>
47 public class CompositeCallbackHandler
extends Composite
implements
49 private static final long serialVersionUID
= -928223893722723777L;
51 private boolean wasUsedAlready
= false;
52 private boolean isSubmitted
= false;
53 private boolean isCanceled
= false;
55 public CompositeCallbackHandler(Composite parent
, int style
) {
60 public synchronized void handle(final Callback
[] callbacks
)
61 throws IOException
, UnsupportedCallbackException
{
63 if (wasUsedAlready
&& !isSubmitted() && !isCanceled()) {
65 for (Control control
: getChildren())
71 for (Callback callback
: callbacks
)
72 checkCallbackSupported(callback
);
73 // create controls synchronously in the UI thread
74 getDisplay().syncExec(new Runnable() {
78 createCallbackHandlers(callbacks
);
83 wasUsedAlready
= true;
85 while (!isSubmitted() && !isCanceled()) {
88 } catch (InterruptedException e
) {
93 cleanCallbacksAfterCancel(callbacks
);
96 public void checkCallbackSupported(Callback callback
)
97 throws UnsupportedCallbackException
{
98 if (callback
instanceof TextOutputCallback
99 || callback
instanceof NameCallback
100 || callback
instanceof PasswordCallback
101 || callback
instanceof LocaleCallback
) {
104 throw new UnsupportedCallbackException(callback
);
109 * Set writable callbacks to null if the handle is canceled (check is done
112 public void cleanCallbacksAfterCancel(Callback
[] callbacks
) {
114 for (Callback callback
: callbacks
) {
115 if (callback
instanceof NameCallback
) {
116 ((NameCallback
) callback
).setName(null);
117 } else if (callback
instanceof PasswordCallback
) {
118 PasswordCallback pCallback
= (PasswordCallback
) callback
;
119 char[] arr
= pCallback
.getPassword();
121 Arrays
.fill(arr
, '*');
122 pCallback
.setPassword(null);
129 public void createCallbackHandlers(Callback
[] callbacks
) {
130 Composite composite
= this;
131 for (int i
= 0; i
< callbacks
.length
; i
++) {
132 Callback callback
= callbacks
[i
];
133 if (callback
instanceof TextOutputCallback
) {
134 createLabelTextoutputHandler(composite
,
135 (TextOutputCallback
) callback
);
136 } else if (callback
instanceof NameCallback
) {
137 createNameHandler(composite
, (NameCallback
) callback
);
138 } else if (callback
instanceof PasswordCallback
) {
139 createPasswordHandler(composite
, (PasswordCallback
) callback
);
140 } else if (callback
instanceof LocaleCallback
) {
141 createLocaleHandler(composite
, (LocaleCallback
) callback
);
146 protected Text
createNameHandler(Composite composite
,
147 final NameCallback callback
) {
148 Label label
= new Label(composite
, SWT
.NONE
);
149 label
.setText(callback
.getPrompt());
150 final Text text
= new Text(composite
, SWT
.SINGLE
| SWT
.LEAD
152 if (callback
.getDefaultName() != null) {
153 // set default value, if provided
154 text
.setText(callback
.getDefaultName());
155 callback
.setName(callback
.getDefaultName());
157 text
.setLayoutData(new GridData(SWT
.FILL
, SWT
.FILL
, true, true));
158 text
.addModifyListener(new ModifyListener() {
159 private static final long serialVersionUID
= 7300032545287292973L;
161 public void modifyText(ModifyEvent event
) {
162 callback
.setName(text
.getText());
165 text
.addSelectionListener(new SelectionListener() {
166 private static final long serialVersionUID
= 1820530045857665111L;
169 public void widgetSelected(SelectionEvent e
) {
173 public void widgetDefaultSelected(SelectionEvent e
) {
178 text
.addKeyListener(new KeyListener() {
179 private static final long serialVersionUID
= -8698107785092095713L;
182 public void keyReleased(KeyEvent e
) {
186 public void keyPressed(KeyEvent e
) {
192 protected Text
createPasswordHandler(Composite composite
,
193 final PasswordCallback callback
) {
194 Label label
= new Label(composite
, SWT
.NONE
);
195 label
.setText(callback
.getPrompt());
196 final Text passwordText
= new Text(composite
, SWT
.SINGLE
| SWT
.LEAD
197 | SWT
.PASSWORD
| SWT
.BORDER
);
199 .setLayoutData(new GridData(SWT
.FILL
, SWT
.FILL
, true, true));
200 passwordText
.addModifyListener(new ModifyListener() {
201 private static final long serialVersionUID
= -7099363995047686732L;
203 public void modifyText(ModifyEvent event
) {
204 callback
.setPassword(passwordText
.getTextChars());
207 passwordText
.addSelectionListener(new SelectionListener() {
208 private static final long serialVersionUID
= 1820530045857665111L;
211 public void widgetSelected(SelectionEvent e
) {
215 public void widgetDefaultSelected(SelectionEvent e
) {
222 protected Combo
createLocaleHandler(Composite composite
,
223 final LocaleCallback callback
) {
224 String
[] labels
= callback
.getSupportedLocalesLabels();
225 if (labels
.length
== 0)
227 Label label
= new Label(composite
, SWT
.NONE
);
228 label
.setText(callback
.getPrompt());
230 final Combo combo
= new Combo(composite
, SWT
.READ_ONLY
);
231 combo
.setItems(labels
);
232 combo
.select(callback
.getDefaultIndex());
233 combo
.setLayoutData(new GridData(SWT
.FILL
, SWT
.FILL
, true, true));
234 combo
.addSelectionListener(new SelectionListener() {
235 private static final long serialVersionUID
= 38678989091946277L;
238 public void widgetSelected(SelectionEvent e
) {
239 callback
.setSelectedIndex(combo
.getSelectionIndex());
243 public void widgetDefaultSelected(SelectionEvent e
) {
249 protected Label
createLabelTextoutputHandler(Composite composite
,
250 final TextOutputCallback callback
) {
251 Label label
= new Label(composite
, SWT
.NONE
);
252 label
.setText(callback
.getMessage());
253 GridData data
= new GridData(SWT
.FILL
, SWT
.FILL
, true, true);
254 data
.horizontalSpan
= 2;
255 label
.setLayoutData(data
);
257 // TODO: find a way to pass this information
258 // int messageType = callback.getMessageType();
259 // int dialogMessageType = IMessageProvider.NONE;
260 // switch (messageType) {
261 // case TextOutputCallback.INFORMATION:
262 // dialogMessageType = IMessageProvider.INFORMATION;
264 // case TextOutputCallback.WARNING:
265 // dialogMessageType = IMessageProvider.WARNING;
267 // case TextOutputCallback.ERROR:
268 // dialogMessageType = IMessageProvider.ERROR;
271 // setMessage(callback.getMessage(), dialogMessageType);
274 synchronized boolean isSubmitted() {
278 synchronized boolean isCanceled() {
282 protected synchronized void submit() {
287 protected synchronized void cancel() {