001    /*
002     * Copyright (C) 2012 eXo Platform SAS.
003     *
004     * This is free software; you can redistribute it and/or modify it
005     * under the terms of the GNU Lesser General Public License as
006     * published by the Free Software Foundation; either version 2.1 of
007     * the License, or (at your option) any later version.
008     *
009     * This software is distributed in the hope that it will be useful,
010     * but WITHOUT ANY WARRANTY; without even the implied warranty of
011     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
012     * Lesser General Public License for more details.
013     *
014     * You should have received a copy of the GNU Lesser General Public
015     * License along with this software; if not, write to the Free
016     * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
017     * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
018     */
019    
020    package org.crsh.text.ui;
021    
022    import org.crsh.text.LineReader;
023    import org.crsh.text.RenderAppendable;
024    import org.crsh.text.Renderer;
025    import org.crsh.text.Style;
026    
027    class LabelRenderer extends Renderer {
028    
029      /** . */
030      private final LabelElement label;
031    
032      LabelRenderer(LabelElement label) {
033        this.label = label;
034      }
035    
036      @Override
037      public int getMinWidth() {
038        return label.minWidth;
039      }
040    
041      @Override
042      public int getActualWidth() {
043        return label.width;
044      }
045    
046      @Override
047      public LineReader renderer(final int width) {
048    
049        if (width == 0) {
050          return new LineReader() {
051            boolean done = false;
052            public boolean hasLine() {
053              return !done;
054            }
055            public void renderLine(RenderAppendable to) throws IllegalStateException {
056              if (done) {
057                throw new IllegalStateException();
058              } else {
059                done = true;
060              }
061            }
062          };
063        } else {
064          return new LineReader() {
065    
066            /** . */
067            boolean done = false;
068    
069            /** . */
070            int index = 0;
071    
072            public boolean hasLine() {
073              return !done;
074            }
075    
076            public void renderLine(RenderAppendable to) {
077              if (done) {
078                throw new IllegalStateException();
079              } else {
080                Style.Composite style = label.getStyle();
081                if (style != null) {
082                  to.enterStyle(style);
083                }
084                int pos = label.value.indexOf('\n', index);
085                int next;
086                if (pos == -1) {
087                  pos = Math.min(index + width, label.value.length());
088                  next = pos;
089                } else {
090                  if (pos <= index + width) {
091                    next = pos + 1;
092                  } else {
093                    next = pos = index + width;
094                  }
095                }
096                to.append(label.value, index, pos);
097                int missing = pos - index;
098                while (missing < width) {
099                  to.append(' ');
100                  missing++;
101                }
102                index = next;
103                done = index >= label.value.length();
104                if (style != null) {
105                  to.leaveStyle();
106                }
107              }
108            }
109          };
110        }
111      }
112    }