Coverage report

| %line | %branch
--- | --- | ---
tsukuba_bunko.peko.scenario.PSMLUtil |
25% |
58% |

1 |  |
     /*
2 |  |
      * "Peko" Visual Novel System
3 |  |
      *
4 |  |
      * All Rights Reserved.
5 |  |
      * Copyright (c) 1999-2003 Tsukuba Bunko.
6 |  |
      *
7 |  |
      * $Id: PSMLUtil.java,v 1.1 2005/07/11 12:49:18 ppoi Exp $
8 |  |
      */
9 |  |
     package tsukuba_bunko.peko.scenario;
10 |  |
11 |  |
     import	java.util.StringTokenizer;
12 |  |
13 |  |
     import	org.xml.sax.Attributes;
14 |  |
15 |  |
     import	tsukuba_bunko.peko.Logger;
16 |  |
17 |  |
     import	tsukuba_bunko.peko.scenario.SceneContext;
18 |  |
19 |  |
20 |  |
     /**
21 |  |
      * PSML の処理に必要なユーティリティメソッドを提供します。
22 |  |
      * @author	$Author: ppoi $
23 |  |
      * @version	$Revision: 1.1 $
24 |  |
      */
25 |  |
     public final class PSMLUtil	{
26 |  |
27 |  |
     	/**
28 |  |
     	 * <code>PSMLUtil</code> のインスタンスは生成できません。
29 |  |
     	 */
30 |  |
     	private PSMLUtil()
31 | 0 |
     	{
32 | 0 |
     	}
33 |  |
34 |  |
35 |  |
     	/**
36 |  |
     	 * ISO 制御文字を除去します。
37 |  |
     	 * @param	string	除去対象の文字列
38 |  |
     	 * @return	除去処理後の文字列
39 |  |
     	 */
40 |  |
     	public static String removeISOControlChar( String string )
41 |  |
     	{
42 | 25 |
     		if( (string == null) || (string.length() == 0) )	{
43 | 0 |
     			return string;
44 |  |
     		}
45 |  |
46 | 25 |
     		int	beginIndex = -1;
47 | 25 |
     		boolean	isISOControlCharSequence = false;
48 |  |
49 | 25 |
     		int	length = string.length();
50 | 25 |
     		StringBuffer	buffer = null;
51 | 620 |
     		for( int current = 0; current < length; ++current )	{
52 | 595 |
     			if( Character.isISOControl(string.charAt(current)) )	{
53 | 155 |
     				if( !isISOControlCharSequence )	{
54 | 60 |
     					if( buffer == null )	{
55 | 20 |
     						if( current == 0 )	{
56 | 15 |
     							buffer = new StringBuffer();
57 | 15 |
     						}
58 |  |
     						else	{
59 | 5 |
     							buffer = new StringBuffer( string.substring(0, current) );
60 |  |
     						}
61 | 5 |
     					}
62 |  |
     					else	{
63 | 40 |
     						buffer.append( string.substring(beginIndex, current) );
64 |  |
     					}
65 | 60 |
     					isISOControlCharSequence = true;
66 | 60 |
     					beginIndex = -1;
67 | 60 |
     				}
68 |  |
     			}
69 |  |
     			else	{
70 | 440 |
     				if( isISOControlCharSequence )	{
71 | 45 |
     					beginIndex = current;
72 | 45 |
     					isISOControlCharSequence = false;
73 |  |
     				}
74 |  |
     			}
75 |  |
     		}
76 | 25 |
     		if( beginIndex != -1 )	{
77 | 5 |
     			buffer.append( string.substring(beginIndex) );
78 |  |
     		}
79 |  |
80 | 25 |
     		if( buffer != null )	{
81 | 20 |
     			return new String( buffer );
82 |  |
     		}
83 |  |
     		else	{
84 | 5 |
     			return string;
85 |  |
     		}
86 |  |
     	}
87 |  |
88 |  |
89 |  |
     	/**
90 |  |
     	 * PSML 1.0 "Scene" ネームスペース、ローカルネームスペースの順で属性値を検索します。
91 |  |
     	 * @param	localName	属性名のローカル名
92 |  |
     	 * @return	属性値。属性が定義されていない場合は <code>null</code>
93 |  |
     	 */
94 |  |
     	public static String getAttributeValue( Attributes attrs, String localName )
95 |  |
     	{
96 | 0 |
     		String	value = attrs.getValue( ElementHandler.NAMESPACE_SCENE, localName );
97 | 0 |
     		if( value == null )	{
98 | 0 |
     			value = attrs.getValue( localName );
99 |  |
     		}
100 |  |
101 | 0 |
     		if( (value == null) || (value.length() == 0) )	{
102 | 0 |
     			return null;
103 |  |
     		}
104 |  |
     		else	{
105 | 0 |
     			value = PSMLUtil.removeISOControlChar(value).trim();
106 | 0 |
     			if( value.length() == 0 )	{
107 | 0 |
     				Logger.warn( MessageIDs.SCN0011W, new Object[]{localName} );
108 | 0 |
     				return null;
109 |  |
     			}
110 |  |
     			else	{
111 | 0 |
     				return value;
112 |  |
     			}
113 |  |
     		}
114 |  |
     	}
115 |  |
116 |  |
     	/**
117 |  |
     	 * <code>attrs</code> からテストを取り出し、シナリオ文脈 <code>context</code> で評価可能かどうかを判定します。
118 |  |
     	 * @param	attrs	要素の属性セット
119 |  |
     	 * @param	context	現在のシナリオ文脈
120 |  |
     	 * @return	評価可能の場合 <code>true</code>、評価不可の場合 <code>false</code>
121 |  |
     	 */
122 |  |
     	public static final boolean isEvaluatable( Attributes attrs, SceneContext context )
123 |  |
     	{
124 | 0 |
     		return isEvaluatable( PSMLUtil.getAttributeValue(attrs, "test"), context );
125 |  |
     	}
126 |  |
127 |  |
     	/**
128 |  |
     	 * <code>target</code> で指定されるテストを使用し、シナリオ文脈 <code>context</code> で評価可能かどうかを判定します。
129 |  |
     	 * @param	target	テスト
130 |  |
     	 * @param	context	現在のシナリオ文脈
131 |  |
     	 * @return	評価可能の場合 <code>true</code>、評価不可の場合 <code>false</code>
132 |  |
     	 */
133 |  |
     	public static final boolean isEvaluatable( String target, SceneContext context )
134 |  |
     	{
135 | 0 |
     		if( (target == null) || (target.length() == 0) )	{
136 | 0 |
     			return true;
137 |  |
     		}
138 | 0 |
     		else if( context == null )	{
139 | 0 |
     			return false;
140 |  |
     		}
141 |  |
     		else	{
142 | 0 |
     			boolean	result = false;
143 |  |
144 | 0 |
     			boolean	multiple = (target.charAt(0) == '[');
145 | 0 |
     			boolean	inBracket = false;
146 | 0 |
     			boolean	individualResult = true;
147 |  |
148 | 0 |
     			StringTokenizer	st = new StringTokenizer( target, "[],", true );
149 | 0 |
     			String	token = null;
150 | 0 |
     			String	lastToken = null;
151 | 0 |
     			int	position = 0;
152 | 0 |
     			while( st.hasMoreTokens() )	{
153 | 0 |
     				lastToken = token;
154 | 0 |
     				token = st.nextToken();
155 | 0 |
     				position += token.length();
156 | 0 |
     				token = token.trim();
157 |  |
158 | 0 |
     				if( !multiple )	{
159 | 0 |
     					if( "[".equals(token) || "]".equals(token) )	{
160 | 0 |
     						Logger.warn( MessageIDs.SCN0008W, new Object[]{String.valueOf(position), token} );
161 | 0 |
     						return false;
162 |  |
     					}
163 | 0 |
     					else if( !",".equals(token) )	{
164 | 0 |
     						if( token.charAt(0) == '!' )	{
165 | 0 |
     							if( token.length() == 1 )	{
166 | 0 |
     								Logger.warn( MessageIDs.SCN0008W, new Object[]{String.valueOf(position), token} );
167 | 0 |
     								return false;
168 |  |
     							}
169 | 0 |
     							token = token.substring( 1 );
170 | 0 |
     							individualResult = individualResult && !context.isDeclaredFlag(token);
171 | 0 |
     						}
172 |  |
     						else	{
173 | 0 |
     							individualResult = individualResult && context.isDeclaredFlag(token);
174 |  |
     						}
175 | 0 |
     					}
176 |  |
     				}
177 |  |
     				else	{
178 | 0 |
     					if( inBracket )	{
179 | 0 |
     						if( "]".equals(token) )	{
180 | 0 |
     							if( (lastToken != null) && ",".equals(lastToken) )	{
181 | 0 |
     								Logger.warn( MessageIDs.SCN0008W, new Object[]{String.valueOf(position), token} );
182 | 0 |
     								return false;
183 |  |
     							}
184 |  |
     							else	{
185 | 0 |
     								result = result || individualResult;
186 | 0 |
     								individualResult = true;
187 | 0 |
     								inBracket = false;
188 |  |
     							}
189 | 0 |
     						}
190 | 0 |
     						else if( !",".equals(token) )	{
191 | 0 |
     							if( token.charAt(0) == '!' )	{
192 | 0 |
     								if( token.length() == 1 )	{
193 | 0 |
     									Logger.warn( MessageIDs.SCN0008W, new Object[]{String.valueOf(position), token} );
194 | 0 |
     									return false;
195 |  |
     								}
196 | 0 |
     								token = token.substring( 1 );
197 | 0 |
     								individualResult = individualResult && !context.isDeclaredFlag(token);
198 | 0 |
     							}
199 |  |
     							else	{
200 | 0 |
     								individualResult = individualResult && context.isDeclaredFlag(token);
201 |  |
     							}
202 | 0 |
     						}
203 |  |
     					}
204 |  |
     					else	{
205 | 0 |
     						if( "[".equals(token) )	{
206 | 0 |
     							inBracket = true;
207 | 0 |
     						}
208 |  |
     						else	{
209 | 0 |
     							Logger.warn( MessageIDs.SCN0008W, new Object[]{String.valueOf(position), token} );
210 | 0 |
     							return false;
211 |  |
     						}
212 |  |
     					}
213 |  |
     				}
214 |  |
     			}
215 |  |
216 | 0 |
     			if( multiple )	{
217 | 0 |
     				if( !"]".equals(token) )	{
218 | 0 |
     					Logger.warn( MessageIDs.SCN0008W, new Object[]{String.valueOf(position), token} );
219 | 0 |
     					return false;
220 |  |
     				}
221 |  |
     			}
222 |  |
     			else	{
223 | 0 |
     				if( ",".equals(token) )	{
224 | 0 |
     					Logger.warn( MessageIDs.SCN0008W, new Object[]{String.valueOf(position), token} );
225 | 0 |
     					return false;
226 |  |
     				}
227 |  |
     				else	{
228 | 0 |
     					result = individualResult;
229 |  |
     				}
230 |  |
     			}
231 | 0 |
     			return result;
232 |  |
     		}
233 |  |
     	}
234 |  |
     }

This report is generated by jcoverage, Maven and Maven JCoverage Plugin.