I want to write a activity for my android app that spell-checks words in my language (Czech). I included the .dic and .aff that I need. The app runs normally but when I try to proceed to this activity
package com.example.mainscreen
import android.content.ClipData
import android.content.ClipboardManager
import android.content.Context
import android.content.Intent
import android.os.Bundle
import android.widget.Button
import android.widget.ImageView
import android.widget.TextView
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import androidx.core.content.ContextCompat.getSystemService
import androidx.core.content.ContextCompat.startActivity
import com.nikialeksey.hunspell.Hunspell
import com.sun.jna.Native
import com.sun.jna.NativeLibrary
class TextCheck : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_text_check)
val incorrectText = findViewById<TextView>(R.id.incorrectText)
val correctText = findViewById<TextView>(R.id.suggText)
val copyBtn = findViewById<ImageView>(R.id.copyicon)
val backBtn = findViewById<Button>(R.id.backBtn)
val resultTV = intent.getStringExtra("resultTV")
incorrectText.text = resultTV
val libPath = "MainScreen\\app\\libs\\hunspell.jar"
val hunspell = Hunspell("resources/dictionaries/cs_CZ.dic", "resources/dictionaries/cs_CZ.aff")
NativeLibrary.addSearchPath("hunspell", libPath)
val misspelledWords = mutableMapOf<String, List<String>>()
resultTV?.split(" ")?.forEach { word ->
if (hunspell.spell(word)) {
misspelledWords[word] = hunspell.suggest(word)
}
}
if (misspelledWords.isNotEmpty()) {
val correctedText = StringBuilder()
misspelledWords.forEach { (misspelled, suggestions) ->
correctedText.append("$misspelled: ${suggestions.joinToString(", ")}")
correctedText.append("\n")
}
correctText.text = correctedText.toString()
} else {
correctText.text = getString(R.string.textright)
}
copyBtn.setOnClickListener {
val clipboard = getSystemService(Context.CLIPBOARD_SERVICE) as ClipboardManager
val clip = ClipData.newPlainText("corrected text", correctText.text)
clipboard.setPrimaryClip(clip)
Toast.makeText(this, "Corrected text copied to clipboard", Toast.LENGTH_SHORT).show()
}
backBtn.setOnClickListener {
val intent = Intent(this, MainActivity::class.java)
startActivity(intent)
}
}
}
it returns to main page and giving me this error
E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.example.mainscreen, PID: 28788
java.lang.UnsatisfiedLinkError: Unable to load library 'hunspell':
dlopen failed: library "libhunspell.so" not found
dlopen failed: library "libhunspell.so" not found
dlopen failed: library "libhunspell.so" not found
Native library (android-aarch64/libhunspell.so) not found in resource path (.)
at com.sun.jna.NativeLibrary.loadLibrary(NativeLibrary.java:323)
at com.sun.jna.NativeLibrary.getInstance(NativeLibrary.java:483)
at com.sun.jna.Library$Handler.<init>(Library.java:197)
at com.sun.jna.Native.load(Native.java:622)
at com.sun.jna.Native.load(Native.java:596)
at com.nikialeksey.hunspell.Hunspell.<clinit>(Hunspell.java:20)
at com.example.mainscreen.TextCheck.onCreate(TextCheck.kt:35)
at android.app.Activity.performCreate(Activity.java:8129)
at android.app.Activity.performCreate(Activity.java:8109)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1344)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3749)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3942)
at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:109)
at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135)
at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2345)
at android.os.Handler.dispatchMessage(Handler.java:106)
at android.os.Looper.loopOnce(Looper.java:233)
at android.os.Looper.loop(Looper.java:344)
at android.app.ActivityThread.main(ActivityThread.java:8212)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:584)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1034)
Suppressed: java.lang.UnsatisfiedLinkError: dlopen failed: library "libhunspell.so" not found
at com.sun.jna.Native.open(Native Method)
at com.sun.jna.NativeLibrary.loadLibrary(NativeLibrary.java:211)
... 22 more
Suppressed: java.lang.UnsatisfiedLinkError: dlopen failed: library "libhunspell.so" not found
at com.sun.jna.Native.open(Native Method)
at com.sun.jna.NativeLibrary.loadLibrary(NativeLibrary.java:224)
... 22 more
Suppressed: java.lang.UnsatisfiedLinkError: dlopen failed: library "libhunspell.so" not found
at java.lang.Runtime.loadLibrary0(Runtime.java:1077)
at java.lang.Runtime.loadLibrary0(Runtime.java:998)
at java.lang.System.loadLibrary(System.java:1661)
at com.sun.jna.NativeLibrary.loadLibrary(NativeLibrary.java:238)
... 22 more
Suppressed: java.io.IOException: Native library (android-aarch64/libhunspell.so) not found in resource path (.)
at com.sun.jna.Native.extractFromResourcePath(Native.java:1145)
at com.sun.jna.NativeLibrary.loadLibrary(NativeLibrary.java:295)
... 22 more
what am I doing wrong? I am only a beginner at developing Android apps
Related
when i build smaple project , app has been crashed
when i see logcat , i see this:
90-30676/io.agora.agora_android_uikit E/agora.io: jni_generator_helper.h: (line 131): android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
what do i do ?
My code:
package io.agora.agora_android_uikit
import android.Manifest
import android.graphics.Color
import android.os.Bundle
import android.view.ViewGroup
import android.widget.Button
import android.widget.FrameLayout
import androidx.appcompat.app.AppCompatActivity
import io.agora.agorauikit_android.AgoraButton
import io.agora.agorauikit_android.AgoraConnectionData
import io.agora.agorauikit_android.AgoraSettings
import io.agora.agorauikit_android.AgoraVideoViewer
import io.agora.agorauikit_android.requestPermission
import io.agora.rtc2.Constants
private const val PERMISSION_REQ_ID = 22
private val REQUESTED_PERMISSIONS = arrayOf<String>(
Manifest.permission.RECORD_AUDIO,
Manifest.permission.CAMERA,
Manifest.permission.WRITE_EXTERNAL_STORAGE
)
#ExperimentalUnsignedTypes
class MainActivity : AppCompatActivity() {
var agView: AgoraVideoViewer? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
try {
agView = AgoraVideoViewer(
this, AgoraConnectionData("*******"),
)
} catch (e: Exception) {
println("Could not initialise AgoraVideoViewer. Check your App ID is valid. ${e.message}")
return
}
val set = FrameLayout.LayoutParams(
FrameLayout.LayoutParams.MATCH_PARENT,
FrameLayout.LayoutParams.MATCH_PARENT
)
this.addContentView(agView, set)
if (AgoraVideoViewer.requestPermission(this)) {
agView!!.join("test", role = Constants.CLIENT_ROLE_BROADCASTER)
} else {
val joinButton = Button(this)
// this#MainActivity.runOnUiThread(java.lang.Runnable {
runOnUiThread {
Runnable { joinButton.text = "Allow Camera and Microphone, then click here" }
}
// })
joinButton.setOnClickListener {
if (AgoraVideoViewer.requestPermission(this)) {
// (joinButton.parent as ViewGroup).removeView(joinButton)
agView!!.join("test", role = Constants.CLIENT_ROLE_BROADCASTER)
}
}
// joinButton.setBackgroundColor(Color.GREEN)
// joinButton.setTextColor(Color.RED)
this.addContentView(
joinButton,
FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, 300)
)
}
}
i want to solve my issue
Please wrap with function and make annotations there instead of mentioning in the main content view and wrap using UI thread.And refer sample github agora sdk github for reference - https://github.com/AgoraIO-Community/VideoUIKit-Android
I'm trying to create a natvie functions in flutter to share a image.
I didnt have problem with IOS, but in android and kotlin URI doesn't work.
Can anyone find a solution?
Its my code:
private fun shareImage(name: String, title: String, mimeType: String, path: String): Boolean {
val path = context.filesDir.absolutePath
val file = File("$path/$name")
Uri myUri = Uri.parse("$path/$name")
val shareIntent: Intent = Intent().apply {
action = Intent.ACTION_SEND
putExtra(Intent.EXTRA_STREAM, myUri)
type = mimeType
}
startActivity(Intent.createChooser(shareIntent, null))
return true
}
My imports:
import androidx.annotation.NonNull
import io.flutter.embedding.android.FlutterActivity
import io.flutter.embedding.engine.FlutterEngine
import io.flutter.plugin.common.MethodChannel
import android.app.Activity
import android.app.PendingIntent
import android.content.Context
import android.content.Intent
import android.net.Uri
import java.io.File;
Errors:
e: /Users/***/MainActivity.kt: (45, 15): Expecting an element
e: /Users/***/MainActivity.kt: (45, 20): Expecting an element
e: /Users/***/MainActivity.kt: (45, 5): Classifier 'Uri' does not have a companion object, and thus must be initialized here
e: /Users/***/MainActivity.kt: (49, 37): Unresolved reference: myUri
FAILURE: Build failed with an exception.
Iam and AR android app. I can load my .sfb files from asset. i want to load from direct server in order to secure my assets. Its loading from asset folder. not from direct server. iam using below code pls help me to solve this.
package com.example.a320_ar
import android.net.Uri
import android.os.Build
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.view.MotionEvent
import android.view.View
import android.widget.Button
import android.widget.Toast
import androidx.annotation.RequiresApi
import androidx.appcompat.app.AlertDialog
import com.google.ar.core.Anchor
import com.google.ar.core.Plane
import com.google.ar.sceneform.AnchorNode
import com.google.ar.sceneform.HitTestResult
import com.google.ar.sceneform.SkeletonNode
import com.google.ar.sceneform.animation.ModelAnimator
import com.google.ar.sceneform.rendering.ModelRenderable
import com.google.ar.sceneform.ux.ArFragment
import com.google.ar.sceneform.ux.TransformableNode
import kotlinx.android.synthetic.main.activity_main.*
import java.io.File
class MainActivity : AppCompatActivity() {
lateinit var arFragment: ArFragment
private lateinit var model: Uri
private var rendarable: ModelRenderable?=null
private var animator: ModelAnimator? = null
//private var modellink:String = "A320_Anim.sfb"
private var modellink:String = "http://10.0.0.193:90/fbx/A320_Anim.sfb"
#RequiresApi(Build.VERSION_CODES.N)
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
arFragment = sceneform_fragment as ArFragment
arFragment.setOnTapArPlaneListener { hitResult, plane, motionEvent ->
if (plane.type != Plane.Type.HORIZONTAL_UPWARD_FACING) {
return#setOnTapArPlaneListener
}
var anchor = hitResult.createAnchor()
btnStart.setOnClickListener {
placeObject(
arFragment,
anchor,
Uri.parse(modellink)
)
}
}
}
#RequiresApi(Build.VERSION_CODES.N)
private fun animateModel(name: String) {
animator?.let { it->
if(it.isRunning){
it.end()
}
}
rendarable?.let { modelRenderable ->
val data = modelRenderable.getAnimationData(name)
animator = ModelAnimator(data,modelRenderable)
animator?.start()
}
}
#RequiresApi(Build.VERSION_CODES.N)
private fun placeObject(arFragment: ArFragment, anchor: Anchor?, model: Uri?) {
ModelRenderable.builder()
.setSource(arFragment.context,model)
.build()
.thenAccept{
rendarable = it
addtoScene(arFragment, anchor, it)
}
.exceptionally {
val builder = AlertDialog.Builder(this)
builder.setMessage( it.message).setTitle("Error")
val dialog = builder.create()
dialog.show()
return#exceptionally null
}
}
private fun addtoScene(arFragment: ArFragment, anchor: Anchor?, it: ModelRenderable?) {
val anchorNode = AnchorNode(anchor)
val skeletonNode = SkeletonNode()
skeletonNode.renderable = rendarable
Toast.makeText(this,"inside add scene",Toast.LENGTH_SHORT).show()
val node = TransformableNode(arFragment.transformationSystem)
node.addChild(skeletonNode)
node.setParent(anchorNode)
node.setOnTapListener { v: HitTestResult?, event: MotionEvent? ->
//msgText.text = "Tapped me...$anchorNode --- $anchor --- $skeletonNode"
// var bt = findViewById<Button>(R.id.btnDel)
//bt.visibility = View.VISIBLE
//removeAnchorNode(anchorNode)
//bt.setOnClickListener { removeAnchorNode(anchorNode) }
}
arFragment.arSceneView.scene.addChild(anchorNode)
}
}
its working fine no errors. but its not showing my object on fragment.
private var modellink:String = "http://10.0.0.193:90/fbx/A320_Anim.sfb" (not loading .sfb)
private var modellink:String = "A320_Anim.sfb" (Loading the .sfb- woring fine)
please help me to load the model directly from server. i used all the permissions correctly.
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.CAMERA"/>
Thanks in advance,
Syed Abdul Rahim
Are you still using the old 1.6 version of Sceneform? You could try the new maintained version and also discard the sfb format and switch to glTF. The maintained version is up to date related to android dependencies and ARCore/Filament.
Well to your second question, if you want to secure your assets you have to serve it from a password protected API-Endpoint, but you have to host your own server, maybe some simpler solutions exists. Strings or text files can be directly secured with on board libraries (https://developer.android.com/guide/topics/security/cryptography)
i created my pagingSource class with paging 3.0.0-alpha10 and it worked but when i changed the version to 3.0.0-alpha12,
i got this error
this is the runtime exception:
java.lang.AbstractMethodError: abstract method "java.lang.Object androidx.paging.PagingDataDiffer.presentNewList(androidx.paging.NullPaddedList, androidx.paging.NullPaddedList, androidx.paging.CombinedLoadStates, int, kotlin.jvm.functions.Function0, kotlin.coroutines.Continuation)"
at androidx.paging.PagingDataDiffer$collectFrom$2$invokeSuspend$$inlined$collect$1$lambda$1.invokeSuspend(PagingDataDiffer.kt:136)
at androidx.paging.PagingDataDiffer$collectFrom$2$invokeSuspend$$inlined$collect$1$lambda$1.invoke(Unknown Source:10)
at kotlinx.coroutines.intrinsics.UndispatchedKt.startUndispatchedOrReturn(Undispatched.kt:91)
at kotlinx.coroutines.BuildersKt__Builders_commonKt.withContext(Builders.common.kt:161)
at kotlinx.coroutines.BuildersKt.withContext(Unknown Source:1)
at androidx.paging.PagingDataDiffer$collectFrom$2$invokeSuspend$$inlined$collect$1.emit(Collect.kt:133)
at kotlinx.coroutines.flow.FlowKt__ChannelsKt.emitAllImpl$FlowKt__ChannelsKt(Channels.kt:61)
at kotlinx.coroutines.flow.FlowKt__ChannelsKt$emitAllImpl$1.invokeSuspend(Unknown Source:11)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:106)
at kotlinx.coroutines.EventLoop.processUnconfinedEvent(EventLoop.common.kt:69)
at kotlinx.coroutines.DispatchedTaskKt.resumeUnconfined(DispatchedTask.kt:236)
at kotlinx.coroutines.DispatchedTaskKt.dispatch(DispatchedTask.kt:161)
at kotlinx.coroutines.CancellableContinuationImpl.dispatchResume(CancellableContinuationImpl.kt:362)
at kotlinx.coroutines.CancellableContinuationImpl.completeResume(CancellableContinuationImpl.kt:479)
at kotlinx.coroutines.channels.AbstractChannel$ReceiveElement.completeResumeReceive(AbstractChannel.kt:899)
at kotlinx.coroutines.channels.ArrayChannel.offerInternal(ArrayChannel.kt:84)
at kotlinx.coroutines.channels.AbstractSendChannel.send(AbstractChannel.kt:135)
at androidx.paging.PageFetcherSnapshot.doInitialLoad(PageFetcherSnapshot.kt:315)
at androidx.paging.PageFetcherSnapshot$doInitialLoad$1.invokeSuspend(Unknown Source:11)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:106)
at android.os.Handler.handleCallback(Handler.java:790)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:164)
at android.app.ActivityThread.main(ActivityThread.java:6543)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:440)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:810)
and this is my PaginSource:
import androidx.paging.PagingSource
import com.example.template.api.MyApi
import com.example.template.api.responses.ChatHistoryResponse
import retrofit2.HttpException
import java.io.IOException
class ChatHistoryPagingSource
constructor(
private val myApi: MyApi,
private val search: String,
private val type: String,
private val token: String,
private val status: String,
): PagingSource<Int, ChatHistoryResponse>() {
override suspend fun load(params: LoadParams<Int>): LoadResult<Int, ChatHistoryResponse> {
val position = params.key ?: 1
return try {
val response = myApi.chatHistoryList(token, status, position, 20, type, search)
LoadResult.Page(
data = response,
prevKey = if (position == 1) null else position -1,
nextKey = if (response.isEmpty()) null else position +1
)
} catch (exception: IOException) {
LoadResult.Error(exception)
} catch (exception: HttpException) {
LoadResult.Error(exception)
}
}
}
it works completely in the previous version but I have to migrate to the new one.
Most likely, the gradle dependencies you are using are not compatible with each other.
In my case, the exception occurred when I used androidx.room:room-paging:2.4.0-alpha05 with androidx.paging:paging-compose:1.0.0-alpha12. I fixed it by bumping version of paging compose to 1.0.0-alpha13.
Had the same issue while using androidx.room:room-paging:2.4.2 and androidx.paging:paging-runtime:3.0.0-alpha12.
I fixed it by changing the paging version to 3.1.0.
Here is my program to display results from a web app (data product) I made on an Android device.
package studio.nyaa.crimeprediction
import android.support.v7.app.AppCompatActivity
import android.os.Bundle
import java.net.URL
import android.util.Log
import android.widget.TextView
import com.beust.klaxon.JsonObject
import com.beust.klaxon.Parser
import kotlinx.coroutines.runBlocking
import kotlinx.coroutines.async
suspend fun obtainJson():JsonObject {
val sourceURL = "http://yingzhou474.pythonanywhere.com/api"
val jsonRes: String = URL(sourceURL).readText()
val parser: Parser = Parser.default()
val json = parser.parse(jsonRes) as JsonObject
Log.d("oj", "oj finished")
return json
}
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
runBlocking {
val json = async{obtainJson()}.await()
Log.d("postcoroutine", json.toString())
val crime1: Double? = json.obj("data")?.double("AGGRAVATED ASSAULT")
val crime2: Double? = json.obj("data")?.double("AUTO THEFT")
val crime3: Double? = json.obj("data")?.double("COMMERCIAL BURGLARY")
val crime4: Double? = json.obj("data")?.double("HOMICIDE")
val crime5: Double? = json.obj("data")?.double("LARCENY")
val crime6: Double? = json.obj("data")?.double("OTHER BURGLARY")
val crime7: Double? = json.obj("data")?.double("RESIDENTIAL BURGLARY")
val crime8: Double? = json.obj("data")?.double("ROBBERY")
val year: Int? = json.int("year")
val month: Int? = json.int("month")
val day: Int? = json.int("day")
val textView1: TextView = findViewById(R.id.editText1B)
textView1.text = crime1?.toString() ?: "N/A"
val textView2: TextView = findViewById(R.id.editText2B)
textView2.text = crime2?.toString() ?: "N/A"
val textView3: TextView = findViewById(R.id.editText3B)
textView3.text = crime3?.toString() ?: "N/A"
val textView4: TextView = findViewById(R.id.editText4B)
textView4.text = crime4?.toString() ?: "N/A"
val textView5: TextView = findViewById(R.id.editText5B)
textView5.text = crime5?.toString() ?: "N/A"
val textView6: TextView = findViewById(R.id.editText6B)
textView6.text = crime6?.toString() ?: "N/A"
val textView7: TextView = findViewById(R.id.editText7B)
textView7.text = crime7?.toString() ?: "N/A"
val textView8: TextView = findViewById(R.id.editText8B)
textView8.text = crime8?.toString() ?: "N/A"
val textViewDate: TextView = findViewById(R.id.editTextDate)
textViewDate.text = "Date: $month/$day/$year"
}
}
}
Here the data source is this site which returns a JsonObject of this kind:
{"data": {"AGGRAVATED ASSAULT": 6.87, "AUTO THEFT": 4.4, "COMMERCIAL BURGLARY": 1.3, "HOMICIDE": 0.62, "LARCENY": 30.72, "OTHER BURGLARY": 0.59, "RESIDENTIAL BURGLARY": 4.21, "ROBBERY": 3.16}, "year": 2019, "month": 8, "day": 20}
Edited2: I fixed the Klaxon error on my own.
Edited: After fixing this now I'm getting something else:
08-19 23:13:32.385 2175-2175/? E/AndroidRuntime: FATAL EXCEPTION: main
Process: studio.nyaa.crimeprediction, PID: 2175
java.lang.RuntimeException: Unable to start activity ComponentInfo{studio.nyaa.crimeprediction/studio.nyaa.crimeprediction.MainActivity}: java.io.FileNotFoundException: {"data": {"AGGRAVATED ASSAULT": 6.87, "AUTO THEFT": 4.4, "COMMERCIAL BURGLARY": 1.3, "HOMICIDE": 0.62, "LARCENY": 30.72, "OTHER BURGLARY": 0.59, "RESIDENTIAL BURGLARY": 4.21, "ROBBERY": 3.16}, "year": 2019, "month": 8, "day": 20}: open failed: ENOENT (No such file or directory)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2404)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2466)
at android.app.ActivityThread.access$900(ActivityThread.java:175)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1369)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:135)
at android.app.ActivityThread.main(ActivityThread.java:5418)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1037)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:832)
Caused by: java.io.FileNotFoundException: {"data": {"AGGRAVATED ASSAULT": 6.87, "AUTO THEFT": 4.4, "COMMERCIAL BURGLARY": 1.3, "HOMICIDE": 0.62, "LARCENY": 30.72, "OTHER BURGLARY": 0.59, "RESIDENTIAL BURGLARY": 4.21, "ROBBERY": 3.16}, "year": 2019, "month": 8, "day": 20}: open failed: ENOENT (No such file or directory)
at libcore.io.IoBridge.open(IoBridge.java:456)
at java.io.FileInputStream.<init>(FileInputStream.java:76)
at com.beust.klaxon.Parser$DefaultImpls.parse(Parser.kt:21)
at com.beust.klaxon.KlaxonParser.parse(KlaxonParser.kt:9)
at studio.nyaa.crimeprediction.MainActivityKt.obtainJson(MainActivity.kt:16)
at studio.nyaa.crimeprediction.MainActivity$onCreate$1$json$1.invokeSuspend(MainActivity.kt:25)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(Dispatched.kt:241)
at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:594)
at kotlinx.coroutines.scheduling.CoroutineScheduler.access$runSafely(CoroutineScheduler.kt:60)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:740)
Caused by: android.system.ErrnoException: open failed: ENOENT (No such file or directory)
at libcore.io.Posix.open(Native Method)
at libcore.io.BlockGuardOs.open(BlockGuardOs.java:186)
at libcore.io.IoBridge.open(IoBridge.java:442)
at java.io.FileInputStream.<init>(FileInputStream.java:76)
at com.beust.klaxon.Parser$DefaultImpls.parse(Parser.kt:21)
at com.beust.klaxon.KlaxonParser.parse(KlaxonParser.kt:9)
at studio.nyaa.crimeprediction.MainActivityKt.obtainJson(MainActivity.kt:16)
at studio.nyaa.crimeprediction.MainActivity$onCreate$1$json$1.invokeSuspend(MainActivity.kt:25)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(Dispatched.kt:241)
at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:594)
at kotlinx.coroutines.scheduling.CoroutineScheduler.access$runSafely(CoroutineScheduler.kt:60)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:740)
08-19 23:13:32.555 2175-2175/? I/Process: Sending signal. PID: 2175 SIG: 9
Old stuff:
Despite using async and await I still got the android.os.NetworkOnMainThreadException. Here is my stack trace:
08-19 22:28:06.675 28015-28015/? E/AndroidRuntime: FATAL EXCEPTION: main
Process: studio.nyaa.crimeprediction, PID: 28015
java.lang.RuntimeException: Unable to start activity ComponentInfo{studio.nyaa.crimeprediction/studio.nyaa.crimeprediction.MainActivity}: android.os.NetworkOnMainThreadException
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2404)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2466)
at android.app.ActivityThread.access$900(ActivityThread.java:175)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1369)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:135)
at android.app.ActivityThread.main(ActivityThread.java:5418)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1037)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:832)
Caused by: android.os.NetworkOnMainThreadException
at android.os.StrictMode$AndroidBlockGuardPolicy.onNetwork(StrictMode.java:1147)
at java.net.InetAddress.lookupHostByName(InetAddress.java:418)
at java.net.InetAddress.getAllByNameImpl(InetAddress.java:252)
at java.net.InetAddress.getAllByName(InetAddress.java:215)
at com.android.okhttp.HostResolver$1.getAllByName(HostResolver.java:29)
at com.android.okhttp.internal.http.RouteSelector.resetNextInetSocketAddress(RouteSelector.java:232)
at com.android.okhttp.internal.http.RouteSelector.next(RouteSelector.java:124)
at com.android.okhttp.internal.http.HttpEngine.connect(HttpEngine.java:272)
at com.android.okhttp.internal.http.HttpEngine.sendRequest(HttpEngine.java:211)
at com.android.okhttp.internal.http.HttpURLConnectionImpl.execute(HttpURLConnectionImpl.java:382)
at com.android.okhttp.internal.http.HttpURLConnectionImpl.getResponse(HttpURLConnectionImpl.java:332)
at com.android.okhttp.internal.http.HttpURLConnectionImpl.getInputStream(HttpURLConnectionImpl.java:199)
at java.net.URL.openStream(URL.java:470)
at kotlin.io.TextStreamsKt.readBytes(ReadWrite.kt:150)
at studio.nyaa.crimeprediction.MainActivityKt.obtainJson(MainActivity.kt:17)
at studio.nyaa.crimeprediction.MainActivity$onCreate$1$json$1.invokeSuspend(MainActivity.kt:28)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(Dispatched.kt:241)
at kotlinx.coroutines.EventLoopImplBase.processNextEvent(EventLoop.common.kt:270)
at kotlinx.coroutines.BlockingCoroutine.joinBlocking(Builders.kt:79)
at kotlinx.coroutines.BuildersKt__BuildersKt.runBlocking(Builders.kt:54)
at kotlinx.coroutines.BuildersKt.runBlocking(Unknown Source)
at kotlinx.coroutines.BuildersKt__BuildersKt.runBlocking$default(Builders.kt:36)
at kotlinx.coroutines.BuildersKt.runBlocking$default(Unknown Source)
at studio.nyaa.crimeprediction.MainActivity.onCreate(MainActivity.kt:27)
at android.app.Activity.performCreate(Activity.java:6083)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1115)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2357)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2466)
at android.app.ActivityThread.access$900(ActivityThread.java:175)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1369)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:135)
at android.app.ActivityThread.main(ActivityThread.java:5418)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1037)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:832)
This question is a variant of my earlier question.
It's because async block is running with Dispatchers.Main try using it with Dispatchers.IO
val json = async(Dispatchers.IO){obtainJson()}.await()
Also a better syntax would be to use withContext
val json = withContext(Dispatchers.IO){obtainJson()}
You shouldn't call network in the main thread. You can fix it by using IO dispatcher:
async(Dispatchers.IO){ obtainJson() }.await()
You should not use runBlocking {} in production code! It'll block your main thread.
Since you're calling this within the main thread, every following call to async or launch will be run in the same scope and thus on the main thread.
Instead you should launch a coroutine preferable with a viewModelScope (GlobalScope would be an acceptable start as well) and run the view updates on the main thread:
GlobalScope.launch(IO) {
val json = obtainJson()
Log.d("postcoroutine", json.toString())
val crime1: Double? = json.obj("data")?.double("AGGRAVATED ASSAULT")
...
val year: Int? = json.int("year")
val month: Int? = json.int("month")
val day: Int? = json.int("day")
launch(Main) {
val textView1: TextView = findViewById(R.id.editText1B)
textView1.text = crime1?.toString() ?: "N/A"
...
val textViewDate: TextView = findViewById(R.id.editTextDate)
textViewDate.text = "Date: $month/$day/$year"
}
}
Using async is not necessary here. Instead of launch(Main) you could use withContext(Main) though.