/*
 * $Header: /home/cvspublic/jakarta-slide/proposals/tamino/src/util/org/apache/slide/util/Strings.java,v 1.3 2004/07/30 06:52:17 ozeigermann Exp $
 * $Revision: 1.3 $
 * $Date: 2004/07/30 06:52:17 $
 *
 * ====================================================================
 *
 * Copyright 1999-2004 The Apache Software Foundation.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package org.apache.slide.util;

import java.util.Collection;
import java.util.StringTokenizer;

/**
 ** Class to collect useful algorithms used within other classes.
 **
 ** @author michael.hartmeier@softwareag.com
 ** @version $Revision: 1.3 $
 */
public class Strings {
    /**
     ** Returns true, if given string m ends with given suffix ignoring case.
     **
     ** @pre        m != null and m.length() gt 0
     ** @pre        suffix != null and suffix.length() gt 0
     ** @post       true
     **
     ** @param      m the string
     ** @param      suffix the suffix to test
     ** @return     true, if given string m ends with given suffix ignoring case
     **/
    public static boolean endsWithIgnoreCase( String m, String suffix ) {
        int mL = m.length();
        int sL = suffix.length();
        
        if( sL > mL )
            return false;
        
        return suffix.equalsIgnoreCase( m.substring(mL-sL) );
    }
    
    /**
     ** Return file name without extension.
     **
     ** @pre        f != null and f.length() gt 0
     ** @post       true
     **
     ** @param      f the file name
     ** @return     the filename without extension
     **/
    public static String stripExtension( String f ) {
        int dotP = f.lastIndexOf( '.' );
        
        if( dotP <= 0 )
            return f;
        
        return f.substring( 0, dotP );
    }
    
    /**
     ** Return file extension.
     **
     ** @pre        f != null and f.length() gt 0
     ** @post       true
     **
     ** @param      f the file name
     ** @return     the extension
     **/
    public static String getFileExtension( String f ) {
        int dotP = f.lastIndexOf( '.' );
        
        if( dotP <= 0 || dotP == f.length()-1 )
            return "";
        
        return f.substring( dotP+1 );
    }
    
    /**
     ** Return the URI tokens. TODO: use split
     **
     ** @pre        u != null and u.length() gt 0
     ** @post       true
     **
     ** @param      u the uri
     ** @return     the uri tokens
     **/
    public static String[] tokenizeUri( String u ) {
        StringTokenizer tr = new StringTokenizer( u, XUri.SEP );
        String[] result = new String[tr.countTokens()];
        for( int i = 0; i < result.length; i++ )
            if( tr.hasMoreTokens() )
                result[i] = tr.nextToken();
        return result;
    }
    
    
    public static String lfill(char ch, int count, String str) {
        for (count -= str.length(); count > 0; count--) {
            str = ch + str;
        }
        return str;
    }
    
    public static String rfill(char ch, int count, String str) {
        for (count -= str.length(); count > 0; count--) {
            str = str + ch;
        }
        return str;
    }

    public static String times(char ch, int count) {
        StringBuffer buffer;
        
        buffer = new StringBuffer();
        while (count-- > 0) {
            buffer.append(ch);
        }
        return buffer.toString();
    }

    /**
     ** Concatenate the specified strings, separated by the specified space.
     **
     ** @param strings to be concatenated
     ** @param separator between two strings
     **
     ** @return concatenated string
     **/
    public static String join(String[] strings, String separator) {
        int i;
        StringBuffer buffer;
        
        buffer = new StringBuffer();
        for (i = 0; i < strings.length; i++) {
            if (i > 0) {
                buffer.append(separator);
            }
            buffer.append(strings[i]);
        }
        return buffer.toString();
    }
    
    
    
    public static void trim(String[] args) {
        int i;
        
        for (i = 0; i < args.length; i++) {
            args[i] = args[i].trim();
        }
    }
    
    public static String[] cdr(String[] args) {
        String[] result;
        
        if (args.length == 0) {
            throw new XAssertionFailed();
        }
        result = new String[args.length - 1];
        System.arraycopy(args, 1, result, 0, result.length);
        return result;
    }
    
    public static String[] split(String str, String delimiters) {
        int i;
        StringTokenizer tokenizer;
        int max;
        String[] result;
        
        tokenizer = new StringTokenizer(str, delimiters);
        max = tokenizer.countTokens();
        result = new String[max];
        for( i = 0; i < max; i++ ) {
            result[i] = tokenizer.nextToken();
        }
        return result;
    }
    
    public static String replace(String str, String in, String out) {
        StringBuffer buffer;
        int inLen;
        int idx;
        int prev;
        
        inLen = in.length();
        if (inLen == 0) {
            throw new IllegalArgumentException();
        }
        buffer = new StringBuffer();
        idx = str.indexOf(in);
        prev = 0;
        while (idx != -1) {
            buffer.append(str.substring(prev, idx));
            buffer.append(out);
            prev = idx + inLen;
            idx = str.indexOf(in, prev);
        }
        buffer.append(str.substring(prev));
        return buffer.toString();
    }
    
    /**
     ** Turns a list of Strings into an array.
     **
     ** @param coll   collection of Strings
     **
     ** @return never null
     **/
    public static String[] toArray(Collection coll) {
        String[] ar;
        
        ar = new String[coll.size()];
        coll.toArray(ar);
        return ar;
    }
    
    public static String[] cons(String head, String[] tail) {
        String[] result;
        
        result = new String[1 + tail.length];
        result[0] = head;
        System.arraycopy(tail, 0, result, 1, tail.length);
        return result;
    }
    
    public static String[] append(String[] left, String[] right) {
        String[] result;
        
        result = new String[left.length + right.length];
        System.arraycopy(left, 0, result, 0, left.length);
        System.arraycopy(right, 0, result, left.length, right.length);
        return result;
    }
    
    public static String getCommon(String left, String right) {
        int i;
        int max;
        
        max = Math.min(left.length(), right.length());
        for (i = 0; i < max; i++) {
            if (left.charAt(i) != right.charAt(i)) {
                break;
            }
        }
        return left.substring(0, i);
    }
    
    public static int count(String str, String part) {
        int count;
        int idx;
        int len;
        
        len = part.length();
        idx = 0;
        for (count = 0; true; count++) {
            idx = str.indexOf(part, idx);
            if (idx == -1) {
                return count;
            }
            idx += len;
        }
    }
    
    public static final String block(String prefix, String body, int width, String suffix) {
        return block(prefix, prefix, body, width, suffix, suffix);
    }

    public static final String block(String first, String prefix, String body, int width, String suffix, String last) {
        String currentPrefix;
        StringBuffer buffer;
        int space;
        int word;
        int line;
        boolean empty;  // false if at least one word was added to the line
        
        buffer = new StringBuffer();
        word = skip(body, 0, true);
        currentPrefix = first;
        while (true) {
            buffer.append(currentPrefix);
            line = 0;
            empty = true;
            while (true) {
                space = skip(body, word, false);
                if (space == word) {
                    buffer.append(last);
                    return buffer.toString();
                }
                line += space - word;
                if (empty) {
                    empty = false;
                } else {
                    line++;
                    if (line > width) {
                        break;
                    }
                    buffer.append(' ');
                }
                buffer.append(body.substring(word, space));
                word = skip(body, space, true);
            }
            buffer.append(suffix);
            currentPrefix = prefix;
        }
    }
    
    public static final int skip(String str, int start, boolean ws) {
        int i;
        int max;
        
        max = str.length();
        for (i = start; i < max; i++) {
            if (Character.isWhitespace(str.charAt(i)) != ws) {
                break;
            }
        }
        return i;
    }
}

