Improvement: add graphical ui

This commit is contained in:
Laurent Clouet
2015-01-15 23:20:17 +01:00
parent 2df4657202
commit df7c97b6a4
13 changed files with 481 additions and 0 deletions

View File

@@ -37,6 +37,9 @@
<filelist dir="." files="extern/args4j.jar" /> <filelist dir="." files="extern/args4j.jar" />
</unjar> </unjar>
<copy file="resources/icon.png" tofile="build/icon.png" overwrite="true" />
<copy file="resources/title.png" tofile="build/title.png" overwrite="true" />
<jar destfile="bin/sheepit-client.jar" <jar destfile="bin/sheepit-client.jar"
basedir="build/"> basedir="build/">
<include name="**"/> <include name="**"/>

BIN
resources/icon.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.9 KiB

BIN
resources/title.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 24 KiB

View File

@@ -93,6 +93,10 @@ public class Client {
return this.config; return this.config;
} }
public Server getServer() {
return this.server;
}
public int run() { public int run() {
if (this.config.checkOSisSupported() == false) { if (this.config.checkOSisSupported() == false) {
this.gui.error(Error.humanString(Error.Type.OS_NOT_SUPPORTED)); this.gui.error(Error.humanString(Error.Type.OS_NOT_SUPPORTED));

View File

@@ -77,10 +77,18 @@ public class Configuration {
return this.login; return this.login;
} }
public void setLogin(String login_) {
this.login = login_;
}
public String password() { public String password() {
return this.password; return this.password;
} }
public void setPassword(String password_) {
this.password = password_;
}
public int maxUploadingJob() { public int maxUploadingJob() {
return this.maxUploadingJob; return this.maxUploadingJob;
} }
@@ -165,6 +173,10 @@ public class Configuration {
} }
} }
public boolean getUserSpecifiedACacheDir() {
return this.userSpecifiedACacheDir;
}
public void setExtras(String str) { public void setExtras(String str) {
this.extras = str; this.extras = str;
} }

View File

@@ -31,4 +31,8 @@ public interface Gui {
public void AddFrameRendered(); public void AddFrameRendered();
public void framesRemaining(int nb_); public void framesRemaining(int nb_);
public void setClient(Client cli);
public Client getClient();
} }

View File

@@ -714,6 +714,41 @@ public class Server extends Thread implements HostnameVerifier, X509TrustManager
return ServerCode.UNKNOWN; return ServerCode.UNKNOWN;
} }
public byte[] getLastRender() {
try {
HttpURLConnection httpCon = this.HTTPRequest(this.getPage("last-render-frame"));
InputStream inStrm = httpCon.getInputStream();
if (httpCon.getResponseCode() != HttpURLConnection.HTTP_OK) {
this.log.debug("Server::getLastRender code not ok " + httpCon.getResponseCode());
return null;
}
int size = httpCon.getContentLength();
if (size == 0) {
this.log.debug("Server::getLastRender size is 0");
return null;
}
byte[] ret = new byte[size];
byte[] ch = new byte[512 * 1024];
int n = 0;
int i = 0;
while ((n = inStrm.read(ch)) != -1) {
System.arraycopy(ch, 0, ret, i, n);
i += n;
}
inStrm.close();
return ret;
}
catch (Exception e) {
System.err.println("Server::getLastRender exception " + e);
e.printStackTrace();
}
return null;
}
private String generateXMLForMD5cache() { private String generateXMLForMD5cache() {
String xml_str = null; String xml_str = null;
try { try {

View File

@@ -19,6 +19,7 @@
package com.sheepit.client.standalone; package com.sheepit.client.standalone;
import com.sheepit.client.Client;
import com.sheepit.client.Gui; import com.sheepit.client.Gui;
import com.sheepit.client.Log; import com.sheepit.client.Log;
@@ -63,4 +64,13 @@ public class GuiText implements Gui {
System.out.println("frame remaining: " + n_); System.out.println("frame remaining: " + n_);
} }
@Override
public void setClient(Client cli) {
}
@Override
public Client getClient() {
return null;
}
} }

View File

@@ -1,5 +1,6 @@
package com.sheepit.client.standalone; package com.sheepit.client.standalone;
import com.sheepit.client.Client;
import com.sheepit.client.Gui; import com.sheepit.client.Gui;
public class GuiTextOneLine implements Gui { public class GuiTextOneLine implements Gui {
@@ -47,6 +48,15 @@ public class GuiTextOneLine implements Gui {
updateLine(); updateLine();
} }
@Override
public void setClient(Client cli) {
}
@Override
public Client getClient() {
return null;
}
private void updateLine() { private void updateLine() {
int charToRemove = line.length(); int charToRemove = line.length();

View File

@@ -273,14 +273,20 @@ public class Worker {
} }
gui = new GuiTextOneLine(); gui = new GuiTextOneLine();
} }
else if (ui_type.equals("swing")) {
gui = new GuiSwing();
}
else { else {
gui = new GuiText(); gui = new GuiText();
} }
Client cli = new Client(gui, config, server); Client cli = new Client(gui, config, server);
gui.setClient(cli);
ShutdownHook hook = new ShutdownHook(cli); ShutdownHook hook = new ShutdownHook(cli);
hook.attachShutDownHook(); hook.attachShutDownHook();
gui.start();
cli.run(); cli.run();
cli.stop(); cli.stop();
} }

View File

@@ -0,0 +1,7 @@
package com.sheepit.client.standalone.swing.activity;
public interface Activity {
public void show();
}

View File

@@ -0,0 +1,236 @@
package com.sheepit.client.standalone.swing.activity;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.File;
import java.io.IOException;
import java.util.LinkedList;
import java.util.List;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JFileChooser;
import javax.swing.JLabel;
import javax.swing.JPasswordField;
import javax.swing.JTextField;
import com.sheepit.client.Configuration;
import com.sheepit.client.Configuration.ComputeType;
import com.sheepit.client.hardware.gpu.GPU;
import com.sheepit.client.hardware.gpu.GPUDevice;
import com.sheepit.client.standalone.GuiSwing;
public class Settings implements Activity {
private static final String DUMMY_CACHE_DIR = "Auto detected";
private GuiSwing parent;
private JTextField login;
private JPasswordField password;
private JLabel cacheDirText;
private File cacheDir;
private JFileChooser cacheDirChooser;
private JCheckBox useCPU;
private List<JCheckBox> useGPUs;
public Settings(GuiSwing parent_) {
parent = parent_;
cacheDir = null;
useGPUs = new LinkedList<JCheckBox>();
}
@Override
public void show() {
Configuration config = parent.getConfiguration();
int size_height_label = 24;
int start_label_left = 109;
int start_label_right = 265;
int end_label_right = 490;
int n = 10;
int sep = 45;
ImageIcon image = new ImageIcon(getClass().getResource("/title.png"));
JLabel labelImage = new JLabel(image);
labelImage.setBounds(600 / 2 - 265 / 2, n, 265, 130 + n);
n = labelImage.getHeight();
parent.getContentPane().add(labelImage);
n += 40;
JLabel loginLabel = new JLabel("Login:");
loginLabel.setBounds(start_label_left, n, 170, size_height_label);
parent.getContentPane().add(loginLabel);
login = new JTextField();
login.setBounds(start_label_right, n, end_label_right - start_label_right, size_height_label);
login.setText(parent.getConfiguration().login());
login.setColumns(20);
parent.getContentPane().add(login);
n += sep;
JLabel passwordLabel = new JLabel("Password:");
passwordLabel.setBounds(start_label_left, n, 170, size_height_label);
parent.getContentPane().add(passwordLabel);
password = new JPasswordField();
password.setBounds(start_label_right, n, end_label_right - start_label_right, size_height_label);
password.setText(parent.getConfiguration().password());
password.setColumns(10);
parent.getContentPane().add(password);
n += sep;
JLabel cacheLabel = new JLabel("Working directory");
cacheLabel.setBounds(start_label_left, n, 240, size_height_label);
parent.getContentPane().add(cacheLabel);
String destination = DUMMY_CACHE_DIR;
if (config.getUserSpecifiedACacheDir()) {
try {
destination = config.getStorageDir().getCanonicalPath();
}
catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
cacheDirText = new JLabel(destination);
cacheDirText.setBounds(start_label_right, n, 240, size_height_label);
parent.getContentPane().add(cacheDirText);
cacheDirChooser = new JFileChooser();
cacheDirChooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
JButton openButton = new JButton("...");
openButton.addActionListener(new ChooseFileAction());
openButton.setBounds(end_label_right - 50, n, 50, size_height_label);
parent.getContentPane().add(openButton);
n += sep;
JLabel computeMethodLabel = new JLabel("Use");
computeMethodLabel.setBounds(start_label_left, n, 240, size_height_label);
parent.getContentPane().add(computeMethodLabel);
ComputeType method = config.getComputeMethod();
useCPU = new JCheckBox("CPU");
boolean gpuChecked = false;
if (method == ComputeType.CPU_GPU) {
useCPU.setSelected(true);
gpuChecked = true;
}
else if (method == ComputeType.CPU_ONLY) {
useCPU.setSelected(true);
gpuChecked = false;
}
else if (method == ComputeType.GPU_ONLY) {
useCPU.setSelected(false);
gpuChecked = true;
}
int size = 60;
useCPU.setBounds(start_label_right, n, size, size_height_label);
parent.getContentPane().add(useCPU);
List<String> gpus = GPU.listDevices();
if (gpus != null) {
for (String model : gpus) {
n += 20;
JCheckBox gpuCheckBox = new JCheckBox(model);
gpuCheckBox.setSelected(gpuChecked);
gpuCheckBox.setBounds(start_label_right, n, 200, size_height_label);
gpuCheckBox.addActionListener(new GpuChangeAction());
parent.getContentPane().add(gpuCheckBox);
useGPUs.add(gpuCheckBox);
}
}
n += sep;
JButton saveButton = new JButton("Start");
saveButton.setBounds(start_label_right, n, 80, size_height_label);
saveButton.addActionListener(new SaveAction());
parent.getContentPane().add(saveButton);
}
class ChooseFileAction implements ActionListener {
@Override
public void actionPerformed(ActionEvent arg0) {
int returnVal = cacheDirChooser.showOpenDialog(parent.getContentPane());
if (returnVal == JFileChooser.APPROVE_OPTION) {
File file = cacheDirChooser.getSelectedFile();
cacheDir = file;
cacheDirText.setText(cacheDir.getName());
}
}
}
class GpuChangeAction implements ActionListener {
@Override
public void actionPerformed(ActionEvent e) {
for (JCheckBox box : useGPUs) {
if (box.equals(e.getSource()) == false) {
box.setSelected(false);
}
}
}
}
class SaveAction implements ActionListener {
@Override
public void actionPerformed(ActionEvent e) {
if (parent == null) {
return;
}
Configuration config = parent.getConfiguration();
if (config == null) {
return;
}
if (cacheDir != null) {
File fromConfig = config.getStorageDir();
if (fromConfig != null && fromConfig.getAbsolutePath().equals(cacheDir.getAbsolutePath()) == false) {
config.setCacheDir(cacheDir);
}
else {
System.out.println("Activity::Settings::handle do not dir since it did not change (dir: " + cacheDir + ")");
}
}
String selected_gpu = null;
for (JCheckBox box : useGPUs) {
if (box.isSelected()) {
selected_gpu = box.getText(); // model
}
}
ComputeType method = ComputeType.CPU_ONLY;
if (useCPU.isSelected() && selected_gpu == null) {
method = ComputeType.CPU_ONLY;
}
else if (useCPU.isSelected() == false && selected_gpu != null) {
method = ComputeType.GPU_ONLY;
}
else if (useCPU.isSelected() && selected_gpu != null) {
method = ComputeType.CPU_GPU;
}
config.setComputeMethod(method);
GPUDevice gpu = GPU.getGPUDevice(selected_gpu);
if (gpu != null) {
config.setUseGPU(gpu);
}
parent.setCredentials(login.getText(), new String(password.getPassword()));
}
}
}

View File

@@ -0,0 +1,154 @@
package com.sheepit.client.standalone.swing.activity;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JLabel;
import com.sheepit.client.Client;
import com.sheepit.client.Server;
import com.sheepit.client.standalone.GuiSwing;
import com.sheepit.client.standalone.GuiSwing.ActivityType;
public class Working implements Activity {
GuiSwing parent;
JLabel statusContent;
JLabel renderedFrameContent;
JLabel remainingFrameContent;
JLabel lastRender;
public Working(GuiSwing parent_) {
parent = parent_;
statusContent = new JLabel("Init");
renderedFrameContent = new JLabel("0");
remainingFrameContent = new JLabel("0");
lastRender = new JLabel();
}
@Override
public void show() {
int n = 10;
int size_height_label = 24;
int sep = 45;
int start_label_left = 109;
int start_label_right = 280;
int end_label_right = 490;
ImageIcon image = new ImageIcon(getClass().getResource("/title.png"));
JLabel labelImage = new JLabel(image);
labelImage.setBounds(600 / 2 - 265 / 2, n, 265, 130 + n);
n = labelImage.getHeight();
parent.getContentPane().add(labelImage);
n += 40;
JLabel statusLabel = new JLabel("Status:");
statusLabel.setBounds(start_label_left, n, 240, size_height_label);
parent.getContentPane().add(statusLabel);
statusContent.setBounds(start_label_right, n, end_label_right - start_label_right, size_height_label);
parent.getContentPane().add(statusContent);
n += sep;
JLabel renderedFrameLabel = new JLabel("Rendered Frame:");
renderedFrameLabel.setBounds(start_label_left, n, 240, size_height_label);
parent.getContentPane().add(renderedFrameLabel);
renderedFrameContent.setBounds(start_label_right, n, end_label_right - start_label_right, size_height_label);
parent.getContentPane().add(renderedFrameContent);
n += sep;
JLabel remainingFrameLabel = new JLabel("Remaining Frame:");
remainingFrameLabel.setBounds(start_label_left, n, 240, size_height_label);
parent.getContentPane().add(remainingFrameLabel);
remainingFrameContent.setBounds(start_label_right, n, end_label_right - start_label_right, size_height_label);
parent.getContentPane().add(remainingFrameContent);
n += sep;
JLabel lastRenderedFrameLabel = new JLabel("Last rendered frame:");
lastRenderedFrameLabel.setBounds(start_label_left, n, 240, size_height_label);
parent.getContentPane().add(lastRenderedFrameLabel);
lastRender.setBounds(start_label_right, n, 200, 112);
parent.getContentPane().add(lastRender);
JButton settingsButton = new JButton("Settings");
settingsButton.setBounds(220, 500, 100, 25);
settingsButton.addActionListener(new SettingsAction());
parent.getContentPane().add(settingsButton);
JButton pauseButton = new JButton("Pause");
pauseButton.setBounds(330, 500, 80, 25);
pauseButton.addActionListener(new PauseAction());
parent.getContentPane().add(pauseButton);
}
public void setStatus(String msg_) {
statusContent.setText(msg_);
}
public void setRemainingFrame(int n) {
remainingFrameContent.setText(String.valueOf(n));
}
public void setRenderedFrame(int n) {
renderedFrameContent.setText(String.valueOf(n));
showLastRender();
}
public void showLastRender() {
Client client = parent.getClient();
if (client != null) {
Server server = client.getServer();
if (server != null) {
byte[] data = server.getLastRender();
if (data != null) {
InputStream is = new ByteArrayInputStream(data);
try {
BufferedImage image = ImageIO.read(is);
lastRender.setIcon(new ImageIcon(image));
}
catch (IOException e) {
System.out.println("Working::showLastRender() exception " + e);
e.printStackTrace();
}
}
}
}
}
class PauseAction implements ActionListener {
@Override
public void actionPerformed(ActionEvent e) {
Client client = parent.getClient();
if (client != null) {
client.suspend();
}
}
}
class SettingsAction implements ActionListener {
@Override
public void actionPerformed(ActionEvent e) {
if (parent != null) {
parent.showActivity(ActivityType.SETTINGS);
}
}
}
}