001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: *
017: * $Header:$
018: */
019:
020: package org.apache.beehive.controls.runtime.webcontext;
021:
022: import java.beans.PropertyChangeListener;
023: import java.beans.PropertyChangeSupport;
024: import java.beans.PropertyVetoException;
025: import java.beans.VetoableChangeListener;
026: import java.beans.VetoableChangeSupport;
027: import java.beans.beancontext.BeanContext;
028: import java.beans.beancontext.BeanContextChild;
029: import java.beans.beancontext.BeanContextServiceAvailableEvent;
030: import java.beans.beancontext.BeanContextServiceRevokedEvent;
031: import java.beans.beancontext.BeanContextServiceRevokedListener;
032: import java.beans.beancontext.BeanContextServicesListener;
033: import java.io.IOException;
034: import java.io.ObjectOutputStream;
035: import java.io.Serializable;
036: import java.io.ObjectInputStream;
037: import java.util.EventListener;
038:
039: /**
040: * Implementation of the BeanContextChild api for Beehive controls.
041: */
042: public class ControlBeanContextChildSupport implements
043: BeanContextChild, BeanContextServiceRevokedListener,
044: BeanContextServicesListener, Serializable, EventListener {
045: private static final long serialVersionUID = 1;
046:
047: private transient BeanContext _beanContext;
048: private transient boolean _vetodOnce;
049: private BeanContextChild _peer;
050: private PropertyChangeSupport _propertyChangeSupport;
051: private VetoableChangeSupport _vetoableChangeSupport;
052:
053: /**
054: * Constructor.
055: */
056: public ControlBeanContextChildSupport() {
057: _beanContext = null;
058: _peer = this ;
059: _vetodOnce = false;
060: _propertyChangeSupport = new PropertyChangeSupport(_peer);
061: _vetoableChangeSupport = new VetoableChangeSupport(_peer);
062: }
063:
064: /**
065: * Constructor -- java bean implements BeanContextChild and delegates the interface
066: * to this implementation.
067: *
068: * @param bcc
069: */
070: public ControlBeanContextChildSupport(BeanContextChild bcc) {
071: _beanContext = null;
072: _vetodOnce = false;
073: _peer = (bcc != null) ? bcc : this ;
074: _propertyChangeSupport = new PropertyChangeSupport(_peer);
075: _vetoableChangeSupport = new VetoableChangeSupport(_peer);
076: }
077:
078: /**
079: * <p/>
080: * Objects that implement this interface,
081: * shall fire a java.beans.PropertyChangeEvent, with parameters:
082: * <p/>
083: * propertyName "beanContext", oldValue (the previous nesting
084: * <code>BeanContext</code> instance, or <code>null</code>),
085: * newValue (the current nesting
086: * <code>BeanContext</code> instance, or <code>null</code>).
087: * <p/>
088: * A change in the value of the nesting BeanContext property of this
089: * BeanContextChild may be vetoed by throwing the appropriate exception.
090: * </p>
091: *
092: * @param bc The <code>BeanContext</code> with which
093: * to associate this <code>BeanContextChild</code>.
094: */
095: public synchronized void setBeanContext(BeanContext bc)
096: throws PropertyVetoException {
097:
098: if (bc == _beanContext)
099: return;
100:
101: // track if veto'd the first time, then then second time remove anyway (dont except);
102: if (!_vetodOnce) {
103: try {
104: _vetoableChangeSupport.fireVetoableChange(
105: "beanContext", _beanContext, bc);
106: } catch (PropertyVetoException pve) {
107: _vetodOnce = true;
108: throw pve;
109: }
110: }
111:
112: releaseBeanContextResources();
113: BeanContext oldValue = _beanContext;
114: _beanContext = bc;
115: _vetodOnce = false;
116: firePropertyChange("beanContext", oldValue, _beanContext);
117: }
118:
119: /**
120: * Gets the <code>BeanContext</code> associated
121: * with this <code>BeanContextChild</code>.
122: *
123: * @return the <code>BeanContext</code> associated
124: * with this <code>BeanContextChild</code>.
125: */
126: public synchronized BeanContext getBeanContext() {
127: return _beanContext;
128: }
129:
130: /**
131: * Adds a <code>PropertyChangeListener</code>
132: * to this <code>BeanContextChild</code>
133: * in order to receive a <code>PropertyChangeEvent</code>
134: * whenever the specified property has changed.
135: *
136: * @param name the name of the property to listen on
137: * @param pcl the <code>PropertyChangeListener</code> to add
138: */
139: public void addPropertyChangeListener(String name,
140: PropertyChangeListener pcl) {
141: _propertyChangeSupport.addPropertyChangeListener(name, pcl);
142: }
143:
144: /**
145: * Removes a <code>PropertyChangeListener</code> from this
146: * <code>BeanContextChild</code> so that it no longer
147: * receives <code>PropertyChangeEvents</code> when the
148: * specified property is changed.
149: *
150: * @param name the name of the property that was listened on
151: * @param pcl the <code>PropertyChangeListener</code> to remove
152: */
153: public void removePropertyChangeListener(String name,
154: PropertyChangeListener pcl) {
155: _propertyChangeSupport.removePropertyChangeListener(name, pcl);
156: }
157:
158: /**
159: * Adds a <code>VetoableChangeListener</code> to
160: * this <code>BeanContextChild</code>
161: * to receive events whenever the specified property changes.
162: *
163: * @param name the name of the property to listen on
164: * @param vcl the <code>VetoableChangeListener</code> to add
165: */
166: public void addVetoableChangeListener(String name,
167: VetoableChangeListener vcl) {
168: _vetoableChangeSupport.addVetoableChangeListener(name, vcl);
169: }
170:
171: /**
172: * Removes a <code>VetoableChangeListener</code> from this
173: * <code>BeanContextChild</code> so that it no longer receives
174: * events when the specified property changes.
175: *
176: * @param name the name of the property that was listened on.
177: * @param vcl the <code>VetoableChangeListener</code> to remove.
178: */
179: public void removeVetoableChangeListener(String name,
180: VetoableChangeListener vcl) {
181: _vetoableChangeSupport.addVetoableChangeListener(name, vcl);
182: }
183:
184: /**
185: * The service named has been registered. getService requests for
186: * this service may now be made.
187: *
188: * @param bcsae the <code>BeanContextServiceAvailableEvent</code>
189: */
190: public void serviceAvailable(BeanContextServiceAvailableEvent bcsae) {
191: // noop
192: }
193:
194: /**
195: * The service named has been revoked. getService requests for
196: * this service will no longer be satisifed.
197: *
198: * @param bcsre the <code>BeanContextServiceRevokedEvent</code> received
199: * by this listener.
200: */
201: public void serviceRevoked(BeanContextServiceRevokedEvent bcsre) {
202: // Noop
203: }
204:
205: /**
206: * ***************************************************************
207: */
208:
209: /**
210: * Get the delegate for this child.
211: */
212: protected BeanContextChild getPeer() {
213: return _peer;
214: }
215:
216: /**
217: * Fire a property change event.
218: * @param name
219: * @param oldValue
220: * @param newValue
221: */
222: protected void firePropertyChange(String name, Object oldValue,
223: Object newValue) {
224: _propertyChangeSupport.firePropertyChange(name, oldValue,
225: newValue);
226: }
227:
228: /**
229: * Release any resources that may have been acumlated from the current bean context, invoked
230: * by setBeanContext BEFORE the context is changed.
231: */
232: protected void releaseBeanContextResources() {
233: // noop
234: }
235:
236: /**
237: * Serialization support -- throw IOException if a non-serializable delegate is present.
238: *
239: * @param out
240: */
241: private void writeObject(ObjectOutputStream out) throws IOException {
242: if (!_peer.equals(this ) && !(_peer instanceof Serializable)) {
243: throw new IOException(
244: "Bean context child delegate does not support serialization!!!");
245: }
246: out.defaultWriteObject();
247: }
248:
249: /**
250: * Deserialization support -- just deserialize.
251: *
252: * @param in
253: * @throws IOException
254: * @throws ClassNotFoundException
255: */
256: private void readObject(ObjectInputStream in) throws IOException,
257: ClassNotFoundException {
258: in.defaultReadObject();
259: }
260: }
|