I'm using Nexus 5. Version 5.1.1
I want to take screenshot programmatically of phone at any given time. I'm okay if the solution is specific to Nexus 5.
After reading many answers, I've tried below solution using screencap.
Issue is it creates image file, but it is blank.
private void takeSS() {
try {
if (isExternalStorageWritable()) {
Process su = Runtime.getRuntime().exec("/system/bin/screencap -p /storage/emulated/0/img.png\n");
DataOutputStream outputStream = new DataOutputStream(su.getOutputStream());
outputStream.flush();
su.waitFor();
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(su.getInputStream()));
String line;
while ((line = bufferedReader.readLine()) != null) {
String output = line + System.getProperty("line.separator");
System.out.println(line);
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
/* Checks if external storage is available for read and write */
public boolean isExternalStorageWritable() {
String state = Environment.getExternalStorageState();
if (Environment.MEDIA_MOUNTED.equals(state)) {
return true;
}
return false;
}
The same command if I run from command prompt, it executes successfully.
Please suggest what might be the issue.
P.S. - My phone is rooted.
Thank You
Have you tried executing the command as su?
"/system/bin/su -c \"/system/bin/screencap -p /storage/emulated/0/img.png\""
Related
I'm accessing to running exe using below method. But I want to get the count of running exe files. Basically I want to get the count of exe process currently runs. Other than assigning all the process name to a list is there a simple way to obtain the count.
public boolean isProcessRunning(String serviceName) {
try {
Process pro = Runtime.getRuntime().exec(TASKLIST);
BufferedReader reader = new BufferedReader(new InputStreamReader(pro.getInputStream()));
String line;
while ((line = reader.readLine()) != null) {
// System.out.println(line);
if (line.startsWith(serviceName)) {
return true;
}
}
} catch (IOException e) {
e.printStackTrace();
}
return false;
}
We are the using the following code to generate PDFs using wkhtmltopdf
public class SystemUtils{
public String executeCommand(String... command) {
Process process = null;
try {
// Using redirectErrorStream as true. Otherwise we have to read both process.getInputStream() and
// process.getErrorStream() in order to not exhaust the stream buffer.
process = new ProcessBuilder(command).redirectErrorStream(true).start();
process.waitFor();
StringBuilder outputBuilder = new StringBuilder();
try(BufferedReader stdError = new BufferedReader(new InputStreamReader(process.getInputStream()))) {
String line;
while ((line = stdError.readLine()) != null) {
outputBuilder.append(line).append(StringConstants.CARRIAGE_RETURN);
}
}
return outputBuilder.toString();
} catch (IOException | InterruptedException e) {
String exceptionMsg = "Error while executing command '"+command+"' : ";
LOGGER.error(exceptionMsg, e);
throw new AppException(exceptionMsg, e);
} finally {
if(process != null){
process.destroy();
}
}
}
public static void main(String[] args){
SystemUtils systemUtils = new SystemUtils();
String[] array = {"wkhtmltopdf", "/home/pgullapalli/Desktop/testsimilar1.html", "/home/pgullapalli/Desktop/test.pdf"};
systemUtils.executeCommand(array);
}
}
This works absolutely fine for smaller size files. But when we try to process a larger file, it is indefinitely waiting without any response. I am not sure what is going wrong? Can someone please suggest?
I moved process.waitFor() before the return statement and it started working. This probably could be happening as the output buffer has filled and we are not reading from it. After moving the process.waitFor after the stream reading, things are working fine.
Well, i'm working a project to test my knowledge of java programming.
My project is a game and i'm making some kind of launcher for it that closes when the project has fully booted. I searched on the web to see how i check if a java program is running or not. I found a way to see if a program is running (here is the link to it or see code below). I tested it but it didn't work so i searched for the answer to check if a process/program is running under a "bigger" program (exemple: multiple windows in firefox). I didn't find it so i hope that you know the answer.
Here is the way to check if a program is running that i found (And here is the link again):
String line;
String pidInfo ="";
Process p =Runtime.getRuntime().exec(System.getenv("windir") +"\\system32\\"+"tasklist.exe");
BufferedReader input = new BufferedReader(new InputStreamReader(p.getInputStream()));
while ((line = input.readLine()) != null) {
pidInfo+=line;
}
input.close();
if(pidInfo.contains("file.class"))
{
// do what you want
}
Instead of checking whether the game process is running (Which isn't so possible with the pid, since that's a number), you can check the contents of a file:
File f = new File("path_to_file.txt");
BufferedReader br;
String text = "";
try {
br= new BufferedReader(new FileReader(f));
String line;
while((line = br.readLine())!=null){
text+=line;
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
if(text.equals("started")){
// we have to make sure it can work next time so we clear the file's contents
try {
BufferedWriter bw = new BufferedWriter(new FileWriter(f));
bw.write("");
bw.flush();
bw.close();
} catch (IOException e) {
e.printStackTrace();
}
//close launcher
}
And then the only thing left to do is have the game write to that file the text "started" after it has started.
I want the Apache Cordova CLI being called by a Java Process but unfortunatly the Java Process doesn't wait until it is finished.
This is, how i call it:
StringBuffer sb = null;
String cmd = "cd /location/generated && cordova create MyNewApp"
try {
Process p = Runtime.getRuntime().exec(cmd);
p.waitFor();
BufferedReader reader =
new BufferedReader(new InputStreamReader(p.getInputStream()));
sb = new StringBuffer();
String line = "";
while ((line = reader.readLine()) != null) {
sb.append(line + "\n");
}
} catch (InterruptedException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
I've seen many solutions, that say "waitFor()" will do the trick but unfortunatly not for me. I've already tried to always read and compare the last line of code generated by the cordova cmd and finish afterwards, but this is not a good approach. Do you have any suggestions?
Resolved it:
Cmd looks like this "cordova create /path/to/generated/app/ Hello World"
Be aware, the path has to exist before the cmd is beeing called
The code that I am using for running a terminal command in Linux Debian and getting the output inside a java program is this:
public static String execute(String command) {
StringBuilder sb = new StringBuilder();
String[] commands = new String[]{"/bin/sh", "-c", command};
try {
Process proc = new ProcessBuilder(commands).start();
BufferedReader stdInput = new BufferedReader(new
InputStreamReader(proc.getInputStream()));
BufferedReader stdError = new BufferedReader(new
InputStreamReader(proc.getErrorStream()));
String s = null;
while ((s = stdInput.readLine()) != null) {
sb.append(s);
sb.append("\n");
}
while ((s = stdError.readLine()) != null) {
sb.append(s);
sb.append("\n");
}
} catch (IOException e) {
return e.getMessage();
}
return sb.toString();
}
Now the problem is, it works for normal commands like ls / and gives back the appropriate result. But my goal is to run commands like:
echo 23 > /sys/class/gpio/export
which is, for example, for activating the gpio pin in the CubieBoard platform.
(Cubieboard is a mini-pc board like Raspberry Pi).
Now running this command in the terminal of the system itself, works fine and gives me the proper result. But when i am running it from this java code, i cannot get any results back.
The point is that, it works and the command executes well, but just that i cannot get the output message of the command!
For example if the pin was active from the past, then normally it should give me back the result like:
bash: echo: write error: Device or resource busy
But when i run this command through java code above, i do not get any response back.
(again it takes effect but just the response of the terminal i cannot get!)
When i run the code, both stdInput and stdError variables in the code are having the value null. :(
Please help me so that i can finish my project. this is the only part that is remaining :(
Thank you.
There maybe the childProcess doesn't run to end
Please to try:
proc.waitFor()
and run read stdInput and stdError in other Thread before proc.waitFor().
Example:
public static String execute(String command) {
String[] commands = new String[] { "/bin/sh", "-c", command };
ExecutorService executor = Executors.newCachedThreadPool();
try {
ProcessBuilder builder = new ProcessBuilder(commands);
/*-
Process proc = builder.start();
CollectOutput collectStdOut = new CollectOutput(
proc.getInputStream());
executor.execute(collectStdOut);
CollectOutput collectStdErr = new CollectOutput(
proc.getErrorStream());
executor.execute(collectStdErr);
// */
// /*-
// merges standard error and standard output
builder.redirectErrorStream();
Process proc = builder.start();
CollectOutput out = new CollectOutput(proc.getInputStream());
executor.execute(out);
// */
// child proc exit code
int waitFor = proc.waitFor();
return out.get();
} catch (IOException e) {
return e.getMessage();
} catch (InterruptedException e) {
// proc maybe interrupted
e.printStackTrace();
}
return null;
}
public static class CollectOutput implements Runnable {
private final StringBuffer buffer = new StringBuffer();
private final InputStream inputStream;
public CollectOutput(InputStream inputStream) {
super();
this.inputStream = inputStream;
}
/*
* (non-Javadoc)
*
* #see java.lang.Runnable#run()
*/
#Override
public void run() {
BufferedReader reader = null;
String line;
try {
reader = new BufferedReader(new InputStreamReader(inputStream));
while ((line = reader.readLine()) != null) {
buffer.append(line).append('\n');
}
} catch (Exception e) {
System.err.println(e);
} finally {
try {
reader.close();
} catch (IOException e) {
}
}
}
public String get() {
return buffer.toString();
}
}
the code is right, just in the second line, I changed
"/bin/sh" to "/bin/bash"
And everything works!
sh == bash?
For a long time, /bin/sh used to point to /bin/bash on most GNU/Linux systems. As a result, it had almost become safe to ignore the difference between the two. But that started to change recently.
Some popular examples of systems where /bin/sh does not point to /bin/bash (and on some of which /bin/bash may not even exist) are:
Modern Debian and Ubuntu systems, which symlink sh to dash by default;
Busybox, which is usually run during the Linux system boot time as part of initramfs. It uses the ash shell implementation.
BSDs. OpenBSD uses pdksh, a descendant of the Korn shell. FreeBSD's sh is a descendant of the original UNIX Bourne shell.
For more information on this please refer to :
Difference between sh and bash