我有一个asyncTask来获取图像(它具有动态的宽度和高度,因此不使用毕加索或壁画)。我为此使用url.OpenConnection,但我想缓存结果,因此具有相同url的下一次调用将仅检查缓存并返回结果。我如何设置它使用缓存?
private var mBitmap: Bitmap? = null
private inner class FetchImageAsync : AsyncTask<String, Void, Bitmap>() {
override fun doInBackground(vararg params: String): Bitmap? {
// your background code fetch InputStream
val imageId = params[0]
var bmp: Bitmap? = null
try {
val url = URL("https://" + BASE_ENDPOINT + "/" + imageId)
bmp = BitmapFactory.decodeStream(url.openConnection().getInputStream())
mBitmap = bmp
} catch (e: Exception) {
}
return bmp
}
override fun onPostExecute(bmp: Bitmap?) {
super.onPostExecute(bmp)
if (bmp != null && activity != null) {
iv.setImageBitmap(bmp)
}
}
}
我试图将解码后的位图的结果保存到一个名为mBitmap的类变量中,但是当片段被“替换”并且返回片段时,它的mBitmap再次为null吗?为什么呢?我以为片段替换会记住状态。为了清楚起见,我正在寻找一种方法,在我已经做完之后不要继续在相同的URL上进行网络调用。这应该全部是本地的,而不是服务器端的。
这是我替换片段的方式:
public void replaceFragment(Fragment f) {
FragmentTransaction transaction = getChildFragmentManager().beginTransaction();
transaction.addToBackStack(null);
transaction.replace(R.id.fl_attributes_container, f, f.getClass().getName()).commit();
}
<FrameLayout
android:id="@+id/fl_attributes_container"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
更新:这是我的整个片段:
class MyFragment : Fragment() {
private var mBitmap: Bitmap? = null
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
val rootView = inflater.inflate(R.layout.fragment_layout, container, false)
return rootView
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
initView()
}
private fun initView() {
setupImage()
}
private fun setupImage() {
//the mBitmap is always null after i come back to the fragment from a replace, why ?
mBitmap?.let { bitmap -> iv.setImageBitmap(bitmap) }
?: run { FetchImageAsync().execute(it) }
}
private inner class FetchImageAsync : AsyncTask<String, Void, Bitmap>() {
override fun doInBackground(vararg params: String): Bitmap? {
// your background code fetch InputStream
val imageId = params[0]
var bmp: Bitmap? = null
try {
val url = URL("https://" + BASE_ENDPOINT + "/" + imageId)
bmp = BitmapFactory.decodeStream(url.openConnection().getInputStream())
mBitmap = bmp
} catch (e: Exception) {
}
return bmp
}
override fun onPostExecute(bmp: Bitmap?) {
super.onPostExecute(bmp)
if (bmp != null && activity != null) {
iv.setImageBitmap(bmp)
}
}
}
companion object {
fun newInstance(b: Bundle?): MyFragment {
val frag = MyFragment()
frag.arguments = b ?: Bundle()
return frag
}
}
答案 0 :(得分:1)
您正在使用replaceFragment
方法切换回以前的某些Fragment
。如评论中所述,其操作如下:
replaceFragment(MyFragment.Companion.newInstance(null));
但是,这每次都需要一个新的实例参数,因此您替换的Fragment
是一个全新的对象,无法知道其他Fragment
的成员变量。
要解决此问题,请尝试标记您的Fragment
,以便在找到后可以重新使用。因此,在调用replaceFragment之前,请执行以下操作:
var frag = getChildFragmentManager().findFragmentByTag(tag)
if (frag == null) {
frag = MyFragment.Companion.newInstance(null)
}
replaceFragment(frag)