我想在我的应用中添加一个控件。控件的特性是它包含多行文本(例如5行)并且不包含滚动条。我将通过下面的例子解释。
|-----------------|
| text1 |
| text2 |
| text3 |
| text4 |
| |
|-----------------|
如果在文本视图中添加字符串,它将变为
|-----------------|
| text1 |
| text2 |
| text3 |
| text4 |
| text5 |
|-----------------|
如果你添加另一行文字,它将成为
|-----------------|
| text2 |
| text3 |
| text4 |
| text5 |
| text6 |
|-----------------|
有可能吗?我用Google搜索,但找不到解决方案。
答案 0 :(得分:1)
如果您希望它是一个可重复使用的控件,您需要为此创建一个自定义视图,您可以在其中添加文本,并在内部在内部TextView之间移动文本。
或者,当您想要添加新行时,您可以使用多个TextView并将文本从一个文本复制到另一个文件。
该功能未包含在标准中。
答案 1 :(得分:1)
我不知道为什么你可能想要没有滚动条的多行,但如果这就是你需要的,我想这可能是一个可能的解决方案。
显然你需要在你的布局上做一些逻辑,因为我想不出一个能给你这个服务但没有调整它的视图。
所以,我正在考虑使用5个TextViews的RelativeLayout(textViews的数量取决于你想要显示多少行)。
因此每个textView都将包含一行,这样当用户添加新行时,您必须按照这些行执行某些操作:
if( linesInView == 5 )
shiftText();
addText();
这样shiftText()
将负责完成循环并将一个textView的文本设置为另一个(移动它们),以便为新文本腾出空间。
然后addText()
只会将用户创建的新文本添加到由shiftText()
生成的释放位置。
总而言之,您可以遵循这些指导原则。请记住,我刚刚编写了这个代码,我目前无法检查其正确性。此外,这是第一次尝试,还有改进的余地:
private static int MAX_NUM_LINES = 5;
private int linesShown = 0;
private ArrayList<TextView> views = new ArrayList<>();
private EditText userInput;
public void onCreate(...){
....
views.add((TextView)findViewById(R.id.firstline);
views.add((TextView)findViewById(R.id.secondline);
views.add((TextView)findViewById(R.id.thirdline);
views.add((TextView)findViewById(R.id.fourthline);
views.add((TextView)findViewById(R.id.fifthline);
this.userInput = (EditText) findViewById(R.id.input);
//I suggest these in order to avoid calling "findViewById()" everytime the user
// adds a new sentences, which I gather will happen often
}
public void someEventCalledWhenUserAddsNewLine(View view){
if(this.linesShown>=MAX_NUM_LINES)
shiftText();
addNewLine();
}
private void shiftText(){
//Shift your text by looping through your this.views
for(pos=0; pos<this.views.size()-1; ++pos){
String nextLine = this.views.get(pos+1).getText();
this.views.get(pos).setText(nextLine);
}
//You need to set the condition to this.views.size()-1 because
//when you reach position 4 (your last TextView) you have to sop
// since there is not text to shift to that one
this.views.get(this.views.size()-1).setText(null);
//Make sure you set the text of the last TextView to null so that
// addLine() will be able to find the first available TextView
}
private void addNewLine(){
//Add text from this.userInput to the first available TextView in this.views
int pos;
for(pos=0; pos<this.views.size(); ++pos){
if(this.views.get(pos).getText()==null){
//We have found the first available TextView
break;
}
}
this.views.get(pos).setText(this.userInput.getText());
//Pos holds the position of the first available TextView, now we have
// added the new line
this.linesShown++;
}
最重要的改进是跟踪第一个可用的TextView的索引,这样你就不必在addLine()
寻找它了。
答案 2 :(得分:1)
我想这样的东西应该可行,但我怀疑它是否是最佳的:
public class LinesTextView {
private TextView tv;
private int linesCount = 0;
private int maxLines = 5;
public LinesTextView(TextView tv){
this.tv = tv;
}
public void addLine(String line){
if(linesCount == maxLines){
String lines = tv.getText().toString();
int pos = lines.indexOf("\n");
StringBuffer buff = new StringBuffer(lines.substring(pos+1));
buff.append('\n');
buff.append(line);
tv.setText(buff.toString());
} else if(linesCount == 0){
tv.setText(line);
linesCount = 1;
} else {
StringBuffer buff = new StringBuffer(tv.getText().toString());
buff.append('\n');
buff.append(line);
tv.setText(buff.toString());
linesCount++;
}
}
}