0

我有以下问题,我的应用程序从在线数据库中检索数据以及文本,还有我正在通过以下课程查看的图像。图像显示正确但尺寸不正确,我想根据显示器的尺寸调整大小,你知道我该怎么做吗?来源是这样的:

import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;

import android.graphics.BitmapFactory;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.text.Html.ImageGetter;

class HttpImageGetter implements ImageGetter {

    @Override
    public Drawable getDrawable(String source) {
            try {
                    URL url = new URL(source);
                    HttpURLConnection conn = (HttpURLConnection)url.openConnection();
                    conn.setDoInput(true);
                    conn.connect();
                    InputStream is = conn.getInputStream();
                    BitmapDrawable dr = new BitmapDrawable(BitmapFactory.decodeStream(is));
                    dr.setBounds(0, 0, dr.getIntrinsicWidth(), dr.getIntrinsicHeight());

                    return dr;
            } catch (IOException e) {
                    e.printStackTrace();
                    return null;
            }
    }
}

我还有第二个问题。文本的打开速度较慢,因为还有一些图像更重,但如果我再次单击文本名称会显示一个全黑的屏幕,有时它会说应用程序没有响应。所有这些都会发生,尤其是当我使用 Edge 连接时。您对我如何修复和加快文本打开有任何想法吗?

PS:图像包含在 TextView

4

1 回答 1

0
private TextView htmlTextView;
private SpannableStringBuilder htmlSpannable;

@Override
public void onCreate(Bundle savedInstanceState) {

    // ...

    // first parse the html
    // replace getHtmlCode() with whatever generates/fetches your html
    Spanned spanned = Html.fromHtml(getHtmlCode());

    // we need a SpannableStringBuilder for later use
    if (spanned instanceof SpannableStringBuilder) {
        // for now Html.fromHtml() returns a SpannableStringBuiler
        // so we can just cast it
        htmlSpannable = (SpannableStringBuilder) spanned;
    } else {
        // but we have a fallback just in case this will change later
        // or a custom subclass of Html is used
        new SpannableStringBuilder(spanned);
    }

    // now we can call setText() on the next view.
    // this won't show any images yet
    htmlTextView.setText(htmlSpannable);

    // next we start a AsyncTask that loads the images
    new ImageLoadTask().execute();

    // ...

}

private class ImageLoadTask extends AsyncTask {

    DisplayMetrics metrics = new DisplayMetrics();

    @Override
    protected void onPreExecute() {

        // we need this to properly scale the images later
        getWindowManager().getDefaultDisplay().getMetrics(metrics);

    }

    @Override
    protected Void doInBackground(Void... params) {

        // iterate over all images found in the html
        for (ImageSpan img : htmlSpannable.getSpans(0,
                    htmlSpannable.length(), ImageSpan.class)) {

            if (!getImageFile(img).isFile()) {

                // here you have to download the file

            }

            // we use publishProgress to run some code on the
            // UI thread to actually show the image
            // -> onProgressUpdate()
            publishProgress(img);

        }

        return null;

    }

    @Override
    protected void onProgressUpdate(ImageSpan... values) {

        // save ImageSpan to a local variable just for convenience
        ImageSpan img = values[0];

        // now we get the File object again. so remeber to always return
        // the same file for the same ImageSpan object
        File cache = getImageFile(img);

        // if the file exists, show it
        if (cache.isFile()) {

            // first we need to get a Drawable object
            Drawable d = new BitmapDrawable(getResources(),
                    cache.getAbsolutePath());

            // next we do some scaling
            int width, height;
            int originalWidthScaled = (int) (d.getIntrinsicWidth() * metrics.density);
            int originalHeightScaled = (int) (d.getIntrinsicHeight() * metrics.density);
            if (originalWidthScaled > metrics.widthPixels) {
                height = d.getIntrinsicHeight() * metrics.widthPixels
                    / d.getIntrinsicWidth();
                width = metrics.widthPixels;
            } else {
                height = originalHeightScaled;
                width = originalWidthScaled;
            }

            // it's important to call setBounds otherwise the image will
            // have a size of 0px * 0px and won't show at all
            d.setBounds(0, 0, width, height);

            // now we create a new ImageSpan
            ImageSpan newImg = new ImageSpan(d, img.getSource());

            // find the position of the old ImageSpan
            int start = htmlSpannable.getSpanStart(img);
            int end = htmlSpannable.getSpanEnd(img);

            // remove the old ImageSpan
            htmlSpannable.removeSpan(img);

            // add the new ImageSpan
            htmlSpannable.setSpan(newImg, start, end,
                    Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);

            // finally we have to update the TextView with our
            // updates Spannable to display the image
            htmlTextView.setText(htmlSpannable);
        }
    }

    private File getImageFile(ImageSpan img) {

        // you need to implement this method yourself.
        // it must return a unique File object (or something
        // different if you also change the rest of the code)
        // for every image tag. use img.getSource() to get
        // the src="" attribute. you might want to use some
        // hash of the url as file name

    }

}

要调整图像大小,包含的代码是您可以根据需要更改逻辑 20 缩放百分比或任何您想要的显示矩阵(屏幕的高度和宽度)享受

DisplayMetrics metrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(metrics);

int width, height;
            int originalWidthScaled = (int) (d.getIntrinsicWidth() * metrics.density);
            int originalHeightScaled = (int) (d.getIntrinsicHeight() * metrics.density);
            if (originalWidthScaled > metrics.widthPixels) {
                height = d.getIntrinsicHeight() * metrics.widthPixels
                    / d.getIntrinsicWidth();
                width = metrics.widthPixels;
            } else {
                height = originalHeightScaled;
                width = originalWidthScaled;
            }

            // it's important to call setBounds otherwise the image will
            // have a size of 0px * 0px and won't show at all
            d.setBounds(0, 0, width, height);

并在单独的线程中加载图像将避免 anr

于 2013-07-17T05:46:55.863 回答