J2ME实现展示内容自动根据屏幕宽度换行的功能

  由于lwuit的label中没有根据内容自动换行的设置,而项目中的TextArea的样式和Label样式的背景不同,不能使用TextArea展示内容,所以就重写了一个TextLabel的类,继承自TextArea类。实现了这个功能,其中大部分源码参考了http://j2me.cc43.com/100916/124.html中的代码。

 

import java.util.Vector;

import com.sun.lwuit.Display;
import com.sun.lwuit.Font;
import com.sun.lwuit.TextArea;
import com.sun.lwuit.geom.Dimension;
import com.sun.lwuit.plaf.Style;
/**
 *
 * @ description:实现展示内容自动根据屏幕宽度换行的功能
 * @ company lingxun
 * @ author Lancelothe
 * @ date 2010-9-30
 */
public class TextLabel extends TextArea
{
    private int autoWidth = 0;// 设置换行的宽度
    private int maxRow = 0;// 最大行数
    private boolean maxrowCode = false;// 是否设置了最大行数
    private int fontCountW = 0;// 通过汉字个数计算的宽度
    private final int fontFx = 14;// 字体的size,现用14个像索

    private Vector rowStrings;
    private int widthForRowCalculations = -1;

    /** * 无参构造函数,默认宽度为屏幕宽度 */
    public TextLabel()
    {
        this("", Display.getInstance().getDisplayWidth());
    }

    /**
     * * 默认宽度为屏幕宽度 *
     *
     * @param text
     */
    public TextLabel(String text)
    {
        this(text, Display.getInstance().getDisplayWidth());
    }

    public TextLabel(String text, int width)
    {
        super(text);
        System.out.println("屏幕宽度:" + Display.getInstance().getDisplayWidth());
        System.out.println("实际宽度:" + width);
        this.setEditable(false);
        // 不能编辑
        this.setFocusable(false);
        // 不能获得焦点
         this.getStyle().setBorder(null);
        // 没有边框
        this.autoWidth = width;
        this.setScrollSize(new Dimension(0, 0));
        // 设置无滚动条
        this.getStyle().setPadding(0, 0, 4, 15);
        this.setPreferredW(this.autoWidth);
    }

    public TextLabel(String text, int width, int maxRow)
    {
        super(text);
        this.setEditable(false);
        // 不能编辑
        this.setFocusable(false);
        // 不能获得焦点
        this.maxRow = maxRow;
        if (this.maxRow > 0)
            this.maxrowCode = true;
        this.getStyle().setBorder(null);
        // 没有边框
        this.setScrollSize(new Dimension(0, 0));
        // 设置无滚动条
        this.getStyle().setPadding(0, 0, 4, 15);
        this.autoWidth = width;
        this.setPreferredW(this.autoWidth);
    }

    /**
     * * 获取宽度 *
     *
     * @return
     */
    public int getAutoWidth()
    {
        return autoWidth;
    }

    private Vector getRowStrings()
    {
        if (rowStrings == null
                || widthForRowCalculations != getWidth()
                        - getStyle().getPadding(false, RIGHT)
                        - getStyle().getPadding(false, LEFT))
        {
            this.initRowString();
            setShouldCalcPreferredSize(true);
        }
        return rowStrings;
    }

    /**
     * @ description:覆盖父类中的getLines方法 @ author Lancelothe @ parameter @ create_date
     * 2010-9-30 @ update_date 2010-9-30
     * @see com.sun.lwuit.TextArea#getLines()
     */
    public int getLines()
    {
        int retVal;
        Vector v = this.getRowStrings();
        retVal = v.size();
        return retVal;
    }

    /**
     * * 覆盖TextArea的initRowString()方法,需修改源码<br/> *
     */
    protected void initRowString()
    {
        rowStrings = new Vector();
        widthForRowCalculations = getWidth();
        if (isSingleLineTextArea())
        {
            rowStrings.addElement(getText());
            return;
        }
        if (getText() == null || getText().equals(""))
        {
            return;
        }
        char[] text = preprocess(getText());
        // 转化成字符数组
        Style style = this.getStyle();
        int textLabelWidth = this.autoWidth;
        // 本身的宽度
        if (textLabelWidth <= 0)
        {
            textLabelWidth = Display.getInstance().getDisplayWidth();
            // 默认屏幕宽度
        }
        rowStrings = this.autoText(style.getFont(), getText(), textLabelWidth);
    }

    /**
     * * 获得指定宽度每行的文本数组 *
     *
     * @param font *
     * @param text *
     * @param maxWidth
     */
    private Vector autoText(Font font, String text, int maxWidth)
    {
        Vector v = new Vector();
        int fcwCode = 0;
        // 用于用汉字宽度计算时
        int piontW = font.charWidth('.') * 3;
        // 计算一个点的宽度
        boolean lastCode = true;
        // 全部显示出来时为true
        int maxLength = maxWidth ;
        int textLength = font.stringWidth(text);
        if (textLength <= maxLength)
        {// 如果一行容得下时
            v.addElement(text);
            return v;
        }
        else
        {
            // this.maxRow=textLength/maxLength+2;
            System.out.println("maxRow=" + maxRow);
            char[] chars = text.toCharArray();
            // 转化成字符数组
            int charWidth = 0;
            // 字符宽度
            int rowLength = 0;
            // 每行的长度
            int rowIndex = 0;
            // 每行开始的index
            boolean changeRow = false;
            for (int i = 0; i < chars.length; i++)
            {
                if (chars[i] == '/n')
                {
                    if (rowLength > 0)
                    {
                        v.addElement(text.substring(rowIndex, i));
                        rowLength = 0;
                    }
                    else
                        v.addElement("");
                    i++;
                    rowIndex = i;
                    continue;
                }
                charWidth = font.charWidth(chars[i]);
                if (!changeRow)
                    fcwCode += charWidth;
                else
                    changeRow = false;
                rowLength += charWidth;
                if (this.fontCountW > 0 && fcwCode > this.fontCountW)
                {
                    int j = font.charWidth('.');
                    int w = rowLength - charWidth;
                    if (w > maxLength || (w + j) > maxLength
                            || (w + 2 * j) > maxLength
                            || (w + 3 * j) > maxLength)
                    {
                        v.addElement(text.substring(rowIndex, i));
                        // v.addElement(new String(chars,rowIndex,i-rowIndex));
                        v.addElement("...");
                    }
                    else
                    {
                        v.addElement(text.substring(rowIndex, i) + "...");
                        // v.addElement(new
                        // String(chars,rowIndex,i-rowIndex)+"...");
                    }
                    break;
                }
                if (rowLength > maxLength)
                {
                    changeRow = true;
                    if (chars[i] >= 'A' && chars[i] <= 'z')
                    {
                        // 如果下行第一个为字母时
                        if (i > 0 && chars[i - 1] >= 'A' && chars[i - 1] <= 'z')
                        {
                            int enIndex = 0;
                            // 单词开始的index
                            for (int j = i; j > 0 && chars[j - 1] >= 'A'
                                    && chars[j - 1] <= 'z'; j--)
                                enIndex = j - 1;
                            if (enIndex > rowIndex)
                            {
                                v.addElement(text.substring(rowIndex, enIndex));
                                // v.addElement(new
                                // String(chars,rowIndex,enIndex-rowIndex));
                                // 把不是字母的放在一行中
                                rowIndex = enIndex;
                                // 下一行的开始位置
                                i = enIndex--;
                                rowLength = 0;
                            }
                            else
                            {
                                v.addElement(text.substring(rowIndex, i));
                                // v.addElement(new
                                // String(chars,rowIndex,i-rowIndex));
                                // 每行的文本
                                rowIndex = i;
                                // 下一行的开始位置
                                i--;
                                // 起点从下一行第一个开始
                                rowLength = 0;
                            }
                        }
                    }
                    else
                    {
                        v.addElement(text.substring(rowIndex, i));
                        // v.addElement(new String(chars,rowIndex,i-rowIndex));
                        // 每行的文本
                        rowIndex = i;
                        // 下一行的开始位置
                        i--;
                        // 起点从下一行第一个开始
                        rowLength = 0;
                    }
                }
                if (i < chars.length - 1)
                    lastCode = false;
                if (this.maxrowCode && v.size() == this.maxRow)
                    break;
            }
            if (this.fontCountW <= 0)
            {
                if (rowIndex <= chars.length - 1)
                {
                    // 最后一行不够文本时
                    boolean h = false;
                    if (maxRow > 0 && v.size() == this.maxRow)
                    {
                        String vLast = (String) v.lastElement();
                        if (!lastCode)
                        {
                            char[] chs = vLast.toCharArray();
                            int chsLength = 0;
                            if (null != chs)
                                chsLength = chs.length;
                            if (chsLength > 0)
                            {
                                if (font.charWidth(chs[chsLength - 1]) > piontW)
                                    // vLast=(new
                                    // String(chs,0,chsLength-1))+"...";
                                    // 如果最后一个字符的宽度大于三个点的宽度时
                                    vLast = vLast.substring(0, chsLength - 1);
                                else
                                {
                                    if (chsLength > 1
                                            && font
                                                    .charWidth(chs[chsLength - 1])
                                                    + font
                                                            .charWidth(chs[chsLength - 2]) > piontW)
                                        // vLast=(new
                                        // String(chs,0,chsLength-2))+"...";
                                        // 如果最后两个字符的宽度都大于三个点的宽度时
                                        vLast = vLast.substring(0,
                                                chsLength - 2)
                                                + "...";
                                    else
                                        // vLast=(new
                                        // String(chs,0,chsLength-3))+"...";
                                        // 其它的按三个字符来算
                                        vLast = vLast.substring(0,
                                                chsLength - 3)
                                                + "...";
                                }
                                v.removeElementAt(v.size() - 1);
                                v.addElement(vLast);
                            }
                        }
                    }
                    else
                    {
                        // v.addElement(new
                        // String(chars,rowIndex,chars.length-rowIndex));
                        String vLast = text.substring(rowIndex, chars.length);
                        char[] chs = vLast.toCharArray();
                        int r = 0;
                        for (int i = 0; i < chs.length; i++)
                        {
                            if (chs[i] == '/n')
                            {
                                h = true;
                                v.addElement(vLast.substring(r, i));
                                i++;
                                r = i;
                            }
                        }
                        if (h)
                        {
                            v.addElement(vLast.substring(r, chs.length));
                        }
                        else
                            v.addElement(vLast);
                    }
                }
            }
        }
        System.out.println("list size=" + v.size());
        System.out.println(v.elementAt(0));
        System.out.println(v.elementAt(5));
        return v;
    }

    /**
     *  @ description:覆盖父类中的getTextAt方法 @ author Lancelothe @ parameter @ create_date 2010-9-30 @ update_date
     * 2010-9-30
     * @see com.sun.lwuit.TextArea#getTextAt(int)
     */
    public String getTextAt(int line)
    {
        Vector rowsV = this.getRowStrings();
        return (String) rowsV.elementAt(line);
    }

    public int getMaxRow()
    {
        return maxRow;
    }

    public void setMaxRow(int maxRow)
    {
        this.maxRow = maxRow;
        this.initRowString();
    }

    public int getFontCountW()
    {
        return fontCountW;
    }

    public void setFontCountW(int fontCount)
    {
        this.fontCountW = fontCount * this.fontFx;
        this.initRowString();
        this.setPreferredSize(new Dimension(this.autoWidth, calcPreferredSize()
                .getHeight()));
    }

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值