KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > nightlabs > inheritance > InheritenceManager


1 /* ************************************************************************** *
2  * Copyright (C) 2004 NightLabs GmbH, Marco Schulze *
3  * All rights reserved. *
4  * http://www.NightLabs.de *
5  * *
6  * This program and the accompanying materials are free software; you can re- *
7  * distribute it and/or modify it under the terms of the GNU General Public *
8  * License as published by the Free Software Foundation; either ver 2 of the *
9  * License, or any later version. *
10  * *
11  * This module is distributed in the hope that it will be useful, but WITHOUT *
12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FIT- *
13  * NESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more *
14  * details. *
15  * *
16  * You should have received a copy of the GNU General Public License along *
17  * with this module; if not, write to the Free Software Foundation, Inc.: *
18  * 59 Temple Place, Suite 330 *
19  * Boston MA 02111-1307 *
20  * USA *
21  * *
22  * Or get it online: *
23  * http://www.opensource.org/licenses/gpl-license.php *
24  * *
25  * In case, you want to use this module or parts of it in a proprietary pro- *
26  * ject, you can purchase it under the NightLabs Commercial License. Please *
27  * contact NightLabs GmbH under info AT nightlabs DOT com for more infos or *
28  * visit http://www.NightLabs.com *
29  * ************************************************************************** */

30
31 /*
32  * Created on 17.10.2004
33  */

34 package com.nightlabs.inheritance;
35
36 import java.lang.reflect.Field JavaDoc;
37 import java.lang.reflect.Modifier JavaDoc;
38 import java.util.ArrayList JavaDoc;
39 import java.util.Iterator JavaDoc;
40
41 import org.apache.log4j.Logger;
42
43 /**
44  * @author Marco Schulze - marco at nightlabs dot de
45  */

46 public class InheritenceManager
47 {
48     public static final Logger LOGGER = Logger.getLogger(InheritenceManager.class);
49
50     public InheritenceManager() { }
51     
52     protected void callPreInherit(Inheritable obj)
53     {
54         if (!(obj instanceof InheritanceCallbacks))
55             return;
56         
57         ((InheritanceCallbacks)obj).preInherit();
58     }
59     
60     protected void callPostInherit(Inheritable obj)
61     {
62         if (!(obj instanceof InheritanceCallbacks))
63             return;
64         
65         ((InheritanceCallbacks)obj).postInherit();
66     }
67
68     public void inheritAllFields(Inheritable mother, Inheritable child)
69     {
70         callPreInherit(mother);
71         callPreInherit(child);
72         
73         Class JavaDoc clazz = mother.getClass();
74         ArrayList JavaDoc allFields = new ArrayList JavaDoc();
75
76         Class JavaDoc fcl = clazz;
77         while (fcl != Object JavaDoc.class) {
78             Field JavaDoc[] fields = fcl.getDeclaredFields();
79             for (int i = 0; i < fields.length; ++i)
80                 allFields.add(fields[i]);
81
82             fcl = fcl.getSuperclass();
83         } // while (fcl != Object.class) {
84

85         for (Iterator JavaDoc it = allFields.iterator(); it.hasNext(); ) {
86             Field JavaDoc f = (Field JavaDoc)it.next();
87
88             if (Modifier.isStatic(f.getModifiers()))
89                 continue;
90             
91             FieldMetaData fmd = mother.getFieldMetaData(f.getName());
92             if (fmd != null)
93                 inheritField(mother, child, clazz, f, fmd);
94         } // for (int i = 0; i < field.length; ++i) {
95

96         callPostInherit(mother);
97         callPostInherit(child);
98     }
99
100     /**
101      * This is a helper method, that does the actual field copying.
102      */

103     protected void inheritField(
104             Inheritable mother, Inheritable child,
105             Class JavaDoc motherClass, Field JavaDoc field,
106             FieldMetaData motherFieldMetaData)
107     {
108         LOGGER.debug("inheritField(...): mother=\""+mother+"\" child=\""+child+"\" field=\""+field.getName()+"\"");
109
110         Class JavaDoc childClass = child.getClass();
111         if (!motherClass.isAssignableFrom(childClass))
112             throw new IllegalArgumentException JavaDoc("Child class is not identical to or inheriting the mother class!");
113
114         FieldMetaData childFieldMetaData = child.getFieldMetaData(field.getName());
115         if (childFieldMetaData == null)
116             throw new NullPointerException JavaDoc("Child \""+child+"\" returned no FieldMetaData for field \""+field.getName()+"\"!");
117
118         
119         if ((motherFieldMetaData.getWritableByChildren() & FieldMetaData.WRITABLEBYCHILDREN_YES) > 0) {
120
121             if ((childFieldMetaData.getWritableByChildren() & FieldMetaData.WRITABLEBYCHILDREN_YES) == 0 &&
122                     (childFieldMetaData.getWritableByChildren() & FieldMetaData.WRITABLEBYCHILDREN_INHERITED) > 0)
123             {
124                 childFieldMetaData.setWritableByChildren(
125                         (byte)(FieldMetaData.WRITABLEBYCHILDREN_YES | FieldMetaData.WRITABLEBYCHILDREN_INHERITED));
126             }
127
128             childFieldMetaData.setWritable(true);
129         }
130         else {
131             if (childFieldMetaData.isWritable())
132                 childFieldMetaData.setWritable(false);
133
134             if (childFieldMetaData.getWritableByChildren() == FieldMetaData.WRITABLEBYCHILDREN_YES)
135                 childFieldMetaData.setWritableByChildren((byte)(FieldMetaData.WRITABLEBYCHILDREN_NO | FieldMetaData.WRITABLEBYCHILDREN_INHERITED));
136
137             if (!childFieldMetaData.isValueInherited())
138                 childFieldMetaData.setValueInherited(true); // ensure it will be overwritten
139
}
140
141         if (childFieldMetaData.isValueInherited()) {
142             FieldInheriter fieldInheriter = child.getFieldInheriter(field.getName());
143             if (fieldInheriter == null)
144                 throw new NullPointerException JavaDoc("fieldInheriter must not be null!");
145             fieldInheriter.copyFieldValue(
146                     mother, child, motherClass, childClass, field, motherFieldMetaData, childFieldMetaData
147                     );
148         }
149     }
150 }
151
Popular Tags