Обосновать текст в Android-приложении, используя WebView, но представляя интерфейс TextView?

Я ищу простой способ забыть, что я использую WebView для WebView текста в своем TextView . Кто-то сделал это для этого? Мне хорошо известно, что я могу сделать что-то вроде этого:

  WebView view = new WebView(this); view.loadData("my html with text justification","text/html","utf-8"); 

Но он становится уродливым, когда вы хотите установить размер, цвет или другие общие свойства TextView . Должен быть более удобный способ сделать это.

    Я это признаю. Мне нравится, что TextViews выглядят как TextViews в коде, и даже если я использую WebView в качестве средства достижения выравнивания text-align: justified formatting, я не хочу смотреть на него таким образом.

    Я создал собственное представление (уродливое, возможно, плохое), которое реализует методы, которые я обычно использую из TextView и изменяет содержимое WebView, чтобы отразить эти изменения. Wether это полезно для кого-то другого или потенциальной опасности, которую я действительно не знаю, для меня это работает, я использовал его в нескольких проектах и ​​не сталкивался с какими-либо проблемами. Единственное небольшое неудобство заключается в том, что я предполагаю, что это больший объем памяти, но нечего беспокоиться о том, если это всего лишь один или два (исправьте меня, если я ошибаюсь).

    В результате получается следующее:

    введите описание изображения здесь

    И код для его программного программирования так же прост:

      JustifiedTextView J = new JustifiedTextView(); J.setText("insert your text here"); 

    Конечно, было бы глупо оставлять это так, поэтому я также добавил методы для изменения размера шрифта и цвета шрифта, которые в основном предназначены для использования TextViews. Значение Я могу сделать что-то вроде этого:

      JustifiedTextView J = new JustifiedTextView(); J.setText("insert your text here"); J.setTextColor(Color.RED); J.setTextSize(30); 

    И получите следующий результат (изображения обрезаны):

    введите описание изображения здесь

    Но это не значит, что мы посмотрим, как это выглядит, делиться тем, как вы это сделали!

    Знаю, знаю. Вот полный код. Он также решает проблемы при настройке прозрачного фона и загрузке строк UTF-8 в представление. Подробнее см. Комментарии в reloadData ().

     public class JustifiedTextView extends WebView{ private String core = "%s"; private String textColor = "0,0,0,255"; private String text = ""; private int textSize = 12; private int backgroundColor=Color.TRANSPARENT; public JustifiedTextView(Context context, AttributeSet attrs) { super(context, attrs); this.setWebChromeClient(new WebChromeClient(){}); } public void setText(String s){ this.text = s; reloadData(); } @SuppressLint("NewApi") private void reloadData(){ // loadData(...) has a bug showing utf-8 correctly. That's why we need to set it first. this.getSettings().setDefaultTextEncodingName("utf-8"); this.loadData(String.format(core,textColor,textSize,text), "text/html","utf-8"); // set WebView's background color *after* data was loaded. super.setBackgroundColor(backgroundColor); // Hardware rendering breaks background color to work as expected. // Need to use software renderer in that case. if(android.os.Build.VERSION.SDK_INT >= 11) this.setLayerType(WebView.LAYER_TYPE_SOFTWARE, null); } public void setTextColor(int hex){ String h = Integer.toHexString(hex); int a = Integer.parseInt(h.substring(0, 2),16); int r = Integer.parseInt(h.substring(2, 4),16); int g = Integer.parseInt(h.substring(4, 6),16); int b = Integer.parseInt(h.substring(6, 8),16); textColor = String.format("%d,%d,%d,%d", r, g, b, a); reloadData(); } public void setBackgroundColor(int hex){ backgroundColor = hex; reloadData(); } public void setTextSize(int textSize){ this.textSize = textSize; reloadData(); } } 

    Без решения веб-просмотра: https://github.com/merterhk/JustifiedTextView

     import java.util.ArrayList; import android.content.Context; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.Typeface; import android.text.TextPaint; import android.view.View; public class JustifiedTextView extends View { String text; ArrayList linesCollection = new ArrayList(); TextPaint textPaint; Typeface font; int textColor; float textSize = 42f, lineHeight = 57f, wordSpacing = 15f, lineSpacing = 15f; float onBirim, w, h; float leftPadding, rightPadding; public JustifiedTextView(Context context, String text) { super(context); this.text = text; init(); } private void init() { textPaint = new TextPaint(Paint.ANTI_ALIAS_FLAG); textColor = Color.BLACK; } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); if (font != null) { font = Typeface.createFromAsset(getContext().getAssets(), "font/Trykker-Regular.ttf"); textPaint.setTypeface(font); } textPaint.setColor(textColor); int minw = getPaddingLeft() + getPaddingRight() + getSuggestedMinimumWidth(); w = resolveSizeAndState(minw, widthMeasureSpec, 1); h = MeasureSpec.getSize(widthMeasureSpec); onBirim = 0.009259259f * w; lineHeight = textSize + lineSpacing; leftPadding = 3 * onBirim + getPaddingLeft(); rightPadding = 3 * onBirim + getPaddingRight(); textPaint.setTextSize(textSize); wordSpacing = 15f; Line lineBuffer = new Line(); this.linesCollection.clear(); String[] lines = text.split("\n"); for (String line : lines) { String[] words = line.split(" "); lineBuffer = new Line(); float lineWidth = leftPadding + rightPadding; float totalWordWidth = 0; for (String word : words) { float ww = textPaint.measureText(word) + wordSpacing; if (lineWidth + ww + (lineBuffer.getWords().size() * wordSpacing) > w) {// is lineBuffer.addWord(word); totalWordWidth += textPaint.measureText(word); lineBuffer.setSpacing((w - totalWordWidth - leftPadding - rightPadding) / (lineBuffer.getWords().size() - 1)); this.linesCollection.add(lineBuffer); lineBuffer = new Line(); totalWordWidth = 0; lineWidth = leftPadding + rightPadding; } else { lineBuffer.setSpacing(wordSpacing); lineBuffer.addWord(word); totalWordWidth += textPaint.measureText(word); lineWidth += ww; } } this.linesCollection.add(lineBuffer); } setMeasuredDimension((int) w, (int) ((this.linesCollection.size() + 1) * lineHeight + (10 * onBirim))); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); canvas.drawLine(0f, 10f, getMeasuredWidth(), 10f, textPaint); float x, y = lineHeight + onBirim; for (Line line : linesCollection) { x = leftPadding; for (String s : line.getWords()) { canvas.drawText(s, x, y, textPaint); x += textPaint.measureText(s) + line.spacing; } y += lineHeight; } } public String getText() { return text; } public void setText(String text) { this.text = text; } public Typeface getFont() { return font; } public void setFont(Typeface font) { this.font = font; } public float getLineHeight() { return lineHeight; } public void setLineHeight(float lineHeight) { this.lineHeight = lineHeight; } public float getLeftPadding() { return leftPadding; } public void setLeftPadding(float leftPadding) { this.leftPadding = leftPadding; } public float getRightPadding() { return rightPadding; } public void setRightPadding(float rightPadding) { this.rightPadding = rightPadding; } public void setWordSpacing(float wordSpacing) { this.wordSpacing = wordSpacing; } public float getWordSpacing() { return wordSpacing; } public float getLineSpacing() { return lineSpacing; } public void setLineSpacing(float lineSpacing) { this.lineSpacing = lineSpacing; } class Line { ArrayList words = new ArrayList(); float spacing = 15f; public Line() { } public Line(ArrayList words, float spacing) { this.words = words; this.spacing = spacing; } public void setSpacing(float spacing) { this.spacing = spacing; } public float getSpacing() { return spacing; } public void addWord(String s) { words.add(s); } public ArrayList getWords() { return words; } } } 

    Всего за три шага вы можете обосновать свой веб-текст.

    1)

     // Justify tag String justifyTag = "%s"; 

    2)

     // Concatenate your string with the tag to Justify it String dataString = String.format(Locale.US, justifyTag, "my html with text justification"); 

    3)

     // Load the data in the web view webView.loadDataWithBaseURL("", dataString, "text/html", "UTF-8", ""); 

    Это тот же class JustifiedTextView, данный Juan (и отредактированный мной), но расширенный для работы с пользовательскими атрибутами xml, которые вы можете использовать в ваших XML-файлах макета. Даже редактор макетов Eclipse покажет ваши пользовательские атрибуты в таблице атрибутов, что будет круто. Я вложил это в дополнительный ответ, если вы хотите сохранить чистоту и не нуждаетесь в атрибутах xml.

     public class JustifiedTextView extends WebView{ private String core = "%s"; private String text; private int textColor; private int backgroundColor; private int textSize; public JustifiedTextView(Context context, AttributeSet attrs) { super(context, attrs); init(attrs); } public JustifiedTextView(Context context, AttributeSet attrs, int i) { super(context, attrs, i); init(attrs); } @SuppressLint("NewApi") public JustifiedTextView(Context context, AttributeSet attrs, int i, boolean b) { super(context, attrs, i, b); init(attrs); } private void init(AttributeSet attrs) { TypedArray a=getContext().obtainStyledAttributes( attrs, R.styleable.JustifiedTextView); text = a.getString(R.styleable.JustifiedTextView_text); if(text==null) text=""; textColor = a.getColor(R.styleable.JustifiedTextView_textColor, Color.BLACK); backgroundColor = a.getColor(R.styleable.JustifiedTextView_backgroundColor, Color.TRANSPARENT); textSize = a.getInt(R.styleable.JustifiedTextView_textSize, 12); a.recycle(); this.setWebChromeClient(new WebChromeClient(){}); reloadData(); } public void setText(String s){ if(s==null) this.text=""; else this.text = s; reloadData(); } @SuppressLint("NewApi") private void reloadData(){ if(text!=null) { String data = String.format(core,toRgba(textColor),textSize,text); Log.d("test", data); this.loadDataWithBaseURL(null, data, "text/html","utf-8", null); } // set WebView's background color *after* data was loaded. super.setBackgroundColor(backgroundColor); // Hardware rendering breaks background color to work as expected. // Need to use software renderer in that case. if(android.os.Build.VERSION.SDK_INT >= 11) this.setLayerType(WebView.LAYER_TYPE_SOFTWARE, null); } public void setTextColor(int hex){ textColor = hex; reloadData(); } public void setBackgroundColor(int hex){ backgroundColor = hex; reloadData(); } public void setTextSize(int textSize){ this.textSize = textSize; reloadData(); } private String toRgba(int hex) { String h = Integer.toHexString(hex); int a = Integer.parseInt(h.substring(0, 2),16); int r = Integer.parseInt(h.substring(2, 4),16); int g = Integer.parseInt(h.substring(4, 6),16); int b = Integer.parseInt(h.substring(6, 8),16); return String.format("%d,%d,%d,%d", r, g, b, a); } } 

    Или добавьте это как justified_text_view_attr.xml в свою папку res / values ​​/ или слейте его в существующий attrs.xml:

              

    Не стесняйтесь редактировать, если вы найдете какие-либо ошибки.

    Я считаю эту простую форму. И я отлично работал

     package domo.suichbt.util; import android.content.Context; import android.text.Html; import android.util.AttributeSet; import android.widget.TextView; public class JustifiedTextView extends TextView { private final String CORE_TEMPLATE = "%s"; public JustifiedTextView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) { super(context, attrs, defStyleAttr, defStyleRes); setText(Html.fromHtml(String.format(CORE_TEMPLATE,getText()))); } public JustifiedTextView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); setText(Html.fromHtml(String.format(CORE_TEMPLATE,getText()))); } public JustifiedTextView(Context context) { super(context); setText(Html.fromHtml(String.format(CORE_TEMPLATE,getText()))); } public JustifiedTextView(Context context, AttributeSet attrs) { super(context, attrs); setText(Html.fromHtml(String.format(CORE_TEMPLATE,getText()))); } } 

    Вставить пример xml

        

    Взгляните на эту ссылку. Он использует WebView для обработки, чтобы полностью обосновать текст CheckBox в Android. Он также может использоваться точно так же в TextView, поскольку каждый CheckBox на самом деле является TextView и Button. http://www.collegemobile.com/2014/09/justify-text-android-checkbox/

    Давайте будем гением компьютера.