{"action":"created","issue":{"url":"https://api.github.com/repos/pocorall/scaloid/issues/119","labels_url":"https://api.github.com/repos/pocorall/scaloid/issues/119/labels{/name}","comments_url":"https://api.github.com/repos/pocorall/scaloid/issues/119/comments","events_url":"https://api.github.com/repos/pocorall/scaloid/issues/119/events","html_url":"https://github.com/pocorall/scaloid/pull/119","id":60236949,"number":119,"title":"Add evalOnUiThread() method, and make runOnUiThread() return Unit.","user":{"login":"tvierling","id":397857,"avatar_url":"https://avatars.githubusercontent.com/u/397857?v=3","gravatar_id":"","url":"https://api.github.com/users/tvierling","html_url":"https://github.com/tvierling","followers_url":"https://api.github.com/users/tvierling/followers","following_url":"https://api.github.com/users/tvierling/following{/other_user}","gists_url":"https://api.github.com/users/tvierling/gists{/gist_id}","starred_url":"https://api.github.com/users/tvierling/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/tvierling/subscriptions","organizations_url":"https://api.github.com/users/tvierling/orgs","repos_url":"https://api.github.com/users/tvierling/repos","events_url":"https://api.github.com/users/tvierling/events{/privacy}","received_events_url":"https://api.github.com/users/tvierling/received_events","type":"User","site_admin":false},"labels":[],"state":"open","locked":false,"assignee":null,"milestone":null,"comments":1,"created_at":"2015-03-08T02:17:15Z","updated_at":"2015-03-08T04:44:56Z","closed_at":null,"pull_request":{"url":"https://api.github.com/repos/pocorall/scaloid/pulls/119","html_url":"https://github.com/pocorall/scaloid/pull/119","diff_url":"https://github.com/pocorall/scaloid/pull/119.diff","patch_url":"https://github.com/pocorall/scaloid/pull/119.patch"},"body":"[NOTE: This change needs MAJOR TESTING on multiple Android versions. I'm not sure that this concurrency management will work correctly across versions, and this has had limited testing on only a 4.3 virtual machine/emulator.]\r\n\r\n\r\nSome operations on the UI thread need to return values. In order to do so\r\nsafely, we need a method of enqueueing a computation behind a container\r\nwhich supports a blocking wait for the result.\r\n\r\nevalOnUiThread() takes a code block just like runOnUiThread(), but\r\nreturns a scala.concurrent.Future wrapper for the result. In most cases\r\nthis can be dereferenced by doing:\r\n\r\nval res = Await.result(f, Duration.Inf)\r\n\r\nwhich will block indefinitely in the current thread, waiting for the\r\nsubmitted computation to execute on the UI thread. Once the computation\r\ncompletes, either res will contain the successful result. If an exception\r\nis thrown in the computation, or the it will be re-thrown in the *current*\r\nthread where Await.result() is called.\r\n\r\nIf Await.result() (or other appropriate handling of the Future) is never\r\ncalled, the result OR exception is discarded. Make sure to do something\r\nwith the Future so an exception result goes somewhere useful!\r\n\r\n(By contrast, runOnUiThread() instead lets an exception bubble up the UI\r\nthread's stack since it has nowhere else to send it. This also means that\r\nevalOnUiThread() can be used for a code block which needs to propagate\r\nan exception outside the UI thread but otherwise has no useful result.)\r\n\r\nThis change also alters two scaloid-internal methods which were depending\r\non the old behavior of getting a result from the call as a side effect of\r\nalready running in the UI thread. Instead, the result is Await'ed.\r\n\r\nThanks to PkmX@github for the basic implementation behind evalOnUiThread.\r\n\r\nFixes #118."},"comment":{"url":"https://api.github.com/repos/pocorall/scaloid/issues/comments/77733011","html_url":"https://github.com/pocorall/scaloid/pull/119#issuecomment-77733011","issue_url":"https://api.github.com/repos/pocorall/scaloid/issues/119","id":77733011,"user":{"login":"pocorall","id":1108852,"avatar_url":"https://avatars.githubusercontent.com/u/1108852?v=3","gravatar_id":"","url":"https://api.github.com/users/pocorall","html_url":"https://github.com/pocorall","followers_url":"https://api.github.com/users/pocorall/followers","following_url":"https://api.github.com/users/pocorall/following{/other_user}","gists_url":"https://api.github.com/users/pocorall/gists{/gist_id}","starred_url":"https://api.github.com/users/pocorall/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/pocorall/subscriptions","organizations_url":"https://api.github.com/users/pocorall/orgs","repos_url":"https://api.github.com/users/pocorall/repos","events_url":"https://api.github.com/users/pocorall/events{/privacy}","received_events_url":"https://api.github.com/users/pocorall/received_events","type":"User","site_admin":false},"created_at":"2015-03-08T04:44:55Z","updated_at":"2015-03-08T04:44:55Z","body":"Thanks for the great contribution!\r\n\r\nI'll test it more on various real devices I have.\r\n\r\nAwaiting the result by default would not be desirable sometimes. How about change the result type of `show()` and `spinnerDialog()` to `Future[AlertDialog]` and `Future[ProgressDialog]` respectively? It is a breaking change, but it would also be a proper indication for users that the behavior is also changed (it doesn't return `null`).\r\n"}}