1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.apache.myfaces.tobago.layout;
21
22 import org.apache.commons.lang.math.NumberUtils;
23 import org.slf4j.Logger;
24 import org.slf4j.LoggerFactory;
25
26 import java.util.ArrayList;
27 import java.util.Iterator;
28 import java.util.List;
29 import java.util.StringTokenizer;
30
31 public final class LayoutTokens implements Iterable<LayoutToken> {
32
33 private static final Logger LOG = LoggerFactory.getLogger(LayoutTokens.class);
34
35 private List<LayoutToken> tokens = new ArrayList<LayoutToken>();
36
37 public LayoutTokens() {
38 }
39
40 public int getSize() {
41 return tokens.size();
42 }
43
44 public void set(int index, LayoutToken token) {
45 tokens.set(index, token);
46 }
47
48 public boolean isEmpty() {
49 return getSize() == 0;
50 }
51
52 public LayoutToken get(int index) {
53 return tokens.get(index);
54 }
55
56 public void shrinkSizeTo(int size) {
57 for (int i = getSize() - 1; i >= size; i--) {
58 tokens.remove(i);
59 }
60 }
61
62 public void ensureSize(int size, LayoutToken token) {
63 for (int index = getSize(); index < size; index++) {
64 addToken(token);
65 }
66 }
67
68 public void addToken(LayoutToken token) {
69 tokens.add(token);
70 }
71
72 public List<LayoutToken> getTokens() {
73 return tokens;
74 }
75
76 public Iterator<LayoutToken> iterator() {
77 return tokens.iterator();
78 }
79
80 public static LayoutTokens parse(String[] tokens) {
81 LayoutTokens layoutTokens = new LayoutTokens();
82 for (String token : tokens) {
83 parseToken(token, layoutTokens);
84 }
85 return layoutTokens;
86 }
87
88 public static LayoutTokens parse(String tokens) {
89 return parse(tokens, null);
90 }
91
92 public static LayoutTokens parse(String tokens, LayoutToken defaultToken) {
93 LayoutTokens layoutTokens = new LayoutTokens();
94 if (tokens == null) {
95 layoutTokens.addToken(defaultToken);
96 return layoutTokens;
97 }
98 StringTokenizer tokenizer = new StringTokenizer(tokens, ";");
99
100 while (tokenizer.hasMoreTokens()) {
101 String token = tokenizer.nextToken().trim();
102 parseToken(token, layoutTokens);
103 }
104 return layoutTokens;
105 }
106
107 private static void parseToken(String token, LayoutTokens layoutTokens) {
108 LayoutToken layoutToken = parseToken(token);
109 if (layoutToken != null) {
110 layoutTokens.addToken(layoutToken);
111 }
112 }
113
114 public static LayoutToken parseToken(String token) {
115 try {
116 if ("*".equals(token)) {
117 return RelativeLayoutToken.DEFAULT_INSTANCE;
118 } else if (token == null) {
119 LOG.error("Empty layout token! Using 'auto' instead.");
120 return AutoLayoutToken.INSTANCE;
121 } else if ("fixed".equals(token) || "auto".equals(token)) {
122 return AutoLayoutToken.INSTANCE;
123 } else if ("minimum".equals(token)) {
124 return new MinimumLayoutToken();
125 } else if (isPixelToken(token)) {
126 return new PixelLayoutToken(Integer.parseInt(removeSuffix(token, PixelLayoutToken.SUFFIX)));
127 } else if (isPercentToken(token)) {
128 return new PercentLayoutToken(Integer.parseInt(removeSuffix(token, PercentLayoutToken.SUFFIX)));
129 } else if (isRelativeToken(token)) {
130 return new RelativeLayoutToken(Integer.parseInt(removeSuffix(token, RelativeLayoutToken.SUFFIX)));
131 } else {
132 LOG.error("Unknown layout token '" + token + "'! Using 'auto' instead.");
133 return AutoLayoutToken.INSTANCE;
134 }
135 } catch (NumberFormatException e) {
136 LOG.error("Error parsing layout token '" + token + "'! Using 'auto' instead.");
137 return AutoLayoutToken.INSTANCE;
138 }
139 }
140
141 static boolean isPixelToken(String token) {
142 return isNumberAndSuffix(token, PixelLayoutToken.SUFFIX);
143 }
144
145 static boolean isPercentToken(String token) {
146 return isNumberAndSuffix(token, PercentLayoutToken.SUFFIX);
147 }
148
149 static boolean isRelativeToken(String token) {
150 return isNumberAndSuffix(token, RelativeLayoutToken.SUFFIX);
151 }
152
153 static boolean isNumberAndSuffix(String token, String suffix) {
154 return token.endsWith(suffix)
155 && NumberUtils.isDigits(removeSuffix(token, suffix));
156 }
157
158 private static String removeSuffix(String token, String suffix) {
159 return token.substring(0, token.length() - suffix.length());
160 }
161
162 public String toString() {
163 StringBuilder str = new StringBuilder();
164 for (LayoutToken token : tokens) {
165 str.append(token);
166 str.append(";");
167 }
168 return str.toString();
169 }
170
171 }