001 
002 /*
003  *  JScripter Simulation 1.0 - For Java To Script
004  *  Copyright (C) 2008-2011  J.J.Liu<jianjunliu@126.com> <http://www.jscripter.org>
005  *  
006  *  This program is free software: you can redistribute it and/or modify
007  *  it under the terms of the GNU Affero General Public License as published by
008  *  the Free Software Foundation, either version 3 of the License, or
009  *  (at your option) any later version.
010  *  
011  *  This program is distributed in the hope that it will be useful,
012  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
013  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
014  *  GNU Affero General Public License for more details.
015  *  
016  *  You should have received a copy of the GNU Affero General Public License
017  *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
018  */
019 
020 package org.jscripter.sim;
021 
022 import java.util.Locale;
023 import java.util.regex.Matcher;
024 
025 import js.ArrayLike;
026 import js.Js;
027 import js.RegExpLike;
028 import js.StringLike;
029 import js.Vars;
030 import js.core.JsFunction;
031 
032 final class SimStringLike implements StringLike
033 {
034     private String s;
035 
036     public SimStringLike(String s) {
037         this.s = s;
038     }
039     //@Override
040     public final int length() {
041         return s.length();
042     }
043     //@Override
044     public final String charAt(Object index) {
045         return new String(new char[]{s.charAt(((Number)Js.valueOf(index)).intValue())});
046     }
047     //@Override
048     public final Character charCodeAt(Object index) {
049         return s.charAt(((Number)Js.valueOf(index)).intValue());
050     }
051     //@Override
052     public final String concat(Object other) {
053         return s.concat(Js.toString(other));
054     }
055     //@Override
056     public final String concat(Vars<?> args) {
057         String str = s;
058         ArrayLike<?> aa = args.var();
059         for (int i = 0, len = aa.length(); i < len; i++) {
060             str = str.concat(Js.toString(aa.get(i)));
061         }
062         return str;
063     }
064     //@Override
065     public final Integer indexOf(Object other) {
066         return s.indexOf(Js.toString(other));
067     }
068     //@Override
069     public final Integer indexOf(Object other, Object pos) {
070         return s.indexOf(Js.toString(other), SimUtil.getNumber(pos).intValue());
071     }
072     //@Override
073     public final Integer lastIndexOf(Object other) {
074         return s.lastIndexOf(Js.toString(other));
075     }
076     //@Override
077     public final Integer lastIndexOf(Object other, Object pos) {
078         return s.lastIndexOf(Js.toString(other), SimUtil.getNumber(pos).intValue());
079     }
080     //@Override
081     public final Integer localeCompare(Object other) {
082         return s.compareTo(Js.toString(other));
083     }
084     //@Override
085     public final ArrayLike<?> match(RegExpLike regexp) {
086         return regexp.exec(s);
087     }
088     //@Override
089     public final String replace(RegExpLike regexp, String newSubStr) {
090         if (regexp instanceof SimRegExpLike) {
091             Matcher m = ((SimRegExpLike)regexp).pattern().matcher(s);
092             return regexp.global() ?
093                     m.replaceAll(newSubStr) : m.replaceFirst(newSubStr);
094         } else {
095             return regexp.global() ?
096                     s.replaceAll(regexp.source(), newSubStr) :
097                         s.replaceFirst(regexp.source(), newSubStr);
098         }
099     }
100     //@Override
101     public final String replace(RegExpLike regexp, StringLike newSubStr) {
102         return replace(regexp, newSubStr == null ? null : newSubStr.valueOf());
103     }
104     //@Override
105     public final String replace(RegExpLike regexp, JsFunction<String> lambda) {
106         return replace(regexp, lambda.invoke());
107     }
108     //@Override
109     public final Integer search(RegExpLike regexp) {
110         if (regexp instanceof SimRegExpLike) {
111             Matcher m = ((SimRegExpLike)regexp).pattern().matcher(s);
112             boolean res = m.find();
113             return res ? m.start() : -1;
114         } else {
115             return search(new SimRegExpLike(regexp.source()));
116         }
117     }
118     //@Override
119     public final String slice(Object begin) {
120         int from = SimUtil.getNumber(begin).intValue();
121         from = from < 0 ? length() + from : from;
122         return s.substring(from);
123     }
124     //@Override
125     public final String slice(Object begin, Object end) {
126         int from = SimUtil.getNumber(begin).intValue();
127         from = from < 0 ? length() + from : from;
128         int to = SimUtil.getNumber(end).intValue();
129         return s.substring(from, to);
130     }
131     //@Override
132     public final ArrayLike<?> split(Object separator) {
133         separator = Js.valueOf(separator);
134         return separator instanceof SimRegExpLike ?
135                 new SimArrayLike<String>(new SimArrayObject<String>(((SimRegExpLike)separator).pattern().split(s))) :
136                 separator instanceof RegExpLike ?
137                 new SimArrayLike<String>(new SimArrayObject<String>(s.split(((RegExpLike)separator).source()))) :                           
138                 new SimArrayLike<String>(new SimArrayObject<String>(s.split(Js.toString(separator))));
139     }
140     //@Override
141     public final ArrayLike<?> split(Object separator, Object limit) {
142         int lim = SimUtil.getNumber(limit).intValue();
143         separator = Js.valueOf(separator);
144         return separator instanceof SimRegExpLike ?
145                 new SimArrayLike<String>(new SimArrayObject<String>(((SimRegExpLike)separator).pattern().split(s, lim))) :
146                 separator instanceof RegExpLike ?
147                 new SimArrayLike<String>(new SimArrayObject<String>(s.split(((RegExpLike)separator).source(), lim))) :                          
148                 new SimArrayLike<String>(new SimArrayObject<String>(s.split(Js.toString(separator), lim)));
149     }
150     //@Override
151     public final String substr(Object start) {
152         int from = SimUtil.getNumber(start).intValue();
153         from = from < 0 ? length() + from : from;
154         return s.substring(from);
155     }
156     //@Override
157     public final String substr(Object start, Object length) {
158         int from = SimUtil.getNumber(start).intValue();
159         from = from < 0 ? length() + from : from;
160         int to = from + SimUtil.getNumber(length).intValue();
161         return s.substring(from, to);
162     }
163     //@Override
164     public final String substring(Object from) {
165         return s.substring(
166                 SimUtil.getNumber(from).intValue()
167         );
168     }
169     //@Override
170     public final String substring(Object from, Object to) {
171         return s.substring(
172                 SimUtil.getNumber(from).intValue(),
173                 SimUtil.getNumber(to  ).intValue()
174         );
175     }
176     //@Override
177     public final String toLocaleLowerCase() {
178         return s.toLowerCase();
179     }
180     //@Override
181     public final String toLocaleUpperCase() {
182         return s.toUpperCase();
183     }
184     //@Override
185     public final String toLowerCase() {
186         return s.toLowerCase(Locale.ENGLISH);
187     }
188     //@Override
189     public final String toUpperCase() {
190         return s.toUpperCase(Locale.ENGLISH);
191     }
192     //@Override
193     public final String toString() {
194         return s;
195     }
196     //@Override
197     public final String typeof() {
198         return "string";
199     }
200     //@Override
201     public final boolean undefined() {
202         return false;
203     }
204     //@Override
205     public final String valueOf() {
206         return s;
207     }
208 }