| /* |
| * Licensed to the Apache Software Foundation (ASF) under one or more |
| * contributor license agreements. See the NOTICE file distributed with |
| * this work for additional information regarding copyright ownership. |
| * The ASF licenses this file to you under the Apache License, |
| * Version 2.0 (the "License"); you may not use this file except in |
| * compliance with the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| package org.apache.pivot.wtk; |
| |
| import java.util.Iterator; |
| |
| import org.apache.pivot.beans.DefaultProperty; |
| import org.apache.pivot.collections.ArrayList; |
| import org.apache.pivot.collections.Sequence; |
| import org.apache.pivot.json.JSONSerializer; |
| import org.apache.pivot.serialization.SerializationException; |
| import org.apache.pivot.util.ImmutableIterator; |
| import org.apache.pivot.util.ListenerList; |
| import org.apache.pivot.util.Resources; |
| |
| /** |
| * Class representing an "alert", a dialog commonly used to facilitate simple |
| * user interaction. |
| */ |
| @DefaultProperty("body") |
| public class Alert extends Dialog { |
| /** |
| * Option sequence implementation. |
| */ |
| public final class OptionSequence implements Sequence<Object>, Iterable<Object> { |
| private OptionSequence() { |
| } |
| |
| @Override |
| public int add(Object option) { |
| int index = getLength(); |
| insert(option, index); |
| |
| return index; |
| } |
| |
| @Override |
| public void insert(Object option, int index) { |
| if (option == null) { |
| throw new IllegalArgumentException("option is null."); |
| } |
| |
| options.insert(option, index); |
| |
| if (selectedOptionIndex >= index) { |
| selectedOptionIndex++; |
| } |
| |
| alertListeners.optionInserted(Alert.this, index); |
| } |
| |
| @Override |
| public Component update(int index, Object option) { |
| throw new UnsupportedOperationException(); |
| } |
| |
| @Override |
| public int remove(Object option) { |
| int index = indexOf(option); |
| if (index != -1) { |
| remove(index, 1); |
| } |
| |
| return index; |
| } |
| |
| @Override |
| public Sequence<Object> remove(int index, int count) { |
| Sequence<Object> removed = options.remove(index, count); |
| |
| if (removed.getLength() > 0) { |
| if (selectedOptionIndex >= index) { |
| if (selectedOptionIndex < index + count) { |
| selectedOptionIndex = -1; |
| } else { |
| selectedOptionIndex -= count; |
| } |
| } |
| |
| alertListeners.optionsRemoved(Alert.this, index, removed); |
| } |
| |
| return removed; |
| } |
| |
| @Override |
| public Object get(int index) { |
| return options.get(index); |
| } |
| |
| @Override |
| public int indexOf(Object option) { |
| return options.indexOf(option); |
| } |
| |
| @Override |
| public int getLength() { |
| return options.getLength(); |
| } |
| |
| @Override |
| public Iterator<Object> iterator() { |
| return new ImmutableIterator<>(options.iterator()); |
| } |
| } |
| |
| private static class AlertListenerList extends WTKListenerList<AlertListener> implements |
| AlertListener { |
| @Override |
| public void messageTypeChanged(Alert alert, MessageType previousMessageType) { |
| for (AlertListener listener : this) { |
| listener.messageTypeChanged(alert, previousMessageType); |
| } |
| } |
| |
| @Override |
| public void messageChanged(Alert alert, String previousMessage) { |
| for (AlertListener listener : this) { |
| listener.messageChanged(alert, previousMessage); |
| } |
| } |
| |
| @Override |
| public void bodyChanged(Alert alert, Component previousBody) { |
| for (AlertListener listener : this) { |
| listener.bodyChanged(alert, previousBody); |
| } |
| } |
| |
| @Override |
| public void optionInserted(Alert alert, int index) { |
| for (AlertListener listener : this) { |
| listener.optionInserted(alert, index); |
| } |
| } |
| |
| @Override |
| public void optionsRemoved(Alert alert, int index, Sequence<?> removed) { |
| for (AlertListener listener : this) { |
| listener.optionsRemoved(alert, index, removed); |
| } |
| } |
| |
| @Override |
| public void selectedOptionChanged(Alert alert, int previousSelectedOption) { |
| for (AlertListener listener : this) { |
| listener.selectedOptionChanged(alert, previousSelectedOption); |
| } |
| } |
| } |
| |
| private MessageType messageType = null; |
| private String message = null; |
| private Component body = null; |
| |
| private ArrayList<Object> options = new ArrayList<>(); |
| private OptionSequence optionSequence = new OptionSequence(); |
| private int selectedOptionIndex = -1; |
| |
| private AlertListenerList alertListeners = new AlertListenerList(); |
| |
| private static Resources resources = null; |
| |
| static { |
| try { |
| resources = new Resources(Alert.class.getName()); |
| } catch (Exception exception) { |
| throw new RuntimeException(exception); |
| } |
| } |
| |
| public Alert() { |
| this(null, null, null); |
| } |
| |
| public Alert(String message) { |
| this(null, message, null, true); |
| } |
| |
| public Alert(MessageType messageType, String message, Sequence<?> options) { |
| this(messageType, message, options, true); |
| } |
| |
| public Alert(MessageType messageType, String message, Sequence<?> options, boolean modal) { |
| this(messageType, message, options, null, modal); |
| } |
| |
| public Alert(MessageType messageType, String message, Sequence<?> options, Component body) { |
| this(messageType, message, options, body, true); |
| } |
| |
| public Alert(MessageType messageType, String message, Sequence<?> options, Component body, |
| boolean modal) { |
| super(modal); |
| |
| setMessageType((messageType == null) ? MessageType.INFO : messageType); |
| setMessage(message); |
| setOptions((options == null) ? new ArrayList<>(resources.get("defaultOption")) : options); |
| setBody(body); |
| |
| if (messageType == null) { |
| setTitle((String) resources.get("defaultTitle")); |
| } else { |
| switch (messageType) { |
| case ERROR: |
| setTitle((String) resources.get("defaultErrorTitle")); |
| break; |
| case WARNING: |
| setTitle((String) resources.get("defaultWarningTitle")); |
| break; |
| case QUESTION: |
| setTitle((String) resources.get("defaultQuestionTitle")); |
| break; |
| case INFO: |
| setTitle((String) resources.get("defaultInfoTitle")); |
| break; |
| default: |
| setTitle((String) resources.get("defaultTitle")); |
| break; |
| } |
| } |
| |
| installSkin(Alert.class); |
| } |
| |
| public MessageType getMessageType() { |
| return messageType; |
| } |
| |
| public void setMessageType(MessageType messageType) { |
| if (messageType == null) { |
| throw new IllegalArgumentException(); |
| } |
| |
| MessageType previousMessageType = this.messageType; |
| if (previousMessageType != messageType) { |
| this.messageType = messageType; |
| alertListeners.messageTypeChanged(this, previousMessageType); |
| } |
| } |
| |
| public String getMessage() { |
| return message; |
| } |
| |
| public void setMessage(String message) { |
| String previousMessage = this.message; |
| if (previousMessage != message) { |
| this.message = message; |
| alertListeners.messageChanged(this, previousMessage); |
| } |
| } |
| |
| public Component getBody() { |
| return body; |
| } |
| |
| public void setBody(Component body) { |
| Component previousBody = this.body; |
| if (previousBody != body) { |
| this.body = body; |
| alertListeners.bodyChanged(this, previousBody); |
| } |
| } |
| |
| public OptionSequence getOptions() { |
| return optionSequence; |
| } |
| |
| public void setOptions(Sequence<?> options) { |
| optionSequence.remove(0, optionSequence.getLength()); |
| |
| if (options != null) { |
| for (int i = 0, n = options.getLength(); i < n; i++) { |
| optionSequence.add(options.get(i)); |
| } |
| |
| setSelectedOptionIndex(0); |
| } |
| } |
| |
| public void setOptions(String options) { |
| try { |
| setOptions(JSONSerializer.parseList(options)); |
| } catch (SerializationException exception) { |
| throw new IllegalArgumentException(exception); |
| } |
| } |
| |
| public int getSelectedOptionIndex() { |
| return selectedOptionIndex; |
| } |
| |
| public void setSelectedOptionIndex(int selectedOption) { |
| indexBoundsCheck("selectedOption", selectedOption, -1, options.getLength() - 1); |
| |
| int previousSelectedOption = this.selectedOptionIndex; |
| |
| if (selectedOption != previousSelectedOption) { |
| this.selectedOptionIndex = selectedOption; |
| alertListeners.selectedOptionChanged(this, previousSelectedOption); |
| } |
| } |
| |
| public Object getSelectedOption() { |
| return (selectedOptionIndex == -1) ? null : options.get(selectedOptionIndex); |
| } |
| |
| public void setSelectedOption(Object selectedOption) { |
| setSelectedOptionIndex(options.indexOf(selectedOption)); |
| } |
| |
| public ListenerList<AlertListener> getAlertListeners() { |
| return alertListeners; |
| } |
| |
| public static void alert(String message, Window owner) { |
| alert(MessageType.INFO, message, null, null, owner, null); |
| } |
| |
| public static void alert(MessageType messageType, String message, Window owner) { |
| alert(messageType, message, null, null, owner, null); |
| } |
| |
| public static void alert(MessageType messageType, String message, Window owner, |
| DialogCloseListener dialogCloseListener) { |
| alert(messageType, message, null, null, owner, dialogCloseListener); |
| } |
| |
| public static void alert(MessageType messageType, String message, Component body, Window owner) { |
| alert(messageType, message, null, body, owner, null); |
| } |
| |
| public static void alert(MessageType messageType, String message, Component body, Window owner, |
| DialogCloseListener dialogCloseListener) { |
| alert(messageType, message, null, body, owner, dialogCloseListener); |
| } |
| |
| public static void alert(MessageType messageType, String message, String title, Component body, |
| Window owner, DialogCloseListener dialogCloseListener) { |
| Alert alert = new Alert(messageType, message, null, body); |
| if (title != null) { |
| alert.setTitle(title); |
| } |
| |
| alert.open(owner.getDisplay(), owner, dialogCloseListener); |
| } |
| } |