[英]Caused by: java.lang.NullPointerException: lock == null
[英]java.lang.NullPointerException: lock == null from InputStreamReader
所以我试图解析一个 .obj 波前文件以使用 OpenGL ES 显示,事情是,我得到 Nullpointer 就好像文件不存在或为空(?)。 我尝试了两种不同的方法来解析文件,还确保上面没有空行,将它放在不同的文件夹中(资产、src 根、res 等),但结果是一样的。 也许我得到的错误更多地与代码的 OpenGL 部分有关? 但我有点迷路了,因为显然它应该工作......还尝试在 function 之外缓冲文件,同样发生了。 从这里的另一个问题来看,这个人遇到的问题与“尝试从工作线程更新 UI”有关。 异步在这里没有帮助我。
我从这个博客中得到了代码想法: http://etcodehome.blogspot.com/2011/07/android-rendering-3d-blender-models.html
fun loadObjFile() {
try {
var str: String
var tmp: Array<String>
var ftmp: Array<String>
var v: Float
val vlist = ArrayList<Float>()
val nlist = ArrayList<Float>()
val fplist = ArrayList<Fp>()
val mContext: Context? = null
//val inb: BufferedReader = File("androidmodel.obj").bufferedReader()
//val inputString = inb.use { it.readText() }
val inb = BufferedReader(InputStreamReader(mContext?.getAssets()?.open
("src/main/res/androidmodel.obj")), 1024) //Error is here at com.example.xxx.MyGLRenderer.loadObjFile
while (inb.readLine().also { str = it } != null) {
tmp = str.split(" ".toRegex()).toTypedArray()
//Parse the vertices
if (tmp[0].equals("v", ignoreCase = true)) {
for (i in 1..3) {
v = tmp[i].toFloat()
vlist.add(v)
}
}
//Parse the vertex normals
if (tmp[0].equals("vn", ignoreCase = true)) {
for (i in 1..3) {
v = tmp[i].toFloat()
nlist.add(v)
}
}
//Parse the faces/indices
if (tmp[0].equals("f", ignoreCase = true)) {
for (i in 1..3) {
ftmp = tmp[i].split("/".toRegex()).toTypedArray()
val chi = ftmp[0].toInt() - 1.toLong()
var cht = 0
if (ftmp[1] != "") cht = ftmp[1].toInt() - 1
val chn = ftmp[2].toInt() - 1
fplist.add(Fp(chi, cht, chn))
}
NBFACES++
}
}
val vbb = ByteBuffer.allocateDirect(fplist.size * 4 * 3)
vbb.order(ByteOrder.nativeOrder())
mVertexBuffer = vbb.asFloatBuffer()
val nbb = ByteBuffer.allocateDirect(fplist.size * 4 * 3)
nbb.order(ByteOrder.nativeOrder())
mNormBuffer = nbb.asFloatBuffer()
for (j in fplist.indices) {
mVertexBuffer?.put(vlist[(fplist[j].Vi * 3).toInt()])
mVertexBuffer?.put(vlist[(fplist[j].Vi * 3 + 1).toInt()])
mVertexBuffer?.put(vlist[(fplist[j].Vi * 3 + 2).toInt()])
mNormBuffer?.put(nlist[fplist[j].Ni * 3])
mNormBuffer?.put(nlist[fplist[j].Ni * 3 + 1])
mNormBuffer?.put(nlist[fplist[j].Ni * 3 + 2])
}
mIndexBuffer = CharBuffer.allocate(fplist.size)
for (j in fplist.indices) {
mIndexBuffer?.put(j.toChar())
}
mVertexBuffer?.position(0)
mNormBuffer?.position(0)
mIndexBuffer?.position(0)
} catch (e: IOException) {
e.printStackTrace()
}
}
private class Fp
(var Vi: Long, var Ti: Int, var Ni: Int)
问题是您将null
传递给InputStreamReader
。 资产路径错误。
assets
目录下,该目录与java
和res
文件夹位于目录层次结构中的同一级别。assets
目录的路径。 因此,如果您的文件直接位于assets
下,则相对路径为"androidmodel.obj"
。 因此,创建输入 stream 将如下所示:InputStreamReader(mContext?.getAssets()?.open("androidmodel.obj"))
但我强烈建议您检查非空值,因为如果mContext
是 null - 问题将返回。
mContext?.getAssets()?.open("androidmodel.obj")?.let { nonNullAsset ->
InputStreamReader(nonNullAsset)
}
这部分是let
的?.let {
如果没有assets
目录,只需创建一个简单的目录,它会被 IDE 自动拾取:
由于 NPE 仍然发生,剩下的唯一原因是mContext
变量中的null
值。 确保它已初始化。
经过更多的挖掘,我可以说这从一开始就是问题所在。 任何将文件的错误路径传递给assets.open(fileName)
function 的尝试都将导致FileNotFoundException
。 因此,即使您使用的路径是错误的,您甚至没有达到打开文件的地步,因为上下文是 null。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.