I have looked into other camera flashlight related problems in stackoverflow, but couldn't find an answer that solves my issue. The flashlight flashes for 6-8 times and then the app crashes. Here I have a blink() method that calls cameraon() and cameraoff() in a loop. Could you please let me know where I went wrong?
My code can be found here: http://pastebin.com/3LRMwd1J
The logcat output can be see here: http://pastebin.com/2GTpn8Ux
I have tried using surface textures, tried to include Thread.sleep() in betweencameraon() and cameraoff() but so far no luck.
I use Android 4.4 with latest sdk and jdk versions.
I use nexus 5 for testing.
Thanks in advance!
just take Thread in Blink() method and put your code with if else
boolean tourchon=false;
Thread thread = new Thread(new Runnable() {
#Override
public void run() {
for (int i = 0; i < 10; i++) {
if(tourchon){
cameraoff();
tourchon=false;
}else{
cameraon();
tourchon=true;
}
try {
Thread.sleep(200);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
});
thread.start();
Try this code...
Separate the obtaining of camera object from your cameraOn() method, as i understand this method should be turning the flash on, calling open() that many times in that short time may be causing your problems as this documentation suggests.
Caution: On some devices, this method may take a long time to complete. It is best to call this method from a worker thread (possibly using AsyncTask) to avoid blocking the main application UI thread.
So have your on and off methods just change the flash mode, because you already have the camera instance.
See if my code helps any:
https://github.com/wolfhorse/SimpleFlashlight
It doesn't blink but it may be a good reference for you.
EDIT:
I modified the onClick() event of the toggle button in the SimpleFlashlight app referenced above by adding the code below and it blinks/flashes fine on my Samsung Galaxy S5 without error.
Thread thread = new Thread(new Runnable() {
#Override
public void run() {
boolean flashOn = false;
for (int i = 0; i < 20; i++) {
flashOn = !flashOn;
toggleFlash(flashOn);
try {
Thread.sleep(300);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
});
thread.start();
Wrapped in new Thread like others suggested here - better performance.
Related
I'm working on a Tetris-app and I have a Thread.sleep command to animate the falling of the tetriminos. But that creates a conflict with the UI. So I tried runOnUiThread() like this:
while (gameover == false) {
tetriminoSettled = false;
try {
Thread.sleep(1000 - (counter * 3));
} catch (InterruptedException e) {
e.printStackTrace();
}
runOnUiThread(new Runnable() {
#Override
public void run() {
Random ran = new Random();
int x = ran.nextInt(7) + 1;
addTetrimino(createTetrimino(x)); //the UI operation
gridView.invalidate();
}
});
But the UI gets only updated after the game ends.
Do you think AsyncTask is a good approach?
Please try to keep in mind that I later need additional UI-Threads for shifting the tetriminos left and right and so on.
Thanks!
Judging from the code you posted, it looks like you are using a gridview for a game. It is possible but not worth the effort. Just use a SurfaceView as shown in this short tutorial. You'll have an onDraw callback in which you can update whatever you like every drawing cycle. Have fun, coding games is really hard :).
Try gridView.postInvalidate();
So essentially I want to simulate a button click in my android app, using a timer.
When the timer goes off, I do find the button then try using performClick() which crashes and closes the app.
The log of course made the problem quite clear: "Only the original thread that created a view hierarchy can touch its views." Which makes total sense. Duh!
But I assume that since it's all my app there is a way to properly do this?
You can use runOnUiThread() in a background Thread in order to update the UI Thread:
try {
runOnUiThread(new Runnable() {
#Override
public void run() {
//Run your functions here
}
});
} catch (InterruptedException e) {
e.printStackTrace();
}
The app I'm making requires that a bit of code be executed whenever the value of a particular variable changes from 0 to 1.
The handler example below is the method I'm currently using to do this (I copied it from someone else).
I have a feeling it's not a proper method though because having just three of these handlers in my app causes the UI to be fairly unresponsive, and causes the device (a phone) to become quite hot.
As you can see, I've put 10ms delays in the handlers to try to deal with this.
Isn't there something more like OnClickListener that can listen at all times for a variable value change without putting such stress on the CPU?
I'm pretty new to Java and Android so a simple example would be very much appreciated.
final Handler myHandler1 = new Handler();
new Thread(new Runnable()
{
#Override
public void run()
{
while (true)
{
try
{
Thread.sleep(10);
myHandler1.post(new Runnable()
{
#Override
public void run()
{
if (myVariable == 1)
{
myVariable = 0;
//do stuff
}
}
});
} catch (Exception e) {}
}
}
}).start();
You must set your variable via a setter method. Then, you can be reactive to that change.
public void setMyVariable(int value) {
this.myVariable = value;
if (myVariable == 1) {
doSomethingWhen1();
} else if (myVariable == 0) {
doSomethingWhen0();
}
}
A more elegant way to do that will be an observer pattern, Here you can find more detailed documentation about it.
You must certainly avoid while(true) loops on mobile device, it will drain your battery and you are also blocking the UI thread. That's the reason why your UI is unresponsive and your cellphone it's quite hot.
I am a relatively new Android programmer and I was wondering how you could get read text off the internet in 4.0.3. I keep finding code that gives me a Network on Main exception: http://developer.android.com/reference/android/os/NetworkOnMainThreadException.html and was wondering if anyone could provide me some sample code to get around this, for reference I got the code I tried to use here: http://android-er.blogspot.com/2011/04/read-text-file-from-internet-using-java.html. Thanks a lot.
In Honeycomb and Ice Cream Sandwich (i.e. Android 3.0+) , you cannot connect to the internet in the main thread (onCreate(), onPause(), onResume() etc.), and you have to instead start a new thread. The reason why this has changed is because network operations can make the app wait for a long time, and if you're running them in the main thread, the whole application becomes unresponsive. If you try to connect from the main thread, Android will throw a NetworkOnMainThreadException.
To bypass this, you can run networking code from a new thread, and use runOnUiThread() to do things in the main thread, such as update the user interface. Generally, you can do something like:
class MyActivity extends Activity {
public onCreate(Bundle savedInstanceState) {
super.onCreate();
// Create thread
Thread networkThread = new Thread() {
#Override
public void run() {
try {
// this is where your networking code goes
// I'm declaring the variable final to be accessible from runOnUiThread
final String result = someFunctionThatUsesNetwork();
runOnUiThread(new Runnable() {
#Override
public void run() {
// this is where you can update your interface with your results
TextView myLabel = (TextView) findViewById(R.id.myLabel);
myLabel.setText(result);
}
}
} catch (IOException e) {
Log.e("App", "IOException thrown", e);
}
}
}
}
}
You need to complete an HTTP Request. There are a lot of examples available on line. Try here for starts.
I have an ImageView, what shows one picture . I tried to use a thread, but it doesn't change the picture. Then I tried a handler, but it doesn't treat the sleep(int) method, so I can't increase the time, what elapsed. How can I make it? Can you write an example please?
Here is my original code:
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
Thread timer = new Thread() {
public void run() {
int time = 0;
while (time <= 7000) {
try {
sleep(100);
time =+ 100;
if(time == 2000) {
radar.setImageResource(R.drawable.radar_full);
}
if(time == 5000) {
radar.setImageResource(R.drawable.radar_50);
}
if(time == 7000) {
radar.setImageResource(R.drawable.radar_found);
}
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
};
timer.start();
};
};
Here are a couple of tutorials for you:
Android GUI thread timer sample
A Stitch in Time
It appears that you need to learn more about Threads and Handlers in general. However, it's worth pointing out that you cannot update a UI element from within a Thread, which is what I'm guessing you tried to do; UI updating (such as changing the content of an ImageView) must be done within the UI thread. Therefore, updating the image inside a Handler on the UI thread was going in the right direction. You just need a way to call that Handler at timed intervals, and the tutorial above demonstrates one such way, by simply posting messages to the Handler.