Removed ethereumj-studio.

This commit is contained in:
Adrian Tiberius 2015-04-28 19:17:05 +02:00
parent 1d3782c3be
commit 781e23ec70
307 changed files with 0 additions and 6263 deletions

View File

@ -1,11 +0,0 @@
## ethereum-studio
To run the ethereumj-studio GUI:
- run `../gradlew run`, or
- run `../gradlew shadowJar`, followed by `java -jar build/libs/ethereumj-studio-*-all.jar`
See ethereumj-studio in action here:
[![ScreenShot](http://i.imgur.com/FQiBihl.jpg)](https://www.youtube.com/watch?v=D5ok7jh7AOg)

View File

@ -1,15 +0,0 @@
plugins {
id 'application'
id 'com.github.johnrengelman.shadow' version '1.2.0'
}
sourceCompatibility = 1.8
mainClassName = 'org.ethereum.gui.ToolBar'
dependencies {
compile project(':ethereumj-core')
compile "com.maxmind.geoip:geoip-api:1.2.11"
compile "com.maxmind.geoip2:geoip2:0.6.0"
compile "com.fifesoft:rsyntaxtextarea:2.5.0"
}

View File

@ -1,19 +0,0 @@
init:
// Setting the storage value
contract.storage[999] = 3
code:
// Using the storage on the call
a = contract.storage[999]
if a > 0:
contract.storage[999] = a - 1
// call to myself:
send((tx.gas/10 * 8), contract.address, 0)
else:
stop

View File

@ -1,34 +0,0 @@
// the sample is good example how one can
// save program that manage his own currency
init:
// this part run only on init stage
// we are about to set the maxim
// amount of currency
contract.storage[0xcd2a3d9f938e13cd947ec05abc7fe734df8dd826] = 10000000
code:
// the currency manager
// support two functions
if msg.datasize == 1:
// 1. balance check
addr = msg.data[0]
return(contract.storage[addr])
else:
// 2. balance manipulation
from = msg.sender
fromvalue = contract.storage[from]
to = msg.data[0]
value = msg.data[1]
if fromvalue >= value:
contract.storage[from] = fromvalue - value
contract.storage[to] = contract.storage[to] + value
return(1)
else:
return(0)

View File

@ -1,10 +0,0 @@
// The sample demonstrates how you
// can simply create a program running
// on top of chain and saving values for
// futre use
if !(contract.storage[msg.data[0]]):
contract.storage[msg.data[0]] = msg.data[1]
return(1)
else:
return(0)

View File

@ -1,56 +0,0 @@
package org.ethereum.geo;
import com.maxmind.geoip.Location;
import com.maxmind.geoip.LookupService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.net.InetAddress;
import java.net.URL;
/**
* @author Roman Mandeleil
* @since 24.04.14
*/
public class IpGeoDB { // change
private static Logger logger = LoggerFactory.getLogger(IpGeoDB.class);
static {
try {
File file = null;
try {
String dir = System.getProperty("user.dir");
String fileName = dir + "/config/GeoLiteCity.dat";
file = new File(fileName);
if (!file.exists()) {
URL geiIpDBFile = ClassLoader
.getSystemResource("GeoLiteCity.dat");
file = new File(geiIpDBFile.toURI());
}
} catch (Throwable th) {
logger.error(th.getMessage(), th);
System.exit(-1);
}
cl = new LookupService(file);
} catch (Throwable e) {
logger.error(e.getMessage(), e);
}
}
private static LookupService cl;
public static Location getLocationForIp(InetAddress ip) {
try {
return cl.getLocation(ip);
} catch (Throwable e) {
// TODO: think about this exception, maybe you can do something more reasonable
logger.error(e.getMessage(), e);
}
return null;
}
}

View File

@ -1,127 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.AccountState;
import org.ethereum.core.Denomination;
import org.ethereum.crypto.HashUtil;
import org.ethereum.facade.Repository;
import org.spongycastle.util.Arrays;
import org.spongycastle.util.encoders.Hex;
import java.awt.*;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import javax.swing.*;
import javax.swing.table.AbstractTableModel;
public class AccountsListWindow extends JFrame {
private JTable tblAccountsDataTable;
private AccountsDataAdapter adapter;
public AccountsListWindow() {
java.net.URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
setTitle("Accounts List");
setSize(700, 500);
setLocation(50, 180);
setResizable(false);
JPanel panel = new JPanel();
getContentPane().add(panel);
tblAccountsDataTable = new JTable();
adapter = new AccountsDataAdapter(new ArrayList<>());
tblAccountsDataTable.setModel(adapter);
JScrollPane scrollPane = new JScrollPane(tblAccountsDataTable);
scrollPane.setPreferredSize(new Dimension(680, 490));
panel.add(scrollPane);
loadAccounts();
}
private void loadAccounts() {
new Thread() {
@Override
public void run() {
Repository repository = UIEthereumManager.ethereum.getRepository();
Set<byte[]> keys = repository.getAccountsKeys();
for (byte[] key : keys) {
DataClass dc = new DataClass();
dc.address = key;
AccountState state = repository.getAccountState(dc.address);
dc.accountState = state;
adapter.addDataPiece(dc);
}
}
}.start();
}
private class AccountsDataAdapter extends AbstractTableModel {
List<DataClass> data;
final String[] columns = new String[]{"Account", "Balance", "Is Contract"};
public AccountsDataAdapter(List<DataClass> data) {
this.data = data;
}
public void addDataPiece(DataClass d) {
data.add(d);
this.fireTableRowsInserted(Math.min(data.size() - 2, 0), data.size() - 1);
}
@Override
public int getRowCount() {
return data.size();
}
@Override
public int getColumnCount() {
return 3;
}
@Override
public String getColumnName(int column) {
return columns[column];
}
@Override
public boolean isCellEditable(int row, int column) { // custom isCellEditable function
return column == 0 ? true : false;
}
@Override
public Object getValueAt(int rowIndex, int columnIndex) {
if (columnIndex == 0) {
return Hex.toHexString(data.get(rowIndex).address);
} else if (columnIndex == 1) {
if (data.get(rowIndex).accountState != null) {
return Denomination.toFriendlyString(data.get(rowIndex).accountState.getBalance());
}
return "---";
} else {
if (data.get(rowIndex).accountState != null) {
if (!Arrays.areEqual(data.get(rowIndex).accountState.getCodeHash(), HashUtil.EMPTY_DATA_HASH))
return "Yes";
}
return "No";
}
}
}
private class DataClass {
public byte[] address;
public AccountState accountState;
}
}

View File

@ -1,856 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.Block;
import org.ethereum.core.Transaction;
import org.ethereum.facade.Blockchain;
import org.ethereum.util.ByteUtil;
import org.ethereum.util.Utils;
import java.awt.*;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.StringSelection;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.util.ArrayList;
import javax.swing.*;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;
import javax.swing.text.AbstractDocument;
import javax.swing.text.AttributeSet;
import javax.swing.text.BadLocationException;
import javax.swing.text.DefaultHighlighter;
import javax.swing.text.DocumentFilter;
import javax.swing.text.Highlighter;
/**
* @author Adrian Benko
* @since 27.08.14
*/
public class BlockChainTable extends JFrame implements ActionListener {
final static int BLOCK_CHECK_INTERVAL = 1000;
final static String FONT_NAME = "Courier New";
final static int FONT_SIZE_TITLE = 20;
final static int FONT_SIZE = 13;
final static Font boldTitle = new Font(FONT_NAME, Font.BOLD, FONT_SIZE_TITLE);
final static Font bold = new Font(FONT_NAME, Font.BOLD, FONT_SIZE);
final static Font plain = new Font(FONT_NAME, Font.PLAIN, FONT_SIZE);
final static Color HILIT_COLOR = Color.LIGHT_GRAY;
class MyDocumentFilter extends DocumentFilter {
@Override
public void insertString(FilterBypass fb, int off
, String str, AttributeSet attr)
throws BadLocationException {
// remove non-digits
fb.insertString(off, str.replaceAll("\\D++", ""), attr);
}
@Override
public void replace(FilterBypass fb, int off
, int len, String str, AttributeSet attr)
throws BadLocationException {
// remove non-digits
fb.replace(off, len, str.replaceAll("\\D++", ""), attr);
}
}
private volatile boolean running;
private TransactionData transactionDataWindow = null;
private JPanel topPanel;
private JPanel titlePanel;
private JPanel blockPanel;
private JPanel transactionsPanel;
private JScrollPane scrollPane;
JTextField blockNumberText;
JButton firstBlock;
JButton prevBlock;
JButton nextBlock;
JButton lastBlock;
JLabel blocksCount;
JTextField findText;
JButton findPrev;
JButton findNext;
JTextField blockN;
JTextField minGasPrice;
JTextField gasLimit;
JTextField gasUsed;
JTextField timestamp;
JTextField difficulty;
JTextField hash;
JTextField parentHash;
JTextField uncleHash;
JTextField stateRoot;
JTextField trieRoot;
JTextField coinbase;
JTextField nonce;
JTextField extraData;
Thread t;
private int lastFindIndex = -1;
private String textToFind = "";
private java.util.List<Long> foundBlocks;
final Highlighter.HighlightPainter painter;
ToolBar toolBar;
public BlockChainTable(ToolBar toolBar) {
this.toolBar = toolBar;
addCloseAction();
foundBlocks = new ArrayList<>();
painter = new DefaultHighlighter.DefaultHighlightPainter(HILIT_COLOR);
setTitle("Block Chain Table");
setSize(900, 400);
setLocation(315, 270);
setBackground(Color.gray);
java.net.URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
// Create a panel to hold all other components
topPanel = new JPanel();
topPanel.setLayout(new BoxLayout(topPanel, BoxLayout.PAGE_AXIS));
getContentPane().add(topPanel, BorderLayout.LINE_START);
titlePanel = new JPanel(new FlowLayout());
titlePanel.setMaximumSize(new Dimension(Short.MAX_VALUE, 50));
createTitlePanel(this);
blockPanel = new JPanel(new GridBagLayout());
blockPanel.setMaximumSize(new Dimension(Short.MAX_VALUE, 160));
createBlockPanel();
transactionsPanel = new JPanel(new GridBagLayout());
scrollPane = new JScrollPane(transactionsPanel);
scrollPane.setBorder(BorderFactory.createEmptyBorder());
scrollPane.setAlignmentX(0);
fillBlock(this);
titlePanel.setAlignmentX(0);
topPanel.add(titlePanel);
blockPanel.setAlignmentX(0);
topPanel.add(blockPanel);
JLabel transactionsLabel = new JLabel("Transactions ");
transactionsLabel.setFont(bold);
transactionsLabel.setAlignmentX(0);
transactionsLabel.setBorder(BorderFactory.createEmptyBorder(0, 10, 0, 0));
topPanel.add(transactionsLabel);
topPanel.add(scrollPane);
topPanel.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_C, KeyEvent.CTRL_DOWN_MASK), "Copy");
topPanel.getActionMap().put("Copy", new AbstractAction() {
@Override
public void actionPerformed(ActionEvent e) {
if (UIEthereumManager.ethereum.getBlockchain().getSize() - 1 < lastFindIndex) return;
Block block = UIEthereumManager.ethereum.getBlockchain().getBlockByNumber(lastFindIndex);
StringSelection selection = new StringSelection(block.toString());
Clipboard system = Toolkit.getDefaultToolkit().getSystemClipboard();
system.setContents(selection, selection);
}
});
t = new Thread() {
public void run() {
running = true;
while (running) {
blocksCount.setText("" + UIEthereumManager.ethereum.getBlockchain().getSize());
try {
sleep(BLOCK_CHECK_INTERVAL);
} catch (InterruptedException e) {
}
}
}
};
t.start();
}
public void actionPerformed(ActionEvent e) {
long blockNum = Long.parseLong(blockNumberText.getText());
if ("firstBlock".equals(e.getActionCommand())) {
blockNum = 0;
} else if ("prevBlock".equals(e.getActionCommand())) {
if (blockNum > 0) {
blockNum--;
}
} else if ("nextBlock".equals(e.getActionCommand())) {
if (blockNum < UIEthereumManager.ethereum.getBlockchain().getSize() - 1) {
blockNum++;
}
} else if ("lastBlock".equals(e.getActionCommand())) {
blockNum = UIEthereumManager.ethereum.getBlockchain().getSize() - 1;
} else if ("findPrev".equals(e.getActionCommand())) {
if (findText.getText().length() > 0) {
if (textToFind.equals(findText.getText())) {
if (lastFindIndex > 0) {
blockNum = foundBlocks.get(lastFindIndex - 1);
lastFindIndex--;
} else {
blockNum = findBlock(textToFind, blockNum, false);
}
} else {
textToFind = findText.getText();
lastFindIndex = -1;
foundBlocks.clear();
blockNum = findBlock(textToFind, blockNum, false);
}
}
} else if ("findNext".equals(e.getActionCommand())) {
if (findText.getText().length() > 0) {
if (textToFind.equals(findText.getText())) {
if (lastFindIndex > -1 && foundBlocks.size() > lastFindIndex + 1) {
blockNum = foundBlocks.get(lastFindIndex + 1);
lastFindIndex++;
} else {
blockNum = findBlock(textToFind, blockNum, true);
}
} else {
textToFind = findText.getText();
lastFindIndex = -1;
foundBlocks.clear();
blockNum = findBlock(textToFind, blockNum, true);
}
}
}
blockNumberText.setText("" + blockNum);
fillBlock(this);
}
private long findBlock(String textToFind, long blockNum, boolean forward) {
if (forward) {
for (long i = blockNum + 1; i < UIEthereumManager.ethereum.getBlockchain().getSize(); i++) {
Block block = UIEthereumManager.ethereum.getBlockchain().getBlockByNumber(i);
if (block.toString().toLowerCase().contains(textToFind.toLowerCase())) {
foundBlocks.add(i);
lastFindIndex = foundBlocks.size() - 1;
break;
}
}
} else {
for (long i = blockNum - 1; i >= 0; i--) {
Block block = UIEthereumManager.ethereum.getBlockchain().getBlockByNumber(i);
if (block.toString().toLowerCase().contains(textToFind.toLowerCase())) {
foundBlocks.add(0, i);
lastFindIndex = 0;
break;
}
}
}
return foundBlocks.get(lastFindIndex);
}
public void terminate() {
running = false;
}
public void addCloseAction() {
this.addWindowListener(new WindowAdapter() {
@Override
public void windowClosing(WindowEvent e) {
toolBar.chainToggle.setSelected(false);
if (transactionDataWindow != null) {
transactionDataWindow.setVisible(false);
}
}
});
}
public static void main(String args[]) {
BlockChainTable mainFrame = new BlockChainTable(null);
mainFrame.setVisible(true);
mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
private void createTitlePanel(final BlockChainTable blockchainTable) {
GridBagConstraints c = new GridBagConstraints();
c.fill = GridBagConstraints.HORIZONTAL;
JLabel blockNumberLabel = new JLabel("Block #");
blockNumberLabel.setFont(boldTitle);
c.gridx = 0;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 10, 0, 0);
titlePanel.add(blockNumberLabel, c);
blockNumberText = new JTextField("0", 7);
((AbstractDocument) blockNumberText.getDocument()).setDocumentFilter(
new MyDocumentFilter());
// Listen for changes in the text
blockNumberText.getDocument().addDocumentListener(new DocumentListener() {
public void changedUpdate(DocumentEvent e) {
fillBlock(blockchainTable);
}
public void removeUpdate(DocumentEvent e) {
fillBlock(blockchainTable);
}
public void insertUpdate(DocumentEvent e) {
fillBlock(blockchainTable);
}
});
blockNumberText.setFont(boldTitle);
c.gridx = 1;
c.gridy = 0;
c.weightx = 1.0;
c.insets = new Insets(0, 0, 0, 10);
titlePanel.add(blockNumberText, c);
firstBlock = new JButton("|<");
firstBlock.setFont(plain);
firstBlock.setActionCommand("firstBlock");
firstBlock.addActionListener(this);
c.gridx = 2;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 0, 0, 0);
titlePanel.add(firstBlock, c);
prevBlock = new JButton("<");
prevBlock.setFont(plain);
prevBlock.setActionCommand("prevBlock");
prevBlock.addActionListener(this);
c.gridx = 3;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 0, 0, 0);
titlePanel.add(prevBlock, c);
nextBlock = new JButton(">");
nextBlock.setFont(plain);
nextBlock.setActionCommand("nextBlock");
nextBlock.addActionListener(this);
c.gridx = 4;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 0, 0, 0);
titlePanel.add(nextBlock, c);
lastBlock = new JButton(">|");
lastBlock.setFont(plain);
lastBlock.setActionCommand("lastBlock");
lastBlock.addActionListener(this);
c.gridx = 5;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 0, 0, 0);
titlePanel.add(lastBlock, c);
JLabel blocksCountLabel = new JLabel("Total blocks: ");
blocksCountLabel.setFont(plain);
c.gridx = 6;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 10, 0, 0);
titlePanel.add(blocksCountLabel, c);
blocksCount = new JLabel();
blocksCount.setFont(plain);
c.gridx = 7;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 0, 0, 0);
titlePanel.add(blocksCount, c);
JLabel findLabel = new JLabel("Find ");
findLabel.setFont(plain);
c.gridx = 8;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 10, 0, 0);
titlePanel.add(findLabel, c);
findText = new JTextField(12);
findText.setFont(plain);
c.gridx = 9;
c.gridy = 0;
c.weightx = 3.0;
c.insets = new Insets(0, 0, 0, 0);
titlePanel.add(findText, c);
findPrev = new JButton("<");
findPrev.setFont(plain);
findPrev.setActionCommand("findPrev");
findPrev.addActionListener(this);
c.gridx = 10;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 10, 0, 0);
titlePanel.add(findPrev, c);
findNext = new JButton(">");
findNext.setFont(plain);
findNext.setActionCommand("findNext");
findNext.addActionListener(this);
c.gridx = 11;
c.gridy = 0;
c.weightx = 0.0;
c.insets = new Insets(0, 0, 0, 10);
titlePanel.add(findNext, c);
}
private void createBlockPanel() {
GridBagConstraints c = new GridBagConstraints();
c.fill = GridBagConstraints.HORIZONTAL;
JLabel summaryLabel = new JLabel("Summary ");
summaryLabel.setFont(bold);
c.gridx = 0;
c.gridy = 1;
c.insets = new Insets(0, 10, 0, 0);
blockPanel.add(summaryLabel, c);
JLabel blocknLabel = new JLabel("Block#");
blocknLabel.setFont(plain);
c.weightx = 1.0;
c.gridx = 0;
c.gridy = 2;
blockPanel.add(blocknLabel, c);
blockN = new JTextField();
blockN.setEditable(false);
blockN.setBorder(null);
blockN.setFont(plain);
c.gridx = 1;
c.gridy = 2;
blockPanel.add(blockN, c);
JLabel minGasPriceLabel = new JLabel("Min gas price");
minGasPriceLabel.setFont(plain);
c.weightx = 1.0;
c.gridx = 0;
c.gridy = 3;
blockPanel.add(minGasPriceLabel, c);
minGasPrice = new JTextField();
minGasPrice.setEditable(false);
minGasPrice.setBorder(null);
minGasPrice.setFont(plain);
c.gridx = 1;
c.gridy = 3;
blockPanel.add(minGasPrice, c);
JLabel gasLimitLabel = new JLabel("Gas limit");
gasLimitLabel.setFont(plain);
c.gridx = 0;
c.gridy = 4;
blockPanel.add(gasLimitLabel, c);
gasLimit = new JTextField();
gasLimit.setEditable(false);
gasLimit.setBorder(null);
gasLimit.setFont(plain);
c.gridx = 1;
c.gridy = 4;
blockPanel.add(gasLimit, c);
JLabel gasUsedLabel = new JLabel("Gas used");
gasUsedLabel.setFont(plain);
c.gridx = 0;
c.gridy = 5;
blockPanel.add(gasUsedLabel, c);
gasUsed = new JTextField();
gasUsed.setEditable(false);
gasUsed.setBorder(null);
gasUsed.setFont(plain);
c.gridx = 1;
c.gridy = 5;
blockPanel.add(gasUsed, c);
JLabel timestampLabel = new JLabel("Timestamp");
timestampLabel.setFont(plain);
c.gridx = 0;
c.gridy = 6;
blockPanel.add(timestampLabel, c);
timestamp = new JTextField();
timestamp.setEditable(false);
timestamp.setBorder(null);
timestamp.setFont(plain);
c.gridx = 1;
c.gridy = 6;
blockPanel.add(timestamp, c);
JLabel difficultyLabel = new JLabel("Difficulty");
difficultyLabel.setFont(plain);
c.gridx = 0;
c.gridy = 7;
blockPanel.add(difficultyLabel, c);
difficulty = new JTextField();
difficulty.setEditable(false);
difficulty.setBorder(null);
difficulty.setFont(plain);
c.gridx = 1;
c.gridy = 7;
blockPanel.add(difficulty, c);
JLabel extraDataLabel = new JLabel("Extra data");
extraDataLabel.setFont(plain);
c.gridx = 0;
c.gridy = 9;
blockPanel.add(extraDataLabel, c);
extraData = new JTextField();
extraData.setEditable(false);
extraData.setBorder(null);
extraData.setFont(plain);
c.ipady = 1;
c.ipadx = 1;
c.gridx = 1;
c.gridy = 9;
c.gridwidth = GridBagConstraints.REMAINDER;
blockPanel.add(extraData, c);
JLabel hashesLabel = new JLabel("Hashes ");
hashesLabel.setFont(bold);
c.gridx = 3;
c.gridy = 1;
c.gridwidth = 1;
blockPanel.add(hashesLabel, c);
JLabel hashLabel = new JLabel("Hash");
hashLabel.setFont(plain);
c.gridx = 3;
c.gridy = 2;
blockPanel.add(hashLabel, c);
hash = new JTextField();
hash.setEditable(false);
hash.setBorder(null);
hash.setFont(plain);
c.weightx = 3.0;
c.gridx = 4;
c.gridy = 2;
blockPanel.add(hash, c);
JLabel parentHashLabel = new JLabel("Parent hash");
parentHashLabel.setFont(plain);
c.weightx = 1.0;
c.gridx = 3;
c.gridy = 3;
blockPanel.add(parentHashLabel, c);
parentHash = new JTextField();
parentHash.setEditable(false);
parentHash.setBorder(null);
parentHash.setFont(plain);
c.gridx = 4;
c.gridy = 3;
blockPanel.add(parentHash, c);
JLabel uncleHashLabel = new JLabel("Uncle hash");
uncleHashLabel.setFont(plain);
c.gridx = 3;
c.gridy = 4;
blockPanel.add(uncleHashLabel, c);
uncleHash = new JTextField();
uncleHash.setEditable(false);
uncleHash.setBorder(null);
uncleHash.setFont(plain);
c.gridx = 4;
c.gridy = 4;
blockPanel.add(uncleHash, c);
JLabel stateRootLabel = new JLabel("State root");
stateRootLabel.setFont(plain);
c.weightx = 1.0;
c.gridx = 3;
c.gridy = 5;
blockPanel.add(stateRootLabel, c);
stateRoot = new JTextField();
stateRoot.setEditable(false);
stateRoot.setBorder(null);
stateRoot.setFont(plain);
c.gridx = 4;
c.gridy = 5;
blockPanel.add(stateRoot, c);
JLabel trieRootLabel = new JLabel("Trie root");
trieRootLabel.setFont(plain);
c.gridx = 3;
c.gridy = 6;
blockPanel.add(trieRootLabel, c);
trieRoot = new JTextField();
trieRoot.setEditable(false);
trieRoot.setBorder(null);
trieRoot.setFont(plain);
c.gridx = 4;
c.gridy = 6;
blockPanel.add(trieRoot, c);
JLabel coinbaseLabel = new JLabel("Coinbase");
coinbaseLabel.setFont(plain);
c.gridx = 3;
c.gridy = 7;
blockPanel.add(coinbaseLabel, c);
coinbase = new JTextField();
coinbase.setEditable(false);
coinbase.setBorder(null);
coinbase.setFont(plain);
c.gridx = 4;
c.gridy = 7;
blockPanel.add(coinbase, c);
JLabel nonceLabel = new JLabel("Nonce");
nonceLabel.setFont(plain);
c.gridx = 3;
c.gridy = 8;
blockPanel.add(nonceLabel, c);
nonce = new JTextField();
nonce.setEditable(false);
nonce.setBorder(null);
nonce.setFont(plain);
c.gridx = 4;
c.gridy = 8;
blockPanel.add(nonce, c);
}
private void fillBlock(final BlockChainTable blockchainTable) {
if (blockNumberText.getText().length() == 0) return;
Blockchain blockchain = UIEthereumManager.ethereum.getBlockchain();
long blockNum = Long.parseLong(blockNumberText.getText());
if (blockNum > blockchain.getSize() - 1) {
blockNum = blockchain.getSize() - 1;
}
Block block = blockchain.getBlockByNumber(blockNum);
blockN.setText("" + block.getNumber());
highlightText(blockN);
minGasPrice.setText("" + 42);
highlightText(minGasPrice);
gasLimit.setText("" + block.getGasLimit());
highlightText(gasLimit);
gasUsed.setText("" + block.getGasUsed());
highlightText(gasUsed);
timestamp.setText(Utils.longToDateTime(block.getTimestamp()));
highlightText(timestamp);
difficulty.setText(ByteUtil.toHexString(block.getDifficulty()));
highlightText(difficulty);
hash.setText(ByteUtil.toHexString(block.getHash()));
highlightText(hash);
parentHash.setText(ByteUtil.toHexString(block.getParentHash()));
highlightText(parentHash);
uncleHash.setText(ByteUtil.toHexString(block.getUnclesHash()));
highlightText(uncleHash);
stateRoot.setText(ByteUtil.toHexString(block.getStateRoot()));
highlightText(stateRoot);
trieRoot.setText(ByteUtil.toHexString(block.getTxTrieRoot()));
highlightText(trieRoot);
coinbase.setText(ByteUtil.toHexString(block.getCoinbase()));
highlightText(coinbase);
nonce.setText(ByteUtil.toHexString(block.getNonce()));
highlightText(nonce);
if (block.getExtraData() != null) {
extraData.setText(ByteUtil.toHexString(block.getExtraData()));
highlightText(extraData);
}
GridBagConstraints c = new GridBagConstraints();
c.fill = GridBagConstraints.HORIZONTAL;
transactionsPanel.removeAll();
int row = 1;
for (Transaction transaction : block.getTransactionsList()) {
JPanel transactionPanel = createTransactionPanel(blockchainTable, transaction);
c.gridx = 0;
c.gridy = row;
c.weighty = 1;
c.weightx = 1;
c.anchor = GridBagConstraints.NORTHWEST;
c.insets = new Insets(10, 10, 0, 10);
transactionsPanel.add(transactionPanel, c);
row++;
}
transactionsPanel.repaint();
scrollPane.revalidate();
}
private JPanel createTransactionPanel(final BlockChainTable blockchainTable, final Transaction transaction) {
GridBagConstraints c = new GridBagConstraints();
c.fill = GridBagConstraints.HORIZONTAL;
JPanel transactionPanel = new JPanel(new GridBagLayout());
transactionPanel.setBorder(BorderFactory.createLineBorder(Color.black));
JLabel senderLabel = new JLabel("Sender");
senderLabel.setFont(plain);
c.gridx = 0;
c.gridy = 0;
c.insets = new Insets(10, 0, 0, 0);
transactionPanel.add(senderLabel, c);
JTextField sender = new JTextField(ByteUtil.toHexString(transaction.getSender()));
highlightText(sender);
sender.setEditable(false);
sender.setBorder(null);
sender.setFont(plain);
c.gridx = 1;
c.gridy = 0;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(sender, c);
JLabel gasPriceLabel = new JLabel("Gas price");
gasPriceLabel.setFont(plain);
c.gridx = 2;
c.gridy = 0;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(gasPriceLabel, c);
JTextField gasPrice = new JTextField(ByteUtil.toHexString(transaction.getGasPrice()));
highlightText(gasPrice);
gasPrice.setEditable(false);
gasPrice.setBorder(null);
gasPrice.setFont(plain);
c.gridx = 3;
c.gridy = 0;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(gasPrice, c);
JLabel receiveAddressLabel = new JLabel("Receive address");
receiveAddressLabel.setFont(plain);
c.gridx = 0;
c.gridy = 1;
c.insets = new Insets(0, 0, 0, 0);
transactionPanel.add(receiveAddressLabel, c);
JTextField receiveAddress = new JTextField(ByteUtil.toHexString(transaction.getReceiveAddress()));
highlightText(receiveAddress);
receiveAddress.setEditable(false);
receiveAddress.setBorder(null);
receiveAddress.setFont(plain);
c.gridx = 1;
c.gridy = 1;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(receiveAddress, c);
JLabel gasLimitLabel = new JLabel("Gas limit");
gasLimitLabel.setFont(plain);
c.gridx = 2;
c.gridy = 1;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(gasLimitLabel, c);
JTextField gasLimit = new JTextField(ByteUtil.toHexString(transaction.getGasLimit()));
highlightText(gasLimit);
gasLimit.setEditable(false);
gasLimit.setBorder(null);
gasLimit.setFont(plain);
c.gridx = 3;
c.gridy = 1;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(gasLimit, c);
JLabel hashLabel = new JLabel("Hash");
hashLabel.setFont(plain);
c.gridx = 0;
c.gridy = 2;
c.insets = new Insets(0, 0, 0, 0);
transactionPanel.add(hashLabel, c);
JTextField hash = new JTextField(ByteUtil.toHexString(transaction.getHash()));
highlightText(hash);
hash.setEditable(false);
hash.setBorder(null);
hash.setFont(plain);
c.gridx = 1;
c.gridy = 2;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(hash, c);
JLabel valueLabel = new JLabel("Value");
valueLabel.setFont(plain);
c.gridx = 2;
c.gridy = 2;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(valueLabel, c);
JTextField value = new JTextField(transaction.getValue() != null ? ByteUtil.toHexString(transaction.getValue
()) : "");
highlightText(value);
value.setEditable(false);
value.setBorder(null);
value.setFont(plain);
c.gridx = 3;
c.gridy = 2;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(value, c);
JLabel nonceLabel = new JLabel("Nonce");
nonceLabel.setFont(plain);
c.gridx = 0;
c.gridy = 3;
c.insets = new Insets(0, 0, 0, 0);
transactionPanel.add(nonceLabel, c);
JTextField nonce = new JTextField(ByteUtil.toHexString(transaction.getNonce()));
highlightText(nonce);
nonce.setEditable(false);
nonce.setBorder(null);
nonce.setFont(plain);
c.gridx = 1;
c.gridy = 3;
c.insets = new Insets(0, 10, 0, 0);
transactionPanel.add(nonce, c);
JButton data = new JButton("Data");
data.addActionListener(event -> {
if (transactionDataWindow == null)
transactionDataWindow = new TransactionData(blockchainTable);
transactionDataWindow.setData(transaction.getData());
transactionDataWindow.setVisible(true);
transactionDataWindow.highlightText(findText.getText(), painter);
});
data.setFont(plain);
if (findText.getText().length() > 0 && ByteUtil.toHexString(transaction.getData()).contains(findText.getText
())) {
data.setBackground(HILIT_COLOR);
}
c.gridx = 3;
c.gridy = 3;
c.insets = new Insets(0, 0, 10, 0);
transactionPanel.add(data, c);
return transactionPanel;
}
private void highlightText(JTextField textField) {
if (findText.getText().length() > 0 && textField.getText().contains(findText.getText())) {
try {
int end = textField.getText().indexOf(findText.getText()) + findText.getText().length();
textField.getHighlighter().addHighlight(textField.getText().indexOf(findText.getText()), end, painter);
} catch (BadLocationException e) {
}
}
}
}

View File

@ -1,156 +0,0 @@
package org.ethereum.gui;
import org.ethereum.config.SystemProperties;
import org.ethereum.listener.EthereumListenerAdapter;
import org.fife.ui.rsyntaxtextarea.AbstractTokenMakerFactory;
import org.fife.ui.rsyntaxtextarea.RSyntaxTextArea;
import org.fife.ui.rsyntaxtextarea.SyntaxScheme;
import org.fife.ui.rsyntaxtextarea.Token;
import org.fife.ui.rsyntaxtextarea.TokenMakerFactory;
import org.fife.ui.rtextarea.RTextScrollPane;
import java.awt.*;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import javax.swing.*;
import static org.ethereum.config.SystemProperties.CONFIG;
/**
* A simple example showing how to modify the fonts and colors used in an
* RSyntaxTextArea. There are two methods to do this - via the Java API, and via
* an XML file. The latter method is preferred since it's more modular, and
* provides a way for your users to customize RSTA in your application.<p>
*
* This example uses RSyntaxTextArea 2.0.1.<p>
*
* Project Home: http://fifesoft.com/rsyntaxtextarea<br>
* Downloads: https://sourceforge.net/projects/rsyntaxtextarea
*/
public class ConnectionConsoleWindow extends JFrame {
private static final long serialVersionUID = 1L;
private boolean autoScroll = false;
private RSyntaxTextArea textArea;
private ToolBar toolBar = null;
/**
* ERROR (exceptions) WARN (when something happens that's not supposed to)
* INFO (wire output)
* DEBUG (test/displaying intermediate values),
* TRACE (start/end method)
*/
public ConnectionConsoleWindow(ToolBar toolBar) {
final ConnectionConsoleWindow thisConsole = this;
this.toolBar = toolBar;
java.net.URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
addCloseAction();
JPanel cp = new JPanel(new BorderLayout());
AbstractTokenMakerFactory atmf = (AbstractTokenMakerFactory) TokenMakerFactory.getDefaultInstance();
atmf.putMapping("text/console", "org.ethereum.gui.ConsoleTokenMaker");
textArea = new RSyntaxTextArea(16, 44);
textArea.setSyntaxEditingStyle("text/console");
// textArea.setSyntaxEditingStyle(SyntaxConstants.SYNTAX_STYLE_LISP);
textArea.setCodeFoldingEnabled(true);
textArea.setAntiAliasingEnabled(true);
changeStyleProgrammatically();
RTextScrollPane sp = new RTextScrollPane(textArea);
cp.add(sp);
setContentPane(cp);
setTitle("Connection Console");
// setDefaultCloseOperation(EXIT_ON_CLOSE);
pack();
setLocation(802, 460);
if (CONFIG.peerDiscovery())
UIEthereumManager.ethereum.startPeerDiscovery();
Thread t = new Thread() {
public void run() {
UIEthereumManager.ethereum.connect(SystemProperties.CONFIG.activePeerIP(),
SystemProperties.CONFIG.activePeerPort());
}
};
UIEthereumManager.ethereum.addListener(new EthereumListenerAdapter() {
@Override
public void trace(final String output) {
SwingUtilities.invokeLater(() -> {
textArea.append(output);
textArea.append("\n");
if (autoScroll)
textArea.setCaretPosition(textArea.getText().length());
});
}
});
t.start();
}
private void changeStyleProgrammatically() {
// Set the font for all token types.
setFont(textArea, new Font("Courier New", Font.PLAIN, 12));
// Change a few things here and there.
SyntaxScheme scheme = textArea.getSyntaxScheme();
scheme.getStyle(Token.RESERVED_WORD).background = Color.white;
scheme.getStyle(Token.RESERVED_WORD).foreground = Color.MAGENTA.darker().darker();
scheme.getStyle(Token.DATA_TYPE).foreground = Color.blue;
scheme.getStyle(Token.LITERAL_STRING_DOUBLE_QUOTE).underline = true;
scheme.getStyle(Token.LITERAL_NUMBER_HEXADECIMAL).underline = true;
scheme.getStyle(Token.LITERAL_NUMBER_HEXADECIMAL).background = Color.pink;
scheme.getStyle(Token.COMMENT_EOL).font = new Font("Georgia",
Font.ITALIC, 10);
textArea.revalidate();
}
public static void setFont(RSyntaxTextArea textArea, Font font) {
if (font != null) {
SyntaxScheme ss = textArea.getSyntaxScheme();
ss = (SyntaxScheme) ss.clone();
for (int i = 0; i < ss.getStyleCount(); i++) {
if (ss.getStyle(i) != null) {
ss.getStyle(i).font = font;
}
}
textArea.setSyntaxScheme(ss);
textArea.setFont(font);
}
}
public void addCloseAction() {
this.addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
toolBar.logToggle.setSelected(false);
}
});
}
public static void main(String[] args) {
// Start all Swing applications on the EDT.
SwingUtilities.invokeLater(() -> new ConnectionConsoleWindow(null).setVisible(true));
}
}

View File

@ -1,959 +0,0 @@
package org.ethereum.gui;
import org.fife.ui.rsyntaxtextarea.AbstractTokenMaker;
import org.fife.ui.rsyntaxtextarea.RSyntaxUtilities;
import org.fife.ui.rsyntaxtextarea.Token;
import org.fife.ui.rsyntaxtextarea.TokenMap;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.swing.text.Segment;
/**
* @author Roman Mandeleil
* @since 24.04.14
*/
public class ConsoleTokenMaker extends AbstractTokenMaker {
private Logger logger = LoggerFactory.getLogger("gui");
protected final String operators = "+-*/%!=<>^&|?:";
protected final String separators = "()[]{}";
protected final String separators2 = ".,;"; // Characters you don't want syntax highlighted but separate identifiers.
protected final String hexCharacters = "0123456789ABCDEFabcdef";
protected final String numberEndChars = "FfLl"; // Characters used to specify literal number types.
private int currentTokenStart;
private int currentTokenType;
/**
* Constructor.
*/
public ConsoleTokenMaker() {
super(); // Initializes tokensToHighlight.
}
/**
* Checks the token to give it the exact ID it deserves before
* being passed up to the super method.
*
* @param segment <code>Segment</code> to get text from.
* @param start Start offset in <code>segment</code> of token.
* @param end End offset in <code>segment</code> of token.
* @param tokenType The token's type.
* @param startOffset The offset in the document at which the token occurs.
*/
public void addToken(Segment segment, int start, int end, int tokenType, int startOffset) {
switch (tokenType) {
// Since reserved words, functions, and data types are all passed
// into here as "identifiers," we have to see what the token
// really is...
case Token.IDENTIFIER:
int value = wordsToHighlight.get(segment, start, end);
if (value != -1)
tokenType = value;
break;
case Token.WHITESPACE:
case Token.SEPARATOR:
case Token.OPERATOR:
case Token.ERROR_IDENTIFIER:
case Token.ERROR_NUMBER_FORMAT:
case Token.ERROR_STRING_DOUBLE:
case Token.ERROR_CHAR:
case Token.COMMENT_EOL:
case Token.COMMENT_MULTILINE:
case Token.LITERAL_BOOLEAN:
case Token.LITERAL_NUMBER_DECIMAL_INT:
case Token.LITERAL_NUMBER_FLOAT:
case Token.LITERAL_NUMBER_HEXADECIMAL:
break;
case Token.LITERAL_STRING_DOUBLE_QUOTE:
case Token.LITERAL_CHAR:
break;
default:
logger.error("Unknown tokenType: '" + tokenType + "'");
tokenType = Token.IDENTIFIER;
break;
}
super.addToken(segment, start, end, tokenType, startOffset);
}
/**
* Returns the text to place at the beginning and end of a
* line to "comment" it in a this programming language.
*
* @return The start and end strings to add to a line to "comment"
* it out.
*/
public String[] getLineCommentStartAndEnd() {
return new String[]{"//", null};
}
/**
* Returns the words to highlight for the JavaScript programming language.
*
* @return A <code>TokenMap</code> containing the words to highlight for
* the JavaScript programming language.
* @see org.fife.ui.rsyntaxtextarea.AbstractTokenMaker#getWordsToHighlight
*/
public TokenMap getWordsToHighlight() {
TokenMap tokenMap = new TokenMap(52);
int reservedWord = Token.RESERVED_WORD;
tokenMap.put("connecting", reservedWord);
int literalBoolean = Token.LITERAL_BOOLEAN;
tokenMap.put("false", literalBoolean);
tokenMap.put("true", literalBoolean);
int dataType = Token.DATA_TYPE;
tokenMap.put("boolean", dataType);
return tokenMap;
}
/**
* Returns <code>true</code> always as JavaScript uses curly braces
* to denote code blocks.
*
* @return <code>true</code> always.
*/
public boolean getCurlyBracesDenoteCodeBlocks() {
return true;
}
/**
* Returns the first token in the linked list of tokens generated
* from <code>text</code>. This method must be implemented by
* subclasses so they can correctly implement syntax highlighting.
*
* @param text The text from which to get tokens.
* @param initialTokenType The token type we should start with.
* @param startOffset The offset into the document at which
* <code>text</code> starts.
* @return The first <code>Token</code> in a linked list representing
* the syntax highlighted text.
*/
public Token getTokenList(Segment text, int initialTokenType,
int startOffset) {
resetTokenList();
char[] array = text.array;
int offset = text.offset;
int count = text.count;
int end = offset + count;
// See, when we find a token, its starting position is always of the
// form: 'startOffset + (currentTokenStart-offset)'; but since
// startOffset and offset are constant, tokens' starting positions
// become: 'newStartOffset+currentTokenStart' for one less subtraction
// operation.
int newStartOffset = startOffset - offset;
currentTokenStart = offset;
currentTokenType = initialTokenType;
boolean backslash = false;
boolean numContainsExponent = false;
boolean numContainsEndCharacter = false;
for (int i = offset; i < end; i++) {
char c = array[i];
switch (currentTokenType) {
case Token.NULL:
currentTokenStart = i; // Starting a new token here.
switch (c) {
case ' ':
case '\t':
currentTokenType = Token.WHITESPACE;
break;
case '"':
if (backslash) { // Escaped double quote => call '"' an identifier..
addToken(text, currentTokenStart, i, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
backslash = false;
} else {
currentTokenType = Token.ERROR_STRING_DOUBLE;
}
break;
case '\'':
if (backslash) { // Escaped single quote => call '\'' an identifier.
addToken(text, currentTokenStart, i, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
backslash = false;
} else {
currentTokenType = Token.ERROR_CHAR;
}
break;
case '\\':
addToken(text, currentTokenStart, i, Token.IDENTIFIER, newStartOffset + currentTokenStart);
currentTokenType = Token.NULL;
backslash = !backslash;
break;
default:
if (RSyntaxUtilities.isDigit(c)) {
currentTokenType = Token.LITERAL_NUMBER_DECIMAL_INT;
break;
} else if (RSyntaxUtilities.isLetter(c) || c == '_') {
currentTokenType = Token.IDENTIFIER;
break;
}
int indexOf = operators.indexOf(c, 0);
if (indexOf > -1) {
currentTokenStart = i;
currentTokenType = Token.OPERATOR;
break;
}
indexOf = separators.indexOf(c, 0);
if (indexOf > -1) {
addToken(text, currentTokenStart, i, Token.SEPARATOR, newStartOffset +
currentTokenStart);
currentTokenType = Token.NULL;
break;
}
indexOf = separators2.indexOf(c, 0);
if (indexOf > -1) {
addToken(text, currentTokenStart, i, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenType = Token.NULL;
break;
} else {
currentTokenType = Token.ERROR_IDENTIFIER;
break;
}
} // End of switch (c).
break;
case Token.WHITESPACE:
switch (c) {
case ' ':
case '\t':
break; // Still whitespace.
case '\\':
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
backslash = true; // Previous char whitespace => this must be first backslash.
break;
case '"': // Don't need to worry about backslashes as previous char is space.
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
backslash = false;
break;
case '\'': // Don't need to worry about backslashes as previous char is space.
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_CHAR;
backslash = false;
break;
default: // Add the whitespace token and start anew.
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
currentTokenStart = i;
if (RSyntaxUtilities.isDigit(c)) {
currentTokenType = Token.LITERAL_NUMBER_DECIMAL_INT;
break;
} else if (RSyntaxUtilities.isLetter(c) || c == '_') {
currentTokenType = Token.IDENTIFIER;
break;
}
int indexOf = operators.indexOf(c, 0);
if (indexOf > -1) {
currentTokenStart = i;
currentTokenType = Token.OPERATOR;
break;
}
indexOf = separators.indexOf(c, 0);
if (indexOf > -1) {
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
indexOf = separators2.indexOf(c, 0);
if (indexOf > -1) {
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
} else {
currentTokenType = Token.ERROR_IDENTIFIER;
}
} // End of switch (c).
break;
default: // Should never happen
case Token.LITERAL_NUMBER_HEXADECIMAL:
switch (c) {
case ' ':
case '\t':
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_HEXADECIMAL, newStartOffset
+ currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.WHITESPACE;
break;
case '"': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_HEXADECIMAL, newStartOffset
+ currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
backslash = false;
break;
case '\'': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_HEXADECIMAL, newStartOffset
+ currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_CHAR;
backslash = false;
break;
case '\\':
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_HEXADECIMAL, newStartOffset
+ currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
backslash = true;
break;
default:
if (c == 'e') { // Exponent.
if (numContainsExponent == false) {
numContainsExponent = true;
} else {
currentTokenType = Token.ERROR_NUMBER_FORMAT;
}
break;
}
int indexOf = hexCharacters.indexOf(c);
if (indexOf > -1) {
break; // Still a hexadecimal number.
}
indexOf = numberEndChars.indexOf(c);
if (indexOf > -1) { // Numbers can end in 'f','F','l','L', etc.
if (numContainsEndCharacter == true) {
currentTokenType = Token.ERROR_NUMBER_FORMAT;
} else {
numContainsEndCharacter = true;
}
break;
}
indexOf = operators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_HEXADECIMAL,
newStartOffset + currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.OPERATOR;
break;
}
indexOf = separators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_HEXADECIMAL,
newStartOffset + currentTokenStart);
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
indexOf = separators2.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_HEXADECIMAL,
newStartOffset + currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
// Otherwise, the token is an error.
currentTokenType = Token.ERROR_NUMBER_FORMAT;
} // End of switch (c).
break;
case Token.IDENTIFIER:
switch (c) {
case ' ':
case '\t':
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.WHITESPACE;
break;
case '"': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
backslash = false;
break;
case '\'': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_CHAR;
backslash = false;
break;
case '\\':
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
backslash = true;
break;
default:
if (RSyntaxUtilities.isLetterOrDigit(c) || c == '_') {
break; // Still an identifier of some type.
}
int indexOf = operators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.OPERATOR;
break;
}
indexOf = separators.indexOf(c, 0);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
indexOf = separators2.indexOf(c, 0);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
} else {
currentTokenType = Token.ERROR_IDENTIFIER;
}
} // End of switch (c).
break;
case Token.LITERAL_NUMBER_DECIMAL_INT:
// Reset our boolean states if we only have one digit char before
// the current one.
if (currentTokenStart == i - 1) {
numContainsExponent = false;
numContainsEndCharacter = false;
}
switch (c) {
case ' ':
case '\t':
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_DECIMAL_INT, newStartOffset
+ currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.WHITESPACE;
break;
case '"': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_DECIMAL_INT, newStartOffset
+ currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
backslash = false;
break;
case '\'': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_DECIMAL_INT, newStartOffset
+ currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_CHAR;
backslash = false;
break;
case '\\':
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_DECIMAL_INT, newStartOffset
+ currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
backslash = true;
break;
default:
if (RSyntaxUtilities.isDigit(c)) {
break; // Still a literal number.
} else if (c == 'e') { // Exponent.
if (numContainsExponent == false) {
numContainsExponent = true;
} else {
currentTokenType = Token.ERROR_NUMBER_FORMAT;
}
break;
} else if (c == '.') { // Decimal point.
if (numContainsExponent == true) {
currentTokenType = Token.ERROR_NUMBER_FORMAT;
} else {
currentTokenType = Token.LITERAL_NUMBER_FLOAT;
}
break;
}
int indexOf = numberEndChars.indexOf(c);
if (indexOf > -1) { // Numbers can end in 'f','F','l','L', etc.
if (numContainsEndCharacter == true) {
currentTokenType = Token.ERROR_NUMBER_FORMAT;
} else {
numContainsEndCharacter = true;
}
break;
}
indexOf = operators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_DECIMAL_INT,
newStartOffset + currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.OPERATOR;
break;
}
indexOf = separators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_DECIMAL_INT,
newStartOffset + currentTokenStart);
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
indexOf = separators2.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_DECIMAL_INT,
newStartOffset + currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
// Otherwise, the token is an error.
currentTokenType = Token.ERROR_NUMBER_FORMAT;
} // End of switch (c).
break;
case Token.LITERAL_NUMBER_FLOAT:
switch (c) {
case ' ':
case '\t':
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_FLOAT, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.WHITESPACE;
break;
case '"': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_FLOAT, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
backslash = false;
break;
case '\'': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_FLOAT, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_CHAR;
backslash = false;
break;
case '\\':
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_FLOAT, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
backslash = true;
break;
default:
if (RSyntaxUtilities.isDigit(c)) {
break; // Still a literal number.
} else if (c == 'e') { // Exponent.
if (numContainsExponent == false) {
numContainsExponent = true;
} else {
currentTokenType = Token.ERROR_NUMBER_FORMAT;
}
break;
} else if (c == '.') { // Second decimal point; must catch now because it's a "separator"
// below.
currentTokenType = Token.ERROR_NUMBER_FORMAT;
break;
}
int indexOf = numberEndChars.indexOf(c);
if (indexOf > -1) { // Numbers can end in 'f','F','l','L', etc.
if (numContainsEndCharacter == true) {
currentTokenType = Token.ERROR_NUMBER_FORMAT;
} else {
numContainsEndCharacter = true;
}
break;
}
indexOf = operators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_FLOAT, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.OPERATOR;
break;
}
indexOf = separators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_FLOAT, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
indexOf = separators2.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.LITERAL_NUMBER_FLOAT, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
// Otherwise, the token is an error.
currentTokenType = Token.ERROR_NUMBER_FORMAT;
} // End of switch (c).
break;
case Token.COMMENT_MULTILINE:
// Find either end of MLC or end of the current line.
while (i < end - 1) {
if (array[i] == '*' && array[i + 1] == '/') {
addToken(text, currentTokenStart, i + 1, Token.COMMENT_MULTILINE, newStartOffset +
currentTokenStart);
i = i + 1;
currentTokenType = Token.NULL;
backslash = false; // Backslashes can't accumulate before and after a comment...
break;
}
i++;
}
break;
case Token.COMMENT_EOL:
i = end - 1;
addToken(text, currentTokenStart, i, Token.COMMENT_EOL, newStartOffset + currentTokenStart);
// We need to set token type to null so at the bottom we don't add one more token.
currentTokenType = Token.NULL;
break;
// We need this state because comments always start with '/', which is an operator.
// Note that when we enter this state, the PREVIOUS character was an operator.
case Token.OPERATOR:
if (array[i - 1] == '/') { // Possibility of comments.
if (c == '*') {
currentTokenType = Token.COMMENT_MULTILINE;
break;
} else if (c == '/') {
currentTokenType = Token.COMMENT_EOL;
i = end - 1; // Since we know the rest of the line is in this token.
} else {
// We MUST add the token at the previous char now; if we don't and let
// operators accumulate before we print them, we will mess up syntax
// highlighting if we get an end-of-line comment.
addToken(text, currentTokenStart, i - 1, Token.OPERATOR, newStartOffset +
currentTokenStart);
currentTokenType = Token.NULL;
i = i - 1;
}
} else {
addToken(text, currentTokenStart, i - 1, Token.OPERATOR, newStartOffset + currentTokenStart);
// Hack to keep code size down...
i--;
currentTokenType = Token.NULL;
}
break;
case Token.ERROR_IDENTIFIER:
switch (c) {
case ' ':
case '\t':
addToken(text, currentTokenStart, i - 1, Token.ERROR_IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.WHITESPACE;
break;
case '"': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.ERROR_IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
backslash = false;
break;
case '\'': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.ERROR_IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_CHAR;
backslash = false;
break;
case ';':
addToken(text, currentTokenStart, i - 1, Token.ERROR_IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
case '\\':
addToken(text, currentTokenStart, i - 1, Token.ERROR_IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
backslash = true; // Must be first backslash in a row since previous character
// identifier char.
break;
default:
int indexOf = operators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.ERROR_IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.OPERATOR;
}
indexOf = separators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.ERROR_IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
}
indexOf = separators2.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.ERROR_IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
}
} // End of switch (c).
break;
case Token.ERROR_NUMBER_FORMAT:
switch (c) {
case ' ':
case '\t':
addToken(text, currentTokenStart, i - 1, Token.ERROR_NUMBER_FORMAT, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.WHITESPACE;
break;
case '"': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.ERROR_NUMBER_FORMAT, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
backslash = false;
break;
case '\'': // Don't need to worry about backslashes as previous char is non-backslash.
addToken(text, currentTokenStart, i - 1, Token.ERROR_NUMBER_FORMAT, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_CHAR;
backslash = false;
break;
case ';':
addToken(text, currentTokenStart, i - 1, Token.ERROR_NUMBER_FORMAT, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
case '\\':
addToken(text, currentTokenStart, i - 1, Token.ERROR_NUMBER_FORMAT, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
backslash = true; // Must be first backslash in a row since previous char is a number
break;
default:
// Could be going into hexadecimal.
int indexOf = hexCharacters.indexOf(c);
if (indexOf > -1 && (i - currentTokenStart == 2 && array[i - 1] == 'x' && array[i - 2] ==
'0')) {
currentTokenType = Token.LITERAL_NUMBER_HEXADECIMAL;
break;
}
indexOf = operators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.ERROR_NUMBER_FORMAT, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.OPERATOR;
}
indexOf = separators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.ERROR_NUMBER_FORMAT, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
}
indexOf = separators2.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.ERROR_NUMBER_FORMAT, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
}
} // End of switch (c).
break;
case Token.ERROR_CHAR:
if (c == '\\') {
backslash = !backslash; // Okay because if we got in here, backslash was initially false.
} else {
if (c == '\'' && !backslash) {
addToken(text, currentTokenStart, i, Token.LITERAL_CHAR, newStartOffset +
currentTokenStart);
currentTokenType = Token.NULL;
// backslash is definitely false when we leave.
}
backslash = false; // Need to set backslash to false here as a character was typed.
}
// Otherwise, we're still an unclosed char...
break;
case Token.ERROR_STRING_DOUBLE:
if (c == '\\') {
backslash = !backslash; // Okay because if we got in here, backslash was initially false.
} else {
if (c == '"' && !backslash) {
addToken(text, currentTokenStart, i, Token.LITERAL_STRING_DOUBLE_QUOTE, newStartOffset +
currentTokenStart);
currentTokenType = Token.NULL;
// backslash is definitely false when we leave.
}
backslash = false; // Need to set backslash to false here as a character was typed.
}
// Otherwise, we're still an unclosed string...
break;
} // End of switch (currentTokenType).
} // End of for (int i=offset; i<end; i++).
// Deal with the (possibly there) last token.
if (currentTokenType != Token.NULL) {
addToken(text, currentTokenStart, end - 1, currentTokenType, newStartOffset + currentTokenStart);
}
if (currentTokenType != Token.COMMENT_MULTILINE) {
addNullToken();
}
// Return the first token in our linked list.
return firstToken;
}
}

View File

@ -1,504 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.Account;
import org.ethereum.core.Block;
import org.ethereum.core.Transaction;
import org.ethereum.core.Wallet;
import org.ethereum.db.ContractDetails;
import org.ethereum.util.ByteUtil;
import org.ethereum.util.Utils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.spongycastle.util.BigIntegers;
import org.spongycastle.util.encoders.Hex;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.FocusAdapter;
import java.awt.event.FocusEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.math.BigInteger;
import java.net.URL;
import java.util.Collection;
import java.util.Map;
import javax.swing.*;
import javax.swing.border.Border;
import javax.swing.border.EtchedBorder;
import javax.swing.plaf.ComboBoxUI;
import javax.swing.plaf.basic.BasicComboPopup;
import javax.swing.table.DefaultTableModel;
/**
* @author Roman Mandeleil
* @since 18.05.14
*/
@SuppressWarnings("unchecked")
class ContractCallDialog extends JDialog implements MessageAwareDialog {
private static final long serialVersionUID = -7561153561155037293L;
private Logger logger = LoggerFactory.getLogger("ui");
private ContractCallDialog dialog;
private JComboBox<AccountWrapper> creatorAddressCombo;
private final JTextField gasInput;
private final JTextField contractAddrInput;
private JScrollPane contractDataInput;
private JTextArea msgDataTA;
private JLabel statusMsg = null;
private JLabel playLabel = null;
private JLabel rejectLabel = null;
private JLabel approveLabel = null;
public ContractCallDialog(Frame parent) {
super(parent, "Call Contract: ", false);
dialog = this;
contractAddrInput = new JTextField(5);
GUIUtils.addStyle(contractAddrInput, "Contract Address: ");
contractAddrInput.addFocusListener(new FocusAdapter() {
@Override
public void focusLost(FocusEvent e) {
SwingUtilities.invokeLater(ContractCallDialog.this::populateContractDetails);
}
});
contractAddrInput.setBounds(70, 30, 350, 45);
this.getContentPane().add(contractAddrInput);
gasInput = new JTextField(5);
GUIUtils.addStyle(gasInput, "Gas: ");
msgDataTA = new JTextArea();
msgDataTA.setLineWrap(true);
contractDataInput = new JScrollPane(msgDataTA);
GUIUtils.addStyle(msgDataTA, null, false);
GUIUtils.addStyle(contractDataInput, "Input:");
msgDataTA.setText("");
msgDataTA.setCaretPosition(0);
this.getContentPane().setBackground(Color.WHITE);
this.getContentPane().setLayout(null);
contractDataInput.setBounds(70, 80, 350, 165);
this.getContentPane().add(contractDataInput);
gasInput.setBounds(330, 260, 90, 45);
this.getContentPane().add(gasInput);
URL rejectIconURL = ClassLoader.getSystemResource("buttons/reject.png");
ImageIcon rejectIcon = new ImageIcon(rejectIconURL);
rejectLabel = new JLabel(rejectIcon);
rejectLabel.setToolTipText("Cancel");
rejectLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
URL playIconURL = ClassLoader.getSystemResource("buttons/play.png");
ImageIcon playIcon = new ImageIcon(playIconURL);
playLabel = new JLabel(playIcon);
playLabel.setToolTipText("Play Drafted");
playLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
playLabel.addMouseListener(
new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
ContractCallDialog.this.playContractCall();
}
}
);
playLabel.setBounds(438, 100, 42, 42);
this.getContentPane().add(playLabel);
JLabel statusMessage = new JLabel("");
statusMessage.setBounds(50, 360, 400, 50);
statusMessage.setHorizontalAlignment(SwingConstants.CENTER);
this.statusMsg = statusMessage;
this.getContentPane().add(statusMessage);
rejectLabel.setBounds(260, 325, 45, 45);
this.getContentPane().add(rejectLabel);
rejectLabel.setVisible(true);
rejectLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
dialog.dispose();
}
});
URL approveIconURL = ClassLoader.getSystemResource("buttons/approve.png");
ImageIcon approveIcon = new ImageIcon(approveIconURL);
approveLabel = new JLabel(approveIcon);
approveLabel.setToolTipText("Submit the transaction");
approveLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
approveLabel.setBounds(200, 325, 45, 45);
this.getContentPane().add(approveLabel);
approveLabel.setVisible(true);
approveLabel.addMouseListener(
new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
submitContractCall();
}
}
);
gasInput.setText("1000");
JComboBox<AccountWrapper> creatorAddressCombo = new JComboBox<AccountWrapper>() {
private static final long serialVersionUID = -3748305421049121671L;
@Override
public ComboBoxUI getUI() {
return super.getUI();
}
};
creatorAddressCombo.setOpaque(true);
creatorAddressCombo.setEnabled(true);
creatorAddressCombo.setBackground(Color.WHITE);
creatorAddressCombo.setFocusable(false);
this.creatorAddressCombo = creatorAddressCombo;
final Border line = BorderFactory.createLineBorder(Color.LIGHT_GRAY);
JComponent editor = (JComponent) (creatorAddressCombo.getEditor().getEditorComponent());
editor.setForeground(Color.RED);
Wallet wallet = UIEthereumManager.ethereum.getWallet();
Collection<Account> accounts = wallet.getAccountCollection();
for (Account account : accounts) {
creatorAddressCombo.addItem(new AccountWrapper(account));
}
creatorAddressCombo.setRenderer(new DefaultListCellRenderer() {
private static final long serialVersionUID = 6100091092527477892L;
@Override
public void paint(Graphics g) {
setBackground(Color.WHITE);
setForeground(new Color(143, 170, 220));
setFont(new Font("Monospaced", 0, 13));
setBorder(BorderFactory.createEmptyBorder());
super.paint(g);
}
});
creatorAddressCombo.setPopupVisible(false);
Object child = creatorAddressCombo.getAccessibleContext().getAccessibleChild(0);
BasicComboPopup popup = (BasicComboPopup) child;
JList list = popup.getList();
list.setSelectionBackground(Color.cyan);
list.setBorder(null);
for (int i = 0; i < creatorAddressCombo.getComponentCount(); i++) {
if (creatorAddressCombo.getComponent(i) instanceof CellRendererPane) {
CellRendererPane crp = ((CellRendererPane) (creatorAddressCombo.getComponent(i)));
}
if (creatorAddressCombo.getComponent(i) instanceof AbstractButton) {
((AbstractButton) creatorAddressCombo.getComponent(i)).setBorder(line);
}
}
creatorAddressCombo.setBounds(70, 267, 230, 36);
this.getContentPane().add(creatorAddressCombo);
this.getContentPane().revalidate();
this.getContentPane().repaint();
this.setResizable(false);
this.setVisible(true);
}
private void populateContractDetails() {
byte[] addr = Utils.addressStringToBytes(contractAddrInput.getText());
if (addr == null) {
alertStatusMsg("Not a valid contract address");
return;
}
ContractDetails contractDetails = UIEthereumManager.ethereum
.getRepository().getContractDetails(addr);
if (contractDetails == null) {
alertStatusMsg("No contract for that address");
return;
}
final byte[] programCode = contractDetails.getCode();
if (programCode == null || programCode.length == 0) {
alertStatusMsg("Such account exist but no code in the db");
return;
}
final Map storageMap = contractDetails.getStorage();
contractDataInput.setBounds(70, 80, 350, 145);
contractDataInput.setViewportView(msgDataTA);
URL expandIconURL = ClassLoader.getSystemResource("buttons/add-23x23.png");
ImageIcon expandIcon = new ImageIcon(expandIconURL);
final JLabel expandLabel = new JLabel(expandIcon);
expandLabel.setToolTipText("Cancel");
expandLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
expandLabel.setBounds(235, 232, 23, 23);
this.getContentPane().add(expandLabel);
expandLabel.setVisible(true);
final Border border = BorderFactory.createEtchedBorder(EtchedBorder.LOWERED);
final JPanel detailPanel = new JPanel();
detailPanel.setBorder(border);
detailPanel.setBounds(135, 242, 230, 2);
final JPanel spacer = new JPanel();
spacer.setForeground(Color.white);
spacer.setBackground(Color.white);
spacer.setBorder(null);
spacer.setBounds(225, 232, 40, 20);
this.getContentPane().add(spacer);
this.getContentPane().add(detailPanel);
expandLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
ContractCallDialog.this.setSize(500, 530);
ContractCallDialog.this.creatorAddressCombo.setBounds(70, 367, 230, 36);
ContractCallDialog.this.gasInput.setBounds(330, 360, 90, 45);
ContractCallDialog.this.rejectLabel.setBounds(260, 425, 45, 45);
ContractCallDialog.this.approveLabel.setBounds(200, 425, 45, 45);
ContractCallDialog.this.statusMsg.setBounds(50, 460, 400, 50);
spacer.setVisible(false);
expandLabel.setVisible(false);
detailPanel.setVisible(false);
JTextField contractCode = new JTextField(15);
contractCode.setText(Hex.toHexString(programCode));
GUIUtils.addStyle(contractCode, "Code: ");
contractCode.setBounds(70, 230, 350, 45);
JTable storage = new JTable(2, 2);
storage.setTableHeader(null);
storage.setShowGrid(false);
storage.setIntercellSpacing(new Dimension(15, 0));
storage.setCellSelectionEnabled(false);
GUIUtils.addStyle(storage);
JTableStorageModel tableModel = new JTableStorageModel(storageMap);
storage.setModel(tableModel);
JScrollPane scrollPane = new JScrollPane(storage);
scrollPane.setBorder(null);
scrollPane.getViewport().setBackground(Color.WHITE);
scrollPane.setBounds(70, 290, 350, 50);
ContractCallDialog.this.getContentPane().add(contractCode);
ContractCallDialog.this.getContentPane().add(scrollPane);
}
});
this.repaint();
}
private void playContractCall() {
byte[] addr = Utils.addressStringToBytes(contractAddrInput.getText());
if (addr == null) {
alertStatusMsg("Not a valid contract address");
return;
}
ContractDetails contractDetails = UIEthereumManager.ethereum
.getRepository().getContractDetails(addr);
if (contractDetails == null) {
alertStatusMsg("No contract for that address");
return;
}
final byte[] programCode = contractDetails.getCode();
if (programCode == null || programCode.length == 0) {
alertStatusMsg("Such account exist but no code in the db");
return;
}
Transaction tx = createTransaction();
if (tx == null) return;
Block lastBlock = UIEthereumManager.ethereum.getBlockchain().getBestBlock();
ProgramPlayDialog.createAndShowGUI(programCode, tx, lastBlock);
}
protected JRootPane createRootPane() {
Container parent = this.getParent();
if (parent != null) {
Dimension parentSize = parent.getSize();
Point p = parent.getLocation();
setLocation(p.x + parentSize.width / 4, p.y + 10);
}
JRootPane rootPane = new JRootPane();
KeyStroke stroke = KeyStroke.getKeyStroke("ESCAPE");
Action actionListener = new AbstractAction() {
public void actionPerformed(ActionEvent actionEvent) {
dispose();
}
};
InputMap inputMap = rootPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
inputMap.put(stroke, "ESCAPE");
rootPane.getActionMap().put("ESCAPE", actionListener);
this.setSize(500, 430);
return rootPane;
}
public void infoStatusMsg(String text) {
this.statusMsg.setForeground(Color.GREEN.darker().darker());
this.statusMsg.setText(text);
}
public void alertStatusMsg(String text) {
this.statusMsg.setForeground(Color.RED);
this.statusMsg.setText(text);
}
public void submitContractCall() {
if (!UIEthereumManager.ethereum.isConnected()) {
dialog.alertStatusMsg("Not connected to any peer");
return;
}
Transaction tx = createTransaction();
if (tx == null) return;
if (logger.isInfoEnabled()) {
logger.info("tx.hash: {}", (new BigInteger(tx.getHash()).toString(16)));
}
// SwingWorker
DialogWorker worker = new DialogWorker(tx, this);
worker.execute();
}
private Transaction createTransaction() {
byte[] data;
if (!msgDataTA.getText().trim().equals("")) {
Object[] lexaList = msgDataTA.getText().split(",");
data = ByteUtil.encodeDataList(lexaList);
} else {
data = new byte[]{};
}
byte[] contractAddress = Hex.decode(contractAddrInput.getText());
Account account = ((AccountWrapper) creatorAddressCombo.getSelectedItem()).getAccount();
byte[] senderPrivKey = account.getEcKey().getPrivKeyBytes();
BigInteger nonce = account.getNonce();
BigInteger gasPrice = new BigInteger("10000000000000");
BigInteger gasBI = new BigInteger(gasInput.getText());
byte[] gasValue = BigIntegers.asUnsignedByteArray(gasBI);
BigInteger endowment = new BigInteger("1000");
if (logger.isInfoEnabled()) {
logger.info("Contract call:");
logger.info("tx.nonce: {}", nonce == null ? "null" : nonce.toString());
logger.info("tx.gasPrice: {}", Hex.toHexString(BigIntegers.asUnsignedByteArray(gasPrice)));
logger.info("tx.gasValue: {}", Hex.toHexString(gasValue));
logger.info("tx.address: {}", Hex.toHexString(contractAddress));
logger.info("tx.endowment: {}", Hex.toHexString(BigIntegers.asUnsignedByteArray(endowment)));
logger.info("tx.data: {}", Hex.toHexString(data));
}
Transaction tx = UIEthereumManager.ethereum.createTransaction(
nonce,
gasPrice, gasBI,
contractAddress, endowment, data);
try {
tx.sign(senderPrivKey);
} catch (Exception e1) {
dialog.alertStatusMsg("Failed to sign the transaction");
return null;
}
return tx;
}
public class AccountWrapper {
private Account account;
public AccountWrapper(Account account) {
this.account = account;
}
public Account getAccount() {
return account;
}
@Override
public String toString() {
String addressShort =
Utils.getAddressShortString(account.getEcKey().getAddress());
String valueShort = "0";
String result = String.format(" By: [%s] %s", addressShort,
valueShort);
return result;
}
}
private class JTableStorageModel extends DefaultTableModel {
private JTableStorageModel(Map<String, String> data) {
if (data != null) {
this.setColumnCount(2);
this.setRowCount(data.size());
int i = 0;
for (String key : data.keySet()) {
this.setValueAt(key, i, 0);
this.setValueAt(data.get(key), i, 1);
++i;
}
}
}
}
public static void main(String args[]) {
ContractCallDialog ccd = new ContractCallDialog(null);
ccd.setVisible(true);
ccd.setDefaultCloseOperation(JDialog.DISPOSE_ON_CLOSE);
ccd.addWindowListener(new WindowAdapter() {
@Override
public void windowClosed(WindowEvent e) {
UIEthereumManager.ethereum.close();
}
});
}
}

View File

@ -1,358 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.Account;
import org.ethereum.core.AccountState;
import org.ethereum.core.Block;
import org.ethereum.core.Transaction;
import org.ethereum.core.Wallet;
import org.ethereum.util.Utils;
import org.spongycastle.util.BigIntegers;
import org.spongycastle.util.encoders.Hex;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.math.BigInteger;
import java.net.URL;
import java.util.Collection;
import javax.swing.*;
import javax.swing.border.Border;
import javax.swing.plaf.ComboBoxUI;
import javax.swing.plaf.basic.BasicComboPopup;
/**
* @author Roman Mandeleil
* @since 18.05.14
*/
class ContractSubmitDialog extends JDialog implements MessageAwareDialog {
private static final long serialVersionUID = -3622984456084608996L;
ContractSubmitDialog dialog;
JComboBox<AccountWrapper> creatorAddressCombo;
final JTextField gasInput;
final JTextField contractAddrInput;
private byte[] initByteCode;
JLabel statusMsg = null;
public ContractSubmitDialog(Frame parent, byte[] byteCode) {
super(parent, "Contract Details: ", false);
dialog = this;
this.initByteCode = byteCode;
contractAddrInput = new JTextField(5);
GUIUtils.addStyle(contractAddrInput, "Contract Address: ");
contractAddrInput.setBounds(70, 30, 350, 45);
this.getContentPane().add(contractAddrInput);
gasInput = new JTextField(5);
GUIUtils.addStyle(gasInput, "Gas: ");
JTextArea contractDataTA = new JTextArea();
contractDataTA.setLineWrap(true);
JScrollPane contractDataInput = new JScrollPane(contractDataTA);
GUIUtils.addStyle(contractDataTA, null, false);
GUIUtils.addStyle(contractDataInput, "Code:");
String byteCodeText = GUIUtils.getHexStyledText(byteCode);
contractDataTA.setText(byteCodeText);
contractDataTA.setEditable(false);
contractDataTA.setCaretPosition(0);
this.getContentPane().setBackground(Color.WHITE);
this.getContentPane().setLayout(null);
contractDataInput.setBounds(70, 80, 350, 165);
this.getContentPane().add(contractDataInput);
gasInput.setBounds(330, 260, 90, 45);
this.getContentPane().add(gasInput);
URL rejectIconURL = ClassLoader.getSystemResource("buttons/reject.png");
ImageIcon rejectIcon = new ImageIcon(rejectIconURL);
JLabel rejectLabel = new JLabel(rejectIcon);
rejectLabel.setToolTipText("Cancel");
rejectLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
URL playIconURL = ClassLoader.getSystemResource("buttons/play.png");
ImageIcon playIcon = new ImageIcon(playIconURL);
JLabel playLabel = new JLabel(playIcon);
playLabel.setToolTipText("Play Drafted");
playLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
playLabel.setBounds(438, 100, 42, 42);
this.getContentPane().add(playLabel);
playLabel.addMouseListener(
new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
Transaction tx = null;
try {
tx = createTransaction();
} catch (Exception e1) {
dialog.alertStatusMsg("Failed to sign the transaction");
return;
}
contractAddrInput.setText(Hex.toHexString(tx.getContractAddress()));
Block lastBlock = UIEthereumManager.ethereum.getBlockchain().getBestBlock();
ProgramPlayDialog.createAndShowGUI(tx.getData(), tx, lastBlock);
}
}
);
JLabel statusMessage = new JLabel("");
statusMessage.setBounds(50, 360, 400, 50);
statusMessage.setHorizontalAlignment(SwingConstants.CENTER);
this.statusMsg = statusMessage;
this.getContentPane().add(statusMessage);
rejectLabel.setBounds(260, 325, 45, 45);
this.getContentPane().add(rejectLabel);
rejectLabel.setVisible(true);
rejectLabel.addMouseListener(
new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
dialog.dispose();
}
}
);
URL approveIconURL = ClassLoader.getSystemResource("buttons/approve.png");
ImageIcon approveIcon = new ImageIcon(approveIconURL);
JLabel approveLabel = new JLabel(approveIcon);
approveLabel.setToolTipText("Submit the transaction");
approveLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
approveLabel.setBounds(200, 325, 45, 45);
this.getContentPane().add(approveLabel);
approveLabel.setVisible(true);
approveLabel.addMouseListener(
new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
submitContract();
}
}
);
gasInput.setText("1000");
JComboBox<AccountWrapper> creatorAddressCombo = new JComboBox<AccountWrapper>() {
@Override
public ComboBoxUI getUI() {
return super.getUI();
}
};
creatorAddressCombo.setOpaque(true);
creatorAddressCombo.setEnabled(true);
creatorAddressCombo.setBackground(Color.WHITE);
creatorAddressCombo.setFocusable(false);
this.creatorAddressCombo = creatorAddressCombo;
final Border line = BorderFactory.createLineBorder(Color.LIGHT_GRAY);
JComponent editor = (JComponent) (creatorAddressCombo.getEditor().getEditorComponent());
editor.setForeground(Color.RED);
Wallet wallet = UIEthereumManager.ethereum.getWallet();
Collection<Account> accounts = wallet.getAccountCollection();
for (Account account : accounts) {
creatorAddressCombo.addItem(new AccountWrapper(account));
}
creatorAddressCombo.setRenderer(new DefaultListCellRenderer() {
@Override
public void paint(Graphics g) {
setBackground(Color.WHITE);
setForeground(new Color(143, 170, 220));
setFont(new Font("Monospaced", 0, 13));
setBorder(BorderFactory.createEmptyBorder());
super.paint(g);
}
});
creatorAddressCombo.setPopupVisible(false);
Object child = creatorAddressCombo.getAccessibleContext().getAccessibleChild(0);
BasicComboPopup popup = (BasicComboPopup) child;
JList list = popup.getList();
list.setSelectionBackground(Color.cyan);
list.setBorder(null);
for (int i = 0; i < creatorAddressCombo.getComponentCount(); i++) {
if (creatorAddressCombo.getComponent(i) instanceof CellRendererPane) {
CellRendererPane crp = ((CellRendererPane)
(creatorAddressCombo.getComponent(i)));
}
if (creatorAddressCombo.getComponent(i) instanceof AbstractButton) {
((AbstractButton) creatorAddressCombo.getComponent(i))
.setBorder(line);
}
}
creatorAddressCombo.setBounds(73, 267, 230, 36);
this.getContentPane().add(creatorAddressCombo);
this.getContentPane().revalidate();
this.getContentPane().repaint();
this.setResizable(false);
this.setVisible(true);
}
protected JRootPane createRootPane() {
Container parent = this.getParent();
if (parent != null) {
Dimension parentSize = parent.getSize();
Point p = parent.getLocation();
setLocation(p.x + parentSize.width / 4, p.y + 10);
}
JRootPane rootPane = new JRootPane();
KeyStroke stroke = KeyStroke.getKeyStroke("ESCAPE");
Action actionListener = new AbstractAction() {
public void actionPerformed(ActionEvent actionEvent) {
dispose();
}
};
InputMap inputMap = rootPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
inputMap.put(stroke, "ESCAPE");
rootPane.getActionMap().put("ESCAPE", actionListener);
this.setSize(500, 430);
return rootPane;
}
public void infoStatusMsg(String text) {
this.statusMsg.setForeground(Color.GREEN.darker().darker());
this.statusMsg.setText(text);
}
public void alertStatusMsg(String text) {
this.statusMsg.setForeground(Color.RED);
this.statusMsg.setText(text);
}
public void submitContract() {
if (!validInput())
return;
Transaction tx = null;
try {
tx = createTransaction();
} catch (Exception e1) {
dialog.alertStatusMsg("Failed to sign the transaction");
return;
}
contractAddrInput.setText(Hex.toHexString(tx.getContractAddress()));
if (!UIEthereumManager.ethereum.isConnected()) {
dialog.alertStatusMsg("Not connected to any peer");
return;
}
// SwingWorker
DialogWorker worker = new DialogWorker(tx, this);
worker.execute();
}
private Transaction createTransaction() {
Account account = ((AccountWrapper) creatorAddressCombo.getSelectedItem()).getAccount();
byte[] senderPrivKey = account.getEcKey().getPrivKeyBytes();
BigInteger nonce = UIEthereumManager.ethereum.getRepository().getNonce(account.getAddress());
byte[] gasPrice = new BigInteger("10000000000000").toByteArray();
BigInteger gasBI = new BigInteger(gasInput.getText());
byte[] gasValue = BigIntegers.asUnsignedByteArray(gasBI);
byte[] endowment = BigIntegers.asUnsignedByteArray(new BigInteger("1000"));
byte[] zeroAddress = null;
// UIEthereumManager.ethereum.createTransaction();
Transaction tx = new Transaction(BigIntegers.asUnsignedByteArray(nonce),
gasPrice, gasValue,
zeroAddress, endowment, initByteCode);
tx.sign(senderPrivKey);
return tx;
}
private boolean validInput() {
Account account = ((AccountWrapper) creatorAddressCombo.getSelectedItem()).getAccount();
BigInteger currentBalance =
UIEthereumManager.ethereum.getRepository().getBalance(account.getAddress());
BigInteger gasPrice = BigInteger.valueOf(42);
BigInteger gasInput = new BigInteger(this.gasInput.getText());
boolean canAfford = currentBalance.compareTo(gasPrice.multiply(gasInput)) >= 0;
if (!canAfford) {
alertStatusMsg("The address can't afford this transaction");
return false;
}
return true;
}
public static void main(String args[]) {
AccountState as = new AccountState();
ContractSubmitDialog pod = new ContractSubmitDialog(null, null);
pod.setVisible(true);
}
public class AccountWrapper {
private Account account;
public AccountWrapper(Account account) {
this.account = account;
}
public Account getAccount() {
return account;
}
@Override
public String toString() {
String addressShort = Utils.getAddressShortString(account.getEcKey().getAddress());
String valueShort = Utils.getValueShortString(
UIEthereumManager.ethereum.getRepository().getBalance(account.getAddress())
);
String result = String.format(" By: [%s] %s", addressShort, valueShort);
return result;
}
}
}

View File

@ -1,60 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.Transaction;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;
import javax.swing.*;
import static org.ethereum.config.SystemProperties.CONFIG;
/**
* @author Roman Mandeleil
* @since 26.05.2014
*/
public class DialogWorker extends SwingWorker<Transaction, Object> {
private static Logger logger = LoggerFactory.getLogger(DialogWorker.class);
private Transaction tx;
private MessageAwareDialog dialog;
public DialogWorker(Transaction tx, MessageAwareDialog dialog) {
this.tx = tx;
this.dialog = dialog;
}
@Override
protected Transaction doInBackground() throws Exception {
Future<Transaction> future = UIEthereumManager.ethereum.submitTransaction(tx);
dialog.infoStatusMsg("Transaction sent to the network, waiting for approve");
try {
future.get(CONFIG.transactionApproveTimeout(), TimeUnit.SECONDS);
} catch (TimeoutException toe) {
logger.error(toe.getMessage(), toe);
dialog.alertStatusMsg("Transaction wasn't approved, network timeout");
return null;
} catch (InterruptedException ie) {
logger.error(ie.getMessage(), ie);
dialog.alertStatusMsg("Transaction wasn't approved");
return null;
} catch (ExecutionException ee) {
logger.error(ee.getMessage(), ee);
dialog.alertStatusMsg("Transaction wasn't approved");
return null;
} finally {
future.cancel(true);
}
dialog.infoStatusMsg("Transaction got approved");
return null;
}
}

View File

@ -1,89 +0,0 @@
package org.ethereum.gui;
import org.ethereum.serpent.SerpentCompiler;
import org.spongycastle.util.encoders.Hex;
import java.awt.*;
import javax.swing.*;
import javax.swing.border.Border;
import javax.swing.border.CompoundBorder;
import javax.swing.border.EmptyBorder;
import javax.swing.border.TitledBorder;
/**
* @author Roman Mandeleil
* @since 23.05.2014
*/
public class GUIUtils {
public static void addStyle(JTextField textField, String labelName) {
textField.setHorizontalAlignment(SwingConstants.RIGHT);
Border line = BorderFactory.createLineBorder(Color.LIGHT_GRAY);
TitledBorder titled = BorderFactory.createTitledBorder(line, labelName);
titled.setTitleFont(new Font("Verdana", 0, 13));
titled.setTitleColor(new Color(213, 225, 185));
Border empty = new EmptyBorder(5, 8, 5, 8);
CompoundBorder border = new CompoundBorder(titled, empty);
textField.setBorder(border);
textField.setForeground(new Color(143, 170, 220));
textField.setFont(new Font("Monospaced", 0, 13));
}
public static void addStyle(JTextArea textArea, String labelName, boolean isBorder) {
Border border = null;
if (isBorder) {
Border line = BorderFactory.createLineBorder(Color.LIGHT_GRAY);
TitledBorder titled = BorderFactory.createTitledBorder(line, labelName);
titled.setTitleFont(new Font("Verdana", 0, 13));
titled.setTitleColor(new Color(213, 225, 185));
Border empty = new EmptyBorder(5, 8, 5, 8);
CompoundBorder cBorder = new CompoundBorder(titled, empty);
}
textArea.setBorder(border);
textArea.setForeground(new Color(143, 170, 220));
textArea.setFont(new Font("Monospaced", 0, 13));
}
public static void addStyle(JScrollPane jScrollPane, String labelName) {
Border line = BorderFactory.createLineBorder(Color.LIGHT_GRAY);
TitledBorder titled = BorderFactory.createTitledBorder(line, labelName);
titled.setTitleFont(new Font("Verdana", 0, 13));
titled.setTitleColor(new Color(213, 225, 185));
Border empty = new EmptyBorder(5, 8, 5, 8);
CompoundBorder border = new CompoundBorder(titled, empty);
jScrollPane.setBorder(border);
jScrollPane.setForeground(new Color(143, 170, 220));
jScrollPane.setBackground(Color.WHITE);
jScrollPane.setFont(new Font("Monospaced", 0, 13));
jScrollPane.setHorizontalScrollBar(null);
}
public static void addStyle(JTable jTable) {
jTable.setForeground(new Color(143, 170, 220));
jTable.setBackground(Color.WHITE);
jTable.setFont(new Font("Monospaced", 0, 13));
}
public static String getHexStyledText(byte[] data) {
String[] dataHex = Hex.toHexString(data).split("(?<=\\G.{2})");
StringBuffer sb = new StringBuffer();
for (int i = 0; i < dataHex.length; ++i) {
sb.append(dataHex[i]).append(" ");
if ((i + 1) % 8 == 0 && i != 0) sb.append("\n");
}
return sb.toString();
}
public static String getStyledAsmCode(String asmCode) {
String initBlock = SerpentCompiler.extractInitBlock(asmCode);
String codeBlock = SerpentCompiler.extractCodeBlock(asmCode);
return String.format(" \n\n *** [Init] *** \n\n %s \n" +
"\n *** [Code] *** \n\n %s \n\n", initBlock, codeBlock);
}
}

View File

@ -1,12 +0,0 @@
package org.ethereum.gui;
/**
* This interface describes the methods required
* for any dialog that displays info- and alert status messages.
*/
public interface MessageAwareDialog {
public void infoStatusMsg(final String text);
public void alertStatusMsg(final String text);
}

View File

@ -1,271 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.Account;
import org.ethereum.core.Transaction;
import org.spongycastle.util.BigIntegers;
import org.spongycastle.util.encoders.Hex;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.math.BigInteger;
import java.net.URL;
import java.util.regex.Pattern;
import javax.swing.*;
/**
* @author Roman Mandeleil
* @since 18.05.14
*/
class PayOutDialog extends JDialog implements MessageAwareDialog {
private static final long serialVersionUID = -2838121935782110981L;
private PayOutDialog dialog;
private Account account = null;
private JLabel statusMsg = null;
private final JTextField receiverInput;
private final JTextField amountInput;
private final JTextField feeInput;
public PayOutDialog(Frame parent, final Account account) {
super(parent, "Payout details: ", false);
dialog = this;
this.account = account;
receiverInput = new JTextField(18);
GUIUtils.addStyle(receiverInput, "Pay to:");
amountInput = new JTextField(18);
GUIUtils.addStyle(amountInput, "Amount: ");
feeInput = new JTextField(5);
GUIUtils.addStyle(feeInput, "Fee: ");
this.getContentPane().setBackground(Color.WHITE);
this.getContentPane().setLayout(null);
receiverInput.setBounds(70, 30, 350, 45);
this.getContentPane().add(receiverInput);
amountInput.setBounds(70, 80, 250, 45);
this.getContentPane().add(amountInput);
feeInput.setBounds(330, 80, 90, 45);
this.getContentPane().add(feeInput);
URL rejectIconURL = ClassLoader.getSystemResource("buttons/reject.png");
ImageIcon rejectIcon = new ImageIcon(rejectIconURL);
JLabel rejectLabel = new JLabel(rejectIcon);
rejectLabel.setToolTipText("Cancel");
rejectLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
JLabel statusMessage = new JLabel("");
statusMessage.setBounds(50, 180, 400, 50);
statusMessage.setHorizontalAlignment(SwingConstants.CENTER);
this.statusMsg = statusMessage;
this.getContentPane().add(statusMessage);
rejectLabel.setBounds(260, 145, 45, 45);
this.getContentPane().add(rejectLabel);
rejectLabel.setVisible(true);
rejectLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
dialog.dispose();
}
});
URL approveIconURL = ClassLoader.getSystemResource("buttons/approve.png");
ImageIcon approveIcon = new ImageIcon(approveIconURL);
JLabel approveLabel = new JLabel(approveIcon);
approveLabel.setToolTipText("Submit the transaction");
approveLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
approveLabel.setBounds(200, 145, 45, 45);
this.getContentPane().add(approveLabel);
approveLabel.setVisible(true);
approveLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
if (!validInput()) {
return;
}
BigInteger fee = new BigInteger(feeInput.getText());
BigInteger value = new BigInteger(amountInput.getText());
byte[] address = Hex.decode(receiverInput.getText());
if (!UIEthereumManager.ethereum.isConnected()) {
dialog.alertStatusMsg("Not connected to any peer");
return;
}
byte[] senderPrivKey = account.getEcKey().getPrivKeyBytes();
BigInteger nonce = account.getNonce();
byte[] gasPrice = BigInteger.valueOf(42).toByteArray();
Transaction tx = new Transaction(
BigIntegers.asUnsignedByteArray(nonce),
gasPrice,
BigIntegers.asUnsignedByteArray(fee), address,
BigIntegers.asUnsignedByteArray(value), null);
try {
tx.sign(senderPrivKey);
} catch (Exception e1) {
dialog.alertStatusMsg("Failed to sign the transaction");
return;
}
// SwingWorker
DialogWorker worker = new DialogWorker(tx, dialog);
worker.execute();
}
});
feeInput.setText("1000");
amountInput.setText("0");
this.getContentPane().revalidate();
this.getContentPane().repaint();
this.setResizable(false);
}
private boolean validInput() {
if (UIEthereumManager.ethereum.isBlockchainLoading()) {
alertStatusMsg("No transaction is allowed during block chain downloading.");
return false;
}
String receiverText = receiverInput.getText();
if (receiverText == null || receiverText.isEmpty()) {
alertStatusMsg("Should specify valid receiver address");
return false;
}
if (!Pattern.matches("[0-9a-fA-F]+", receiverText)) {
alertStatusMsg("Should specify valid receiver address");
return false;
}
if (Hex.decode(receiverText).length != 20) {
alertStatusMsg("Should specify valid receiver address");
return false;
}
String amountText = amountInput.getText();
if (amountText == null || amountText.isEmpty()) {
alertStatusMsg("Should specify amount to transfer");
return false;
}
if (!Pattern.matches("[0-9]+", amountText)) {
alertStatusMsg("Should specify numeric value for amount ");
return false;
}
if (amountText.equals("0")) {
alertStatusMsg("Should specify more than zero for transaction");
return false;
}
String feeText = feeInput.getText();
if (feeText == null || feeText.isEmpty()) {
alertStatusMsg("Should specify fee to fund the transaction");
return false;
}
if (!Pattern.matches("[0-9]+", feeText)) {
alertStatusMsg("Should specify numeric value for a fee");
return false;
}
// check if the tx is affordable
BigInteger ammountValue = new BigInteger(amountText);
BigInteger feeValue = new BigInteger(feeText);
BigInteger gasPrice = BigInteger.valueOf(42);
BigInteger currentBalance = account.getBalance();
boolean canAfford = gasPrice.multiply(feeValue).add(ammountValue).compareTo(currentBalance) != 1;
if (!canAfford) {
alertStatusMsg("The address can't afford this transaction");
return false;
}
return true;
}
protected JRootPane createRootPane() {
Container parent = this.getParent();
if (parent != null) {
Dimension parentSize = parent.getSize();
Point p = parent.getLocation();
setLocation(p.x + parentSize.width / 4, p.y + parentSize.height / 4);
}
JRootPane rootPane = new JRootPane();
KeyStroke stroke = KeyStroke.getKeyStroke("ESCAPE");
Action actionListener = new AbstractAction() {
public void actionPerformed(ActionEvent actionEvent) {
dispose();
}
};
InputMap inputMap = rootPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
inputMap.put(stroke, "ESCAPE");
rootPane.getActionMap().put("ESCAPE", actionListener);
SwingUtilities.invokeLater(() -> {
setSize(500, 255);
setVisible(true);
});
return rootPane;
}
public void infoStatusMsg(final String text) {
final PayOutDialog dialog = this;
SwingUtilities.invokeLater(() -> {
dialog.statusMsg.setForeground(Color.GREEN.darker().darker());
dialog.statusMsg.setText(text);
dialog.revalidate();
dialog.repaint();
});
}
public void alertStatusMsg(final String text) {
final PayOutDialog dialog = this;
SwingUtilities.invokeLater(() -> {
dialog.statusMsg.setForeground(Color.RED);
dialog.statusMsg.setText(text);
dialog.revalidate();
dialog.repaint();
});
}
}

View File

@ -1,86 +0,0 @@
package org.ethereum.gui;
import org.fife.ui.rsyntaxtextarea.AbstractTokenMakerFactory;
import org.fife.ui.rsyntaxtextarea.RSyntaxTextArea;
import org.fife.ui.rsyntaxtextarea.TokenMakerFactory;
import org.fife.ui.rtextarea.RTextScrollPane;
import java.awt.*;
import java.awt.event.WindowAdapter;
import javax.swing.*;
import static org.ethereum.config.SystemProperties.CONFIG;
/**
* A simple example showing how to modify the fonts and colors used in an
* RSyntaxTextArea. There are two methods to do this - via the Java API, and via
* an XML file. The latter method is preferred since it's more modular, and
* provides a way for your users to customize RSTA in your application.<p>
*
* This example uses RSyntaxTextArea 2.0.1.<p>
*
* Project Home: http://fifesoft.com/rsyntaxtextarea<br>
* Downloads: https://sourceforge.net/projects/rsyntaxtextarea
*/
public class PeerInfoWindow extends JFrame {
private static final long serialVersionUID = 1L;
private boolean autoScroll = false;
private RSyntaxTextArea textArea;
private ToolBar toolBar = null;
/**
* ERROR (exceptions) WARN (when something happens that's not supposed to)
* INFO (wire output)
* DEBUG (test/displaying intermediate values),
* TRACE (start/end method)
*/
public PeerInfoWindow(PeersTableModel.PeerInfo peerInfo) {
final PeerInfoWindow thisConsole = this;
java.net.URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
addCloseAction();
JPanel cp = new JPanel(new BorderLayout());
AbstractTokenMakerFactory atmf = (AbstractTokenMakerFactory) TokenMakerFactory.getDefaultInstance();
atmf.putMapping("text/console", "org.ethereum.gui.ConsoleTokenMaker");
textArea = new RSyntaxTextArea(16, 44);
textArea.setSyntaxEditingStyle("text/console");
// textArea.setSyntaxEditingStyle(SyntaxConstants.SYNTAX_STYLE_LISP);
textArea.setCodeFoldingEnabled(true);
textArea.setAntiAliasingEnabled(true);
RTextScrollPane sp = new RTextScrollPane(textArea);
textArea.setText(peerInfo.toString());
cp.add(sp);
setContentPane(cp);
setTitle("Connection Console");
// setDefaultCloseOperation(EXIT_ON_CLOSE);
pack();
setLocation(802, 460);
if (CONFIG.peerDiscovery())
UIEthereumManager.ethereum.startPeerDiscovery();
}
public void addCloseAction() {
this.addWindowListener(new WindowAdapter() {
});
}
public static void main(String[] args) {
// Start all Swing applications on the EDT.
SwingUtilities.invokeLater(() -> new PeerInfoWindow(null).setVisible(true));
}
}

View File

@ -1,185 +0,0 @@
package org.ethereum.gui;
import org.ethereum.geo.IpGeoDB;
import org.ethereum.net.eth.StatusMessage;
import org.ethereum.net.p2p.HelloMessage;
import org.ethereum.util.Utils;
import com.maxmind.geoip.Location;
import java.net.InetAddress;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.Timer;
import java.util.TimerTask;
import javax.swing.*;
import javax.swing.table.AbstractTableModel;
/**
* @author Roman Mandeleil
* @since 25.04.14
*/
public class PeersTableModel extends AbstractTableModel {
private List<PeerInfo> peerInfoList = new ArrayList<>();
Timer updater = new Timer();
public PeersTableModel() {
updater.scheduleAtFixedRate(new TimerTask() {
public void run() {
SwingUtilities.invokeLater(
PeersTableModel.this::updateModel
);
}
}, 0, 100);
}
public String getColumnName(int column) {
if (column == 0) return "Location";
if (column == 1) return "IP";
if (column == 2) return "Environment";
if (column == 3) return "Live";
else return "";
}
public boolean isCellEditable(int row, int column) {
return false;
}
public Class<?> getColumnClass(int column) {
if (column == 0) return ImageIcon.class;
if (column == 1) return String.class;
if (column == 2) return String.class;
if (column == 3) return ImageIcon.class;
else return String.class;
}
public Object getValueAt(int row, int column) {
PeerInfo peerInfo = peerInfoList.get(row);
if (column == 0) {
String countryCode = peerInfo.getLocation().countryCode;
ImageIcon flagIcon = null;
if (countryCode != null) {
URL flagURL = ClassLoader.getSystemResource("flags/" + countryCode.toLowerCase() + ".png");
flagIcon = new ImageIcon(flagURL);
}
return flagIcon;
}
if (column == 1)
return peerInfo.getIp().getHostAddress();
if (column == 2) {
if (peerInfo.getLastAccessed() == 0)
return "?";
else
return (System.currentTimeMillis() - peerInfo.getLastAccessed()) / 1000 + " seconds ago";
}
if (column == 3) {
ImageIcon flagIcon = null;
if (peerInfo.isConnected()) {
flagIcon = Utils.getImageIcon("connected.png");
} else {
flagIcon = Utils.getImageIcon("disconnected.png");
}
return flagIcon;
} else return "";
}
public int getRowCount() {
return this.peerInfoList.size();
}
public int getColumnCount() {
return 4;
}
public void updateModel() {
synchronized (peerInfoList) {
peerInfoList.clear();
final Set<org.ethereum.net.peerdiscovery.PeerInfo> peers = UIEthereumManager.ethereum.getPeers();
synchronized (peers) {
for (org.ethereum.net.peerdiscovery.PeerInfo peer : peers) {
InetAddress addr = peer.getAddress();
Location cr = IpGeoDB.getLocationForIp(addr);
peerInfoList.add(new PeerInfo(cr, addr, peer.isOnline(), peer.getLastCheckTime(),
peer.getHandshakeHelloMessage(), peer.getStatusMessage()));
}
}
}
}
public PeerInfo getPeerInfo(int index) {
return peerInfoList.get(index);
}
public class PeerInfo {
Location location;
InetAddress ip;
boolean connected;
long lastAccessed = 0;
HelloMessage handshakeHelloMessage;
StatusMessage handshakeStatusMessage;
private PeerInfo(Location location, InetAddress ip,
boolean isConnected, long lastAccessed, HelloMessage helloMessage, StatusMessage
statusMessage) {
if (location == null)
this.location = new Location();
else
this.location = location;
this.ip = ip;
this.connected = isConnected;
this.lastAccessed = lastAccessed;
this.handshakeHelloMessage = helloMessage;
this.handshakeStatusMessage = statusMessage;
}
private Location getLocation() {
return location;
}
private InetAddress getIp() {
return ip;
}
private boolean isConnected() {
return connected;
}
public long getLastAccessed() {
return lastAccessed;
}
@Override
public String toString() {
return "PeerInfo{" +
"location=" + location.countryName +
", geo= [ " + location.latitude + "/" + location.longitude + " ]" +
", ip=" + ip +
", connected=" + connected +
", lastAccessed=" + lastAccessed +
'}' + "\n -->" + (handshakeHelloMessage == null ? "" : handshakeHelloMessage.toString())
+ "\n -->" + (handshakeStatusMessage == null ? "" : handshakeStatusMessage.toString());
}
}
}

View File

@ -1,126 +0,0 @@
package org.ethereum.gui;
import java.awt.*;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.util.Timer;
import java.util.TimerTask;
import javax.swing.*;
import javax.swing.table.DefaultTableCellRenderer;
import javax.swing.table.TableCellRenderer;
/**
* @author Roman Mandeleil
* @since 25.04.14
*/
public class PeersTableWindow extends JFrame {
// Instance attributes used in this example
private JPanel topPanel;
private JTable table;
private JScrollPane scrollPane;
private Timer updater = new Timer();
private ToolBar toolBar;
// Constructor of main frame
public PeersTableWindow(ToolBar toolBar) {
this.toolBar = toolBar;
addCloseAction();
// Set the frame characteristics
setTitle("Ethereum Peers");
setSize(515, 400);
setLocation(615, 30);
java.net.URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
// Create a panel to hold all other components
topPanel = new JPanel();
topPanel.setLayout(new BorderLayout());
topPanel.setBackground(Color.WHITE);
getContentPane().add(topPanel);
getContentPane().setBackground(Color.WHITE);
// Create a new table instance
table = new JTable();
table.setModel(new PeersTableModel());
table.addMouseListener(new MouseAdapter() {
public void mousePressed(MouseEvent me) {
JTable table = (JTable) me.getSource();
Point p = me.getPoint();
int row = table.rowAtPoint(p);
PeersTableModel model = (PeersTableModel) table.getModel();
if (me.getClickCount() == 2) {
final PeersTableModel.PeerInfo peerInfo = model.getPeerInfo(row);
SwingUtilities.invokeLater(() -> new PeerInfoWindow(peerInfo).setVisible(true));
System.out.println(peerInfo);
}
}
});
table.setFont(new Font("Courier New", Font.PLAIN, 15));
table.setForeground(Color.GRAY);
table.setTableHeader(null);
TableCellRenderer tcr = table.getDefaultRenderer(String.class);
DefaultTableCellRenderer renderer = (DefaultTableCellRenderer) tcr;
renderer.setHorizontalAlignment(SwingConstants.CENTER);
table.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
table.setCellSelectionEnabled(true);
table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
table.getColumnModel().getColumn(0).setPreferredWidth(60);
table.getColumnModel().getColumn(1).setPreferredWidth(200);
table.getColumnModel().getColumn(2).setPreferredWidth(160);
table.getColumnModel().getColumn(3).setPreferredWidth(60);
table.setRowMargin(3);
table.setRowHeight(50);
table.setShowHorizontalLines(true);
table.setShowVerticalLines(true);
table.setGridColor(new Color(230, 230, 230));
// Add the table to a scrolling pane
scrollPane = new JScrollPane(table);
scrollPane.getViewport().setBackground(Color.WHITE);
topPanel.add(scrollPane, BorderLayout.CENTER);
updater.scheduleAtFixedRate(new TimerTask() {
public void run() {
table.revalidate();
table.repaint();
}
}, 1000, 1000);
UIEthereumManager.ethereum.startPeerDiscovery();
}
public void addCloseAction() {
this.addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
toolBar.peersToggle.setSelected(false);
}
});
}
public static void main(String args[]) {
PeersTableWindow mainFrame = new PeersTableWindow(null);
mainFrame.setVisible(true);
mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}

View File

@ -1,195 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.Block;
import org.ethereum.core.Transaction;
import org.ethereum.vm.Program;
import org.ethereum.vm.ProgramInvoke;
import org.ethereum.vm.ProgramInvokeMockImpl;
import org.ethereum.vm.VM;
import org.spongycastle.util.encoders.Hex;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.util.List;
import javax.swing.*;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
/**
* @author Roman Mandeleil
* @since 02.06.2014
*/
public class ProgramPlayDialog extends JPanel implements ActionListener,
ChangeListener, Program.ProgramListener {
private List<String> outputList;
private JTextArea console;
private JSlider stepSlider;
private ProgramInvoke pi;
public ProgramPlayDialog(byte[] code) {
this(code, new ProgramInvokeMockImpl());
}
public ProgramPlayDialog(byte[] code, Transaction tx, Block lastBlock) {
// this(code, ProgramInvokeFactory.createProgramInvoke(tx, lastBlock,
// UIEthereumManager.ethereum.getRepository()));
}
public ProgramPlayDialog(byte[] code, ProgramInvoke programInvoke) {
pi = programInvoke;
outputList = new ArrayList<>();
VM vm = new VM();
Program program = new Program(code, programInvoke);
program.addListener(this);
program.fullTrace();
vm.play(program);
if (programInvoke.getRepository() != null)
programInvoke.getRepository().rollback();
doGUI();
}
public void doGUI() {
setLayout(new BoxLayout(this, BoxLayout.PAGE_AXIS));
//Create the slider.
stepSlider = new JSlider(JSlider.HORIZONTAL,
0, outputList.size() - 1, 0);
stepSlider.addChangeListener(this);
//Turn on labels at major tick marks.
stepSlider.setMajorTickSpacing(1);
if (outputList.size() > 40)
stepSlider.setMajorTickSpacing(3);
if (outputList.size() > 100)
stepSlider.setMajorTickSpacing(20);
stepSlider.setMinorTickSpacing(1);
stepSlider.setPaintTicks(true);
stepSlider.setPaintLabels(true);
stepSlider.setBorder(
BorderFactory.createEmptyBorder(0, 0, 10, 0));
Font font = new Font("Courier New", Font.PLAIN, 10);
stepSlider.setFont(font);
stepSlider.addChangeListener(this);
//Create the label that displays the animation.
int i = stepSlider.getValue();
console = new JTextArea(outputList.get(i));
console.setFont(new Font("Courier New", Font.PLAIN, 13));
console.setForeground(new Color(183, 209, 253));
console.setBackground(Color.BLACK);
console.setLineWrap(true);
stepSlider.setFocusable(true);
JScrollPane scrollPane = new JScrollPane(console,
ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS,
ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);
scrollPane.getVerticalScrollBar().setPreferredSize(new Dimension(10, 0));
add(scrollPane);
add(stepSlider);
}
public void setFocus() {
stepSlider.requestFocus();
}
@Override
public void actionPerformed(ActionEvent e) {
}
@Override
public void stateChanged(ChangeEvent e) {
JSlider source = (JSlider) e.getSource();
int step = source.getValue();
int i = source.getValue();
String out = outputList.get(i);
console.setText(out);
console.setCaretPosition(0);
}
/**
* Create the GUI and show it. For thread safety,
* this method should be invoked from the
* event-dispatching thread.
*/
public static void createAndShowGUI(byte[] runCode, final Transaction tx, Block lastBlock) {
final ProgramPlayDialog ppd;
if (tx != null)
ppd = new ProgramPlayDialog(runCode, tx, lastBlock);
else {
ppd = new ProgramPlayDialog(runCode);
}
//Create and set up the window.
JFrame frame = new JFrame("Program Draft Play");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
java.net.URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
frame.setIconImage(img);
frame.setPreferredSize(new Dimension(580, 500));
frame.setLocation(400, 200);
//Add content to the window.
frame.add(ppd, BorderLayout.CENTER);
// close event
frame.addWindowListener(new java.awt.event.WindowAdapter() {
@Override
public void windowClosing(java.awt.event.WindowEvent windowEvent) {
if (tx == null) {
ppd.pi.getRepository().close();
ppd.pi = null;
}
}
});
//Display the window.
frame.pack();
frame.setVisible(true);
ppd.setFocus();
}
@Override
public void output(String out) {
outputList.add(out);
}
public static void main(String[] args) {
/* Turn off metal's use of bold fonts */
UIManager.put("swing.boldMetal", Boolean.FALSE);
//Schedule a job for the event-dispatching thread:
//creating and showing this application's GUI.
String asmCode = "11 0 MSTORE 22 32 MSTORE 33 64 MSTORE 44 96 MSTORE 55 128 MSTORE 66 160 MSTORE 192 0 RETURN";
// final byte[] code = SerpentCompiler.compileAssemblyToMachine(asmCode);
final byte[] code = Hex.decode("7f4e616d65526567000000000000000000000000000000000000000000000000003057307f4e616d6552656700000000000000000000000000000000000000000000000000573360455760415160566000396000f20036602259604556330e0f600f5933ff33560f601e5960003356576000335700604158600035560f602b590033560f60365960003356573360003557600035335700");
SwingUtilities.invokeLater(() -> createAndShowGUI(code, null, null));
}
}

View File

@ -1,478 +0,0 @@
package org.ethereum.gui;
import org.ethereum.serpent.SerpentCompiler;
import org.fife.ui.rsyntaxtextarea.AbstractTokenMakerFactory;
import org.fife.ui.rsyntaxtextarea.RSyntaxTextArea;
import org.fife.ui.rsyntaxtextarea.SyntaxScheme;
import org.fife.ui.rsyntaxtextarea.Token;
import org.fife.ui.rsyntaxtextarea.TokenMakerFactory;
import org.fife.ui.rtextarea.RTextScrollPane;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.InputEvent;
import java.awt.event.KeyEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileWriter;
import java.io.IOException;
import java.net.URL;
import java.util.Scanner;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.swing.*;
import static org.ethereum.config.SystemProperties.CONFIG;
/**
* @author Roman Mandeleil
* @since 24.04.14
*/
public class SerpentEditor extends JFrame {
private Logger logger = LoggerFactory.getLogger("gui");
private String codeSample = "\n\n\n" +
"" +
"if !contract.storage[msg.data[0]]:\n" +
" contract.storage[msg.data[0]] = msg.data[1]\n" +
" return(1)\n" +
"else:\n" +
" return(0)\n";
private String codeSample2 = "\n\n\n" +
"" +
"\n" +
"\n" +
"a=block.gaslimit\n" +
"b = block.difficulty\n" +
"if 10*2+5 > 15:\n" +
" b = 2\n" +
"elif 2*6+5 < a ^ 6:\n" +
" c = 4\n" +
"else:\n" +
" d = 5\n" +
" \n" +
"\n" +
"return(0)\n";
private String defaultCode = "\n" +
"\n" +
"init: \n" +
"\n" +
" // [init block] - executed once when contract\n" +
" // being initialized.\n" +
" contract.storage[999] = 3 \n" +
"\n" +
"code:\n" +
"\n" +
" // [code block] - the actual code\n" +
" // executed when the call msg\n" +
" // hit the peer\n" +
" a = contract.storage[999]\n" +
" b = msg.data[a]\n";
private final RSyntaxTextArea codeArea;
private static final long serialVersionUID = 1L;
private final JSplitPane splitPanel;
private final JTextArea result;
private final JPanel contentPane;
private JFileChooser fileChooser = null;
private ToolBar toolBar = null;
public SerpentEditor(ToolBar toolBar) {
this.toolBar = toolBar;
addCloseAction();
contentPane = new JPanel(new BorderLayout());
URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
this.setLocation(30, 70);
AbstractTokenMakerFactory atmf = (AbstractTokenMakerFactory) TokenMakerFactory.getDefaultInstance();
atmf.putMapping("text/serpent", "org.ethereum.gui.SerpentTokenMaker");
codeArea = new RSyntaxTextArea(32, 80);
codeArea.setSyntaxEditingStyle("text/serpent");
codeArea.setCodeFoldingEnabled(true);
codeArea.setAntiAliasingEnabled(true);
codeArea.setText(defaultCode);
changeStyleProgrammatically();
RTextScrollPane sp = new RTextScrollPane(codeArea);
sp.setFoldIndicatorEnabled(true);
contentPane.setLayout(new BorderLayout());
splitPanel = new JSplitPane(JSplitPane.VERTICAL_SPLIT);
splitPanel.setOneTouchExpandable(true);
splitPanel.setDividerSize(5);
splitPanel.setContinuousLayout(true);
contentPane.add(splitPanel, BorderLayout.CENTER);
splitPanel.add(sp);
result = new JTextArea();
result.setLineWrap(true);
result.setWrapStyleWord(true);
result.setVisible(false);
splitPanel.add(result);
JPanel controlsPanel = new JPanel();
FlowLayout fl = new FlowLayout(FlowLayout.CENTER, 10, 5);
// fl.setAlignment(FlowLayout.RIGHT);
controlsPanel.setLayout(fl);
controlsPanel.setMaximumSize(new Dimension(10000, 20));
controlsPanel.setPreferredSize(new Dimension(600, 20));
controlsPanel.setMinimumSize(new Dimension(1, 20));
contentPane.add(controlsPanel, BorderLayout.SOUTH);
createToolBar();
setContentPane(contentPane);
setTitle("Serpent Editor");
pack();
this.revalidate();
this.repaint();
}
private void changeStyleProgrammatically() {
// Set the font for all token types.
// Change a few things here and there.
SyntaxScheme scheme = codeArea.getSyntaxScheme();
scheme.getStyle(Token.RESERVED_WORD).background = Color.white;
scheme.getStyle(Token.RESERVED_WORD).foreground = Color.BLUE.darker();
scheme.getStyle(Token.IDENTIFIER).foreground = Color.black;
scheme.getStyle(Token.RESERVED_WORD_2).background = Color.WHITE;
scheme.getStyle(Token.RESERVED_WORD_2).foreground = Color.MAGENTA.darker();
scheme.getStyle(Token.ANNOTATION).foreground = Color.ORANGE;
scheme.getStyle(Token.ANNOTATION).background = Color.black;
scheme.getStyle(Token.ANNOTATION).font = new Font("Consolas", Font.BOLD, 15);
// scheme.getStyle(Token.LITERAL_STRING_DOUBLE_QUOTE).underline = true;
// scheme.getStyle(Token.LITERAL_NUMBER_HEXADECIMAL).underline = true;
// scheme.getStyle(Token.LITERAL_NUMBER_HEXADECIMAL).background = Color.pink;
scheme.getStyle(Token.COMMENT_EOL).foreground = Color.lightGray;
// scheme.getStyle(Token.COMMENT_EOL).font = new Font("Georgia", Font.ITALIC, 10);
codeArea.revalidate();
}
protected void compileCode() {
String code = codeArea.getText();
String asmResult = "";
Pattern pattern = Pattern.compile("(.*?)init:(.*?)code:(.*?)", Pattern.DOTALL);
Matcher matcher = pattern.matcher(code);
try {
if (matcher.find()) {
asmResult = SerpentCompiler.compileFullNotion(codeArea.getText());
asmResult = GUIUtils.getStyledAsmCode(asmResult);
} else {
asmResult = SerpentCompiler.compile(codeArea.getText());
}
} catch (Throwable th) {
logger.error(th.getMessage(), th);
splitPanel.setDividerLocation(0.8);
result.setVisible(true);
result.setText(th.getMessage());
result.setForeground(Color.RED);
return;
}
result.setForeground(Color.BLACK.brighter());
result.setVisible(true);
result.setText(asmResult);
splitPanel.setDividerLocation(
1 - result.getPreferredSize().getHeight() / codeArea.getPreferredSize().getHeight());
this.repaint();
}
protected byte[] prepareCodeForSend() {
String asmResult = "";
byte[] machineCode = null;
try {
String code = codeArea.getText();
Pattern pattern = Pattern.compile("(.*?)init:(.*?)code:(.*?)", Pattern.DOTALL);
Matcher matcher = pattern.matcher(code);
if (matcher.find()) {
asmResult = SerpentCompiler.compileFullNotion(codeArea.getText());
machineCode = SerpentCompiler.compileFullNotionAssemblyToMachine(asmResult);
} else {
asmResult = SerpentCompiler.compile(codeArea.getText());
machineCode = SerpentCompiler.compileAssemblyToMachine(asmResult);
machineCode = SerpentCompiler.encodeMachineCodeForVMRun(machineCode, null);
}
} catch (Throwable th) {
logger.error(th.getMessage(), th);
splitPanel.setDividerLocation(0.7);
result.setVisible(true);
result.setText(th.getMessage());
result.setForeground(Color.RED);
return null;
}
return machineCode;
}
public void createToolBar() {
JToolBar toolbar = new JToolBar(SwingConstants.VERTICAL);
toolbar.putClientProperty("JToolBar.isRollover", Boolean.TRUE);
toolbar.setFloatable(false);
final JPanel mainContentPane = SerpentEditor.this.contentPane;
{
URL url = ClassLoader.getSystemResource("buttons/open-file.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
ImageIcon imageIcon = new ImageIcon(img);
final JButton button = new JButton(imageIcon);
button.setToolTipText("Open File < Ctrl + O >");
Action openFile = new AbstractAction() {
@Override
public void actionPerformed(ActionEvent e) {
button.doClick();
}
};
mainContentPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).
put(KeyStroke.getKeyStroke(KeyEvent.VK_O, InputEvent.CTRL_DOWN_MASK),
"OpenFileButton");
mainContentPane.getActionMap().put("OpenFileButton", openFile);
button.addActionListener(e -> {
File file = callFileChooser();
try {
if (file == null)
return;
String content = new Scanner(file).useDelimiter("\\Z").next();
codeArea.setText(content);
} catch (FileNotFoundException e1) {
logger.error(e1.getMessage(), e1);
} catch (java.util.NoSuchElementException e2) {
// don't worry it's just the file is empty
codeArea.setText("");
}
});
toolbar.add(button);
}
{
URL url = ClassLoader.getSystemResource("buttons/save-file.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
ImageIcon imageIcon = new ImageIcon(img);
final JButton button = new JButton(imageIcon);
button.setToolTipText("Save File < Ctrl + S >");
Action saveNewFile = new AbstractAction() {
@Override
public void actionPerformed(ActionEvent e) {
button.doClick();
}
};
mainContentPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).
put(KeyStroke.getKeyStroke(KeyEvent.VK_S, InputEvent.CTRL_DOWN_MASK | InputEvent.SHIFT_DOWN_MASK),
"OpenSaveButtonAlways");
mainContentPane.getActionMap().put("OpenSaveButtonAlways", saveNewFile);
Action saveFile = new AbstractAction() {
@Override
public void actionPerformed(ActionEvent e) {
button.doClick();
}
};
mainContentPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).
put(KeyStroke.getKeyStroke(KeyEvent.VK_S, InputEvent.CTRL_DOWN_MASK),
"OpenSaveButton");
mainContentPane.getActionMap().put("OpenSaveButton", saveFile);
button.addActionListener(e -> {
File file = null;
if (e.getModifiers() == (InputEvent.CTRL_MASK | InputEvent.SHIFT_MASK)) {
file = callFileChooser();
if (file == null)
return;
} else if (fileChooser == null
|| fileChooser.getSelectedFile() == null) {
file = callFileChooser();
if (file == null)
return;
} else {
file = fileChooser.getSelectedFile();
}
try {
BufferedWriter out = new BufferedWriter(new FileWriter(file), 32768);
out.write(codeArea.getText());
out.close();
} catch (IOException e1) {
logger.error(e1.getMessage(), e1);
}
});
toolbar.add(button);
}
toolbar.addSeparator();
{
URL url = ClassLoader.getSystemResource("buttons/compile.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
ImageIcon imageIcon = new ImageIcon(img);
final JButton button = new JButton(imageIcon);
button.setToolTipText("Compile the contract < Ctrl + F9 >");
Action compile = new AbstractAction() {
@Override
public void actionPerformed(ActionEvent e) {
button.doClick();
}
};
mainContentPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).
put(KeyStroke.getKeyStroke(KeyEvent.VK_F9, InputEvent.CTRL_DOWN_MASK),
"CompileButton");
mainContentPane.getActionMap().put("CompileButton", compile);
button.addActionListener(e -> compileCode());
toolbar.add(button);
}
{
URL url = ClassLoader.getSystemResource("buttons/deploy.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
ImageIcon imageIcon = new ImageIcon(img);
final JButton button = new JButton(imageIcon);
button.setToolTipText("Deploy contract to the chain < Ctrl + Shift + F9 >");
Action deploy = new AbstractAction() {
@Override
public void actionPerformed(ActionEvent e) {
button.doClick();
}
};
mainContentPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).
put(KeyStroke.getKeyStroke(KeyEvent.VK_F9,
InputEvent.SHIFT_DOWN_MASK | InputEvent.CTRL_DOWN_MASK),
"DeployButton");
mainContentPane.getActionMap().put("DeployButton", deploy);
button.addActionListener(e -> {
byte[] machineCode = prepareCodeForSend();
if (machineCode == null) return;
ContractSubmitDialog payOutDialog =
new ContractSubmitDialog((Frame) SwingUtilities.getAncestorOfClass(JFrame.class,
contentPane), machineCode);
});
toolbar.add(button);
}
{
URL url = ClassLoader.getSystemResource("buttons/call.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
ImageIcon imageIcon = new ImageIcon(img);
final JButton button = new JButton(imageIcon);
button.setToolTipText("Call contract <Ctrl + F8>");
Action call = new AbstractAction() {
@Override
public void actionPerformed(ActionEvent e) {
button.doClick();
}
};
mainContentPane.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).
put(KeyStroke.getKeyStroke(KeyEvent.VK_F8,
InputEvent.CTRL_DOWN_MASK),
"CallButton");
mainContentPane.getActionMap().put("CallButton", call);
button.addActionListener(e -> {
ContractCallDialog payOutDialog = new ContractCallDialog(
(Frame) SwingUtilities.getAncestorOfClass(
JFrame.class, contentPane));
});
toolbar.add(button);
}
this.contentPane.add(toolbar, BorderLayout.EAST);
}
protected File callFileChooser() {
File file = null;
if (fileChooser == null) {
fileChooser = new JFileChooser(CONFIG.samplesDir());
fileChooser.setMultiSelectionEnabled(false);
}
switch (fileChooser.showOpenDialog(SerpentEditor.this)) {
case JFileChooser.APPROVE_OPTION:
file = fileChooser.getSelectedFile();
break;
}
return file;
}
public void addCloseAction() {
this.addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
toolBar.editorToggle.setSelected(false);
}
});
}
public static void main(String[] args) {
// Start all Swing applications on the EDT.
SwingUtilities.invokeLater(() -> new SerpentEditor(null).setVisible(true));
}
}

View File

@ -1,504 +0,0 @@
package org.ethereum.gui;
import org.ethereum.vm.OpCode;
import org.fife.ui.rsyntaxtextarea.AbstractTokenMaker;
import org.fife.ui.rsyntaxtextarea.RSyntaxUtilities;
import org.fife.ui.rsyntaxtextarea.Token;
import org.fife.ui.rsyntaxtextarea.TokenMap;
import javax.swing.text.Segment;
/**
* @author Roman Mandeleil
* @since 24.04.14
*/
public class SerpentTokenMaker extends AbstractTokenMaker {
// http://fifesoft.com/rsyntaxtextarea/doc/CustomSyntaxHighlighting.html
protected final String operators = ".@:*<>=?|!";
private int currentTokenStart;
private int currentTokenType;
private boolean bracketVariable; // Whether a variable is of the format %{...}
/**
* Constructor.
*/
public SerpentTokenMaker() {
super(); // Initializes tokensToHighlight.
}
/**
* Checks the token to give it the exact ID it deserves before
* being passed up to the super method.
*
* @param segment <code>Segment</code> to get text from.
* @param start Start offset in <code>segment</code> of token.
* @param end End offset in <code>segment</code> of token.
* @param tokenType The token's type.
* @param startOffset The offset in the document at which the token occurs.
*/
@Override
public void addToken(Segment segment, int start, int end, int tokenType, int startOffset) {
switch (tokenType) {
// Since reserved words, functions, and data types are all passed
// into here as "identifiers," we have to see what the token
// really is...
case Token.IDENTIFIER:
int value = wordsToHighlight.get(segment, start, end);
if (value != -1)
tokenType = value;
break;
case Token.ANNOTATION:
value = wordsToHighlight.get(segment, start, end);
if (value != -1)
tokenType = value;
break;
}
super.addToken(segment, start, end, tokenType, startOffset);
}
/**
* Returns the text to place at the beginning and end of a
* line to "comment" it in a this programming language.
*
* @return The start and end strings to add to a line to "comment"
* it out.
*/
@Override
public String[] getLineCommentStartAndEnd() {
return new String[]{"#", null};
}
/**
* Returns whether tokens of the specified type should have "mark
* occurrences" enabled for the current programming language.
*
* @param type The token type.
* @return Whether tokens of this type should have "mark occurrences"
* enabled.
*/
@Override
public boolean getMarkOccurrencesOfTokenType(int type) {
return type == Token.IDENTIFIER || type == Token.VARIABLE;
}
/**
* Returns the words to highlight for Windows batch files.
*
* @return A <code>TokenMap</code> containing the words to highlight for
* Windows batch files.
* @see org.fife.ui.rsyntaxtextarea.AbstractTokenMaker#getWordsToHighlight
*/
@Override
public TokenMap getWordsToHighlight() {
TokenMap tokenMap = new TokenMap(false); // Ignore case.
int reservedWord = Token.RESERVED_WORD;
tokenMap.put("set", reservedWord);
tokenMap.put("if", reservedWord);
tokenMap.put("else", reservedWord);
tokenMap.put("elif", reservedWord);
tokenMap.put("seq", reservedWord);
tokenMap.put("while", reservedWord);
tokenMap.put("byte", reservedWord);
tokenMap.put("access", reservedWord);
tokenMap.put("arrset", reservedWord);
tokenMap.put("set_and_inc", reservedWord);
tokenMap.put("array", reservedWord);
tokenMap.put("getch", reservedWord);
tokenMap.put("setch", reservedWord);
tokenMap.put("string", reservedWord);
tokenMap.put("send", reservedWord);
tokenMap.put("create", reservedWord);
tokenMap.put("sha3", reservedWord);
tokenMap.put("sha3bytes", reservedWord);
tokenMap.put("sload", reservedWord);
tokenMap.put("sstore", reservedWord);
tokenMap.put("calldataload", reservedWord);
tokenMap.put("id", reservedWord);
tokenMap.put("return", reservedWord);
tokenMap.put("suicide", reservedWord);
tokenMap.put("stop", reservedWord);
int function = Token.FUNCTION;
tokenMap.put("msg", function);
tokenMap.put("data", function);
tokenMap.put("contract", function);
tokenMap.put("storage", function);
tokenMap.put("block", function);
tokenMap.put("tx", function);
// ALL the assembly tokens
int reservedWord2 = Token.RESERVED_WORD_2;
for (OpCode value : OpCode.values()) {
tokenMap.put(value.name(), reservedWord2);
tokenMap.put("[asm", reservedWord2);
tokenMap.put("asm]", reservedWord2);
}
int dataType = Token.ANNOTATION;
tokenMap.put("init", dataType);
tokenMap.put("code", dataType);
return tokenMap;
}
/**
* Returns a peerInfoList of tokens representing the given text.
*
* @param text The text to break into tokens.
* @param startTokenType The token with which to start tokenizing.
* @param startOffset The offset at which the line of tokens begins.
* @return A linked peerInfoList of tokens representing <code>text</code>.
*/
public Token getTokenList(Segment text, int startTokenType, final int startOffset) {
resetTokenList();
char[] array = text.array;
int offset = text.offset;
int count = text.count;
int end = offset + count;
// See, when we find a token, its starting position is always of the form:
// 'startOffset + (currentTokenStart-offset)'; but since startOffset
// offset are constant, tokens' starting positions become:
// 'newStartOffset+currentTokenStart' for one less subtraction operation.
int newStartOffset = startOffset - offset;
currentTokenStart = offset;
currentTokenType = startTokenType;
//beginning:
for (int i = offset; i < end; i++) {
char c = array[i];
switch (currentTokenType) {
case Token.NULL:
currentTokenStart = i; // Starting a new token here.
switch (c) {
case '#':
currentTokenType = Token.COMMENT_EOL;
break;
case ' ':
case '\t':
currentTokenType = Token.WHITESPACE;
break;
case '"':
currentTokenType = Token.ERROR_STRING_DOUBLE;
break;
// The "separators".
case '(':
case ')':
addToken(text, currentTokenStart, i, Token.SEPARATOR, newStartOffset + currentTokenStart);
currentTokenType = Token.NULL;
break;
// The "separators2".
case ',':
case ';':
addToken(text, currentTokenStart, i, Token.IDENTIFIER, newStartOffset + currentTokenStart);
currentTokenType = Token.NULL;
break;
// Newer version of EOL comments, or a label
case ':':
// If this will be the first token added, it is
// a new-style comment or a label
if (firstToken == null) {
if (i < end - 1 && array[i + 1] == ':') { // new-style comment
currentTokenType = Token.COMMENT_EOL;
} else { // Label
currentTokenType = Token.PREPROCESSOR;
}
} else { // Just a colon
currentTokenType = Token.IDENTIFIER;
}
break;
// Newer version of EOL comments, or a label
default:
// Just to speed things up a tad, as this will usually be the case (if spaces above failed).
if (RSyntaxUtilities.isLetterOrDigit(c) || c == '\\') {
currentTokenType = Token.IDENTIFIER;
break;
}
int indexOf = operators.indexOf(c, 0);
if (indexOf > -1) {
addToken(text, currentTokenStart, i, Token.OPERATOR, newStartOffset +
currentTokenStart);
currentTokenType = Token.NULL;
break;
} else {
currentTokenType = Token.IDENTIFIER;
break;
}
} // End of switch (c).
break;
case Token.WHITESPACE:
switch (c) {
case '/':
addToken(text, currentTokenStart, i - 1,
Token.COMMENT_EOL, newStartOffset + currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.COMMENT_EOL;
break;
case ' ':
case '\t':
break; // Still whitespace.
case '"':
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
break;
// The "separators".
case '(':
case ')':
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
break;
// The "separators2".
case ',':
case ';':
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
// Newer version of EOL comments, or a label
case ':':
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
currentTokenStart = i;
// If the previous (whitespace) token was the first token
// added, this is a new-style comment or a label
if (firstToken.getNextToken() == null) {
if (i < end - 1 && array[i + 1] == ':') { // new-style comment
currentTokenType = Token.COMMENT_EOL;
} else { // Label
currentTokenType = Token.PREPROCESSOR;
}
} else { // Just a colon
currentTokenType = Token.IDENTIFIER;
}
break;
default: // Add the whitespace token and start anew.
addToken(text, currentTokenStart, i - 1, Token.WHITESPACE, newStartOffset +
currentTokenStart);
currentTokenStart = i;
// Just to speed things up a tad, as this will usually be the case (if spaces above failed).
if (RSyntaxUtilities.isLetterOrDigit(c) || c == '\\') {
currentTokenType = Token.IDENTIFIER;
break;
}
int indexOf = operators.indexOf(c, 0);
if (indexOf > -1) {
addToken(text, currentTokenStart, i, Token.OPERATOR, newStartOffset +
currentTokenStart);
currentTokenType = Token.NULL;
break;
} else {
currentTokenType = Token.IDENTIFIER;
}
} // End of switch (c).
break;
default: // Should never happen
case Token.IDENTIFIER:
switch (c) {
case ' ':
case '\t':
// Check for REM comments.
if (i - currentTokenStart == 3 &&
(array[i - 3] == 'r' || array[i - 3] == 'R') &&
(array[i - 2] == 'e' || array[i - 2] == 'E') &&
(array[i - 1] == 'm' || array[i - 1] == 'M')) {
currentTokenType = Token.COMMENT_EOL;
break;
}
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.WHITESPACE;
break;
case '"':
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
currentTokenStart = i;
currentTokenType = Token.ERROR_STRING_DOUBLE;
break;
// Should be part of identifiers, but not at end of "REM".
case '\\':
// Check for REM comments.
if (i - currentTokenStart == 3 &&
(array[i - 3] == 'r' || array[i - 3] == 'R') &&
(array[i - 2] == 'e' || array[i - 2] == 'E') &&
(array[i - 1] == 'm' || array[i - 1] == 'M')) {
currentTokenType = Token.COMMENT_EOL;
}
break;
// case '.':
case '_':
break; // Characters good for identifiers.
// The "separators".
case '(':
case ')':
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.SEPARATOR, newStartOffset + i);
currentTokenType = Token.NULL;
break;
// The "separators2".
case ',':
case ';':
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.IDENTIFIER, newStartOffset + i);
currentTokenType = Token.NULL;
break;
default:
// Just to speed things up a tad, as this will usually be the case.
if (RSyntaxUtilities.isLetterOrDigit(c) || c == '\\') {
break;
}
int indexOf = operators.indexOf(c);
if (indexOf > -1) {
addToken(text, currentTokenStart, i - 1, Token.IDENTIFIER, newStartOffset +
currentTokenStart);
addToken(text, i, i, Token.OPERATOR, newStartOffset + i);
currentTokenType = Token.NULL;
break;
}
// Otherwise, fall through and assume we're still okay as an IDENTIFIER...
} // End of switch (c).
break;
case Token.COMMENT_EOL:
if (i + 1 >= array.length)
break;
char nextC = array[i + 1];
if (nextC == '/') {
i = end - 1;
addToken(text, currentTokenStart, i, Token.COMMENT_EOL, newStartOffset + currentTokenStart);
// We need to set token type to null so at the bottom we don't add one more token.
currentTokenType = Token.NULL;
}
break;
case Token.PREPROCESSOR: // Used for labels
i = end - 1;
addToken(text, currentTokenStart, i, Token.PREPROCESSOR, newStartOffset + currentTokenStart);
// We need to set token type to null so at the bottom we don't add one more token.
currentTokenType = Token.NULL;
break;
case Token.ERROR_STRING_DOUBLE:
if (c == '"') {
addToken(text, currentTokenStart, i, Token.LITERAL_STRING_DOUBLE_QUOTE, newStartOffset + currentTokenStart);
currentTokenStart = i + 1;
currentTokenType = Token.NULL;
}
// Otherwise, we're still an unclosed string...
break;
case Token.VARIABLE:
if (i == currentTokenStart + 1) { // first character after '%'.
bracketVariable = false;
switch (c) {
case '{':
bracketVariable = true;
break;
default:
if (RSyntaxUtilities.isLetter(c) || c == ' ') { // No tab, just space; spaces are okay in variable names.
break;
} else if (RSyntaxUtilities.isDigit(c)) { // Single-digit command-line argument ("%1").
addToken(text, currentTokenStart, i, Token.VARIABLE, newStartOffset + currentTokenStart);
currentTokenType = Token.NULL;
break;
} else { // Anything else, ???.
addToken(text, currentTokenStart, i - 1, Token.VARIABLE, newStartOffset + currentTokenStart); // ???
i--;
currentTokenType = Token.NULL;
break;
}
} // End of switch (c).
} else { // Character other than first after the '%'.
if (bracketVariable == true) {
if (c == '}') {
addToken(text, currentTokenStart, i, Token.VARIABLE, newStartOffset + currentTokenStart);
currentTokenType = Token.NULL;
}
}
break;
}
break;
} // End of switch (currentTokenType).
} // End of for (int i=offset; i<end; i++).
// Deal with the (possibly there) last token.
if (currentTokenType != Token.NULL) {
// Check for REM comments.
if (end - currentTokenStart == 3 &&
(array[end - 3] == 'r' || array[end - 3] == 'R') &&
(array[end - 2] == 'e' || array[end - 2] == 'E') &&
(array[end - 1] == 'm' || array[end - 1] == 'M')) {
currentTokenType = Token.COMMENT_EOL;
}
addToken(text, currentTokenStart, end - 1, currentTokenType, newStartOffset + currentTokenStart);
}
addNullToken();
// Return the first token in our linked peerInfoList.
return firstToken;
}
}

View File

@ -1,310 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.AccountState;
import org.ethereum.db.ContractDetails;
import org.ethereum.facade.Repository;
import org.ethereum.util.Utils;
import org.ethereum.vm.DataWord;
import org.ethereum.vm.Program;
import org.spongycastle.util.encoders.Hex;
import java.awt.*;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.math.BigInteger;
import java.net.URL;
import java.util.Map;
import javax.swing.*;
import javax.swing.table.AbstractTableModel;
@SuppressWarnings("unchecked")
public class StateExplorerWindow extends JFrame {
private ToolBar toolBar = null;
private JTextField txfAccountAddress;
private WindowTextArea txaPrinter;
private JButton btnPlayCode;
private AccountsListWindow accountsListWindow;
ProgramPlayDialog codePanel;
private JTable tblStateDataTable;
private StateDataTableModel dataModel;
String[] dataTypes = {"String", "Hex", "Number"};
public StateExplorerWindow(ToolBar toolBar) {
this.toolBar = toolBar;
URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
setTitle("State Explorer");
setSize(700, 530);
setLocation(50, 180);
setResizable(false);
/*
* top search panel
*/
JPanel panel = new JPanel();
getContentPane().add(panel);
Box horizontalBox = Box.createHorizontalBox();
panel.add(horizontalBox);
java.net.URL imageURL = ClassLoader.getSystemResource("buttons/list.png");
ImageIcon image = new ImageIcon(imageURL);
JToggleButton btnListAccounts = new JToggleButton("");
btnListAccounts.setIcon(image);
btnListAccounts.setContentAreaFilled(true);
btnListAccounts.setToolTipText("Serpent Editor");
btnListAccounts.setBackground(Color.WHITE);
btnListAccounts.setBorderPainted(false);
btnListAccounts.setFocusPainted(false);
btnListAccounts.setCursor(new Cursor(Cursor.HAND_CURSOR));
btnListAccounts.addItemListener(e -> SwingUtilities.invokeLater(() -> {
if (accountsListWindow == null)
accountsListWindow = new AccountsListWindow();
accountsListWindow.setVisible(true);
}));
horizontalBox.add(btnListAccounts);
txfAccountAddress = new JTextField();
horizontalBox.add(txfAccountAddress);
txfAccountAddress.setColumns(30);
JButton btnSearch = new JButton("Search");
horizontalBox.add(btnSearch);
btnSearch.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
byte[] addr = Utils.addressStringToBytes(txfAccountAddress.getText());
if (addr != null)
searchAccount(addr);
}
});
btnPlayCode = new JButton("Play Code");
horizontalBox.add(btnPlayCode);
btnPlayCode.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
byte[] addr = Utils.addressStringToBytes(txfAccountAddress.getText());
if (addr != null) {
Repository repository = UIEthereumManager.ethereum.getRepository();
byte[] code = repository.getCode(addr);
if (code != null)
ProgramPlayDialog.createAndShowGUI(code, null, null);
}
}
});
/*
* center text panel
*/
JPanel centerPanel = new JPanel();
panel.add(centerPanel);
txaPrinter = new WindowTextArea();
centerPanel.add(txaPrinter);
/*
* bottom data panel
*/
// data type choice boxes
Box Hbox = Box.createHorizontalBox();
panel.add(Hbox);
Box VBox1 = Box.createVerticalBox();
JLabel l1 = new JLabel("Key Encoding");
l1.setAlignmentX(Component.CENTER_ALIGNMENT);
JComboBox cmbKey = new JComboBox(dataTypes);
cmbKey.setSelectedIndex(1);
cmbKey.addActionListener(e -> {
JComboBox cmb = (JComboBox) e.getSource();
DataEncodingType t = DataEncodingType.getTypeFromString((String) cmb.getSelectedItem());
dataModel.setKeyEncoding(t);
});
VBox1.add(l1);
VBox1.add(cmbKey);
Box VBox2 = Box.createVerticalBox();
VBox2.setAlignmentX(LEFT_ALIGNMENT);
JLabel l2 = new JLabel("Value Encoding");
l2.setAlignmentX(Component.CENTER_ALIGNMENT);
JComboBox cmbValue = new JComboBox(dataTypes);
cmbValue.setSelectedIndex(1);
cmbValue.addActionListener(e -> {
JComboBox cmb = (JComboBox) e.getSource();
DataEncodingType t = DataEncodingType.getTypeFromString((String) cmb.getSelectedItem());
dataModel.setValueEncoding(t);
});
VBox2.add(l2);
VBox2.add(cmbValue);
Hbox.add(VBox1);
JPanel spacer = new JPanel();
FlowLayout flowLayout = (FlowLayout) spacer.getLayout();
flowLayout.setHgap(100);
Hbox.add(spacer);
Hbox.add(VBox2);
// table
tblStateDataTable = new JTable();
dataModel = new StateDataTableModel();
tblStateDataTable.setModel(dataModel);
JScrollPane scrollPane = new JScrollPane(tblStateDataTable);
scrollPane.setPreferredSize(new Dimension(600, 200));
panel.add(scrollPane);
}
private void searchAccount(byte[] add) {
txaPrinter.clean();
txaPrinter.println(accountDetailsString(add, dataModel));
}
private String accountDetailsString(byte[] account, StateDataTableModel dataModel) {
String ret = "";
// 1) print account address
ret = "Account: " + Hex.toHexString(account) + "\n";
//2) print state
Repository repository = UIEthereumManager.ethereum.getRepository();
AccountState state = repository.getAccountState(account);
if (state != null)
ret += state.toString() + "\n";
//3) print storage
ContractDetails contractDetails = repository.getContractDetails(account);
if (contractDetails != null) {
Map<DataWord, DataWord> accountStorage = contractDetails.getStorage();
dataModel.setData(accountStorage);
}
//4) code print
byte[] code = repository.getCode(account);
if (code != null) {
ret += "\n\nCode:\n";
ret += Program.stringify(code, 0, "");
}
return ret;
}
private class StateDataTableModel extends AbstractTableModel {
Map<DataWord, DataWord> data;
DataEncodingType keyEncodingType = DataEncodingType.HEX;
DataEncodingType valueEncodingType = DataEncodingType.HEX;
String[] columns = new String[]{"Key", "Value"};
public StateDataTableModel() {
}
public StateDataTableModel(Map<DataWord, DataWord> initData) {
setData(initData);
}
public void setData(Map<DataWord, DataWord> initData) {
data = initData;
fireTableDataChanged();
}
public void setKeyEncoding(DataEncodingType type) {
keyEncodingType = type;
fireTableDataChanged();
}
public void setValueEncoding(DataEncodingType type) {
valueEncodingType = type;
fireTableDataChanged();
}
@Override
public String getColumnName(int column) {
return columns[column];
}
@Override
public int getRowCount() {
return data == null ? 0 : data.size();
}
@Override
public int getColumnCount() {
return columns.length;
}
@Override
public Object getValueAt(int rowIndex, int columnIndex) {
DataWord key = (DataWord) this.data.keySet().toArray()[rowIndex];
if (columnIndex == 0) {
return getDataWithEncoding(key.getData(), keyEncodingType);
} else {
DataWord value = this.data.get(key);
return getDataWithEncoding(value.getData(), valueEncodingType);
}
}
private String getDataWithEncoding(byte[] data, DataEncodingType enc) {
switch (enc) {
case STRING:
return new String(data);
case HEX:
return Hex.toHexString(data);
case NUMBER:
return new BigInteger(data).toString();
}
return data.toString();
}
}
private enum DataEncodingType {
STRING,
HEX,
NUMBER;
static public DataEncodingType getTypeFromString(String value) {
switch (value) {
case "String":
return STRING;
case "Hex":
return HEX;
case "Number":
return NUMBER;
}
return STRING;
}
}
private class WindowTextArea extends TextArea {
public WindowTextArea() {
super();
}
public void println(String txt) {
setText(getText() + txt + "\n");
}
public void clean() {
setText("");
}
}
public static void main(String[] args) {
// Start all Swing applications on the EDT.
SwingUtilities.invokeLater(() -> new StateExplorerWindow(null).setVisible(true));
}
}

View File

@ -1,242 +0,0 @@
package org.ethereum.gui;
import org.ethereum.config.SystemProperties;
import org.ethereum.facade.Ethereum;
import org.ethereum.util.Utils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.awt.*;
import java.awt.event.ItemEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import javax.swing.*;
/**
* @author Roman Mandeleil
* @since 30.04.14
*/
public class ToolBar extends JFrame {
private Logger introLogger = LoggerFactory.getLogger("Intro");
private ConnectionConsoleWindow connectionConsoleWindow = null;
private PeersTableWindow mainFrame = null;
private BlockChainTable blockchainWindow = null;
private WalletWindow walletWindow = null;
private SerpentEditor serpentEditor = null;
private StateExplorerWindow stateExplorerWindow = null;
JToggleButton editorToggle;
JToggleButton logToggle;
JToggleButton peersToggle;
JToggleButton chainToggle;
JToggleButton walletToggle;
JToggleButton stateExplorer;
public ToolBar() throws HeadlessException {
String version = SystemProperties.CONFIG.projectVersion();
introLogger.info("");
introLogger.info("|Ξ| EthereumJ [v" + version + "]");
introLogger.info("|Ξ| Code by Roman Mandeleil, (c) 2014.");
introLogger.info("|Ξ| Contribution: Nick Savers ");
introLogger.info("|Ξ| Based on a design by Vitalik Buterin.");
introLogger.info("");
introLogger.info("java.version: " + System.getProperty("java.version"));
introLogger.info("java.home: " + System.getProperty("java.home"));
introLogger.info("java.vendor: " + System.getProperty("java.vendor"));
introLogger.info("");
if (Utils.JAVA_VERSION < 1.7 && Utils.JAVA_VERSION != 0) {
introLogger.info("EthereumJ support version 1.7 and higher of Java Runtime please update");
System.exit(0);
}
final JPanel cp = new JPanel(new FlowLayout());
cp.setBackground(Color.WHITE);
java.net.URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
this.setSize(350, 200);
this.setLocation(460, 25);
this.setAlwaysOnTop(true);
this.setResizable(false);
this.setBackground(Color.WHITE);
setTitle("EthereumJ Studio");
setDefaultCloseOperation(EXIT_ON_CLOSE);
addWindowListener(new WindowAdapter() {
@Override
public void windowClosing(WindowEvent e) {
UIEthereumManager.ethereum.close();
}
});
this.setContentPane(cp);
java.net.URL imageURL_1 = ClassLoader.getSystemResource("buttons/feedly.png");
ImageIcon image_1 = new ImageIcon(imageURL_1);
java.net.URL imageURL_2 = ClassLoader.getSystemResource("buttons/winamp.png");
ImageIcon image_2 = new ImageIcon(imageURL_2);
java.net.URL imageURL_3 = ClassLoader.getSystemResource("buttons/browser.png");
ImageIcon image_3 = new ImageIcon(imageURL_3);
java.net.URL imageURL_4 = ClassLoader.getSystemResource("buttons/shazam.png");
ImageIcon image_4 = new ImageIcon(imageURL_4);
java.net.URL imageURL_5 = ClassLoader.getSystemResource("buttons/wallet.png");
ImageIcon image_5 = new ImageIcon(imageURL_5);
java.net.URL imageURL_6 = ClassLoader.getSystemResource("buttons/stateExplorer.png");
ImageIcon image_6 = new ImageIcon(imageURL_6);
editorToggle = new JToggleButton("");
editorToggle.setIcon(image_1);
editorToggle.setContentAreaFilled(true);
editorToggle.setToolTipText("Serpent Editor");
editorToggle.setBackground(Color.WHITE);
editorToggle.setBorderPainted(false);
editorToggle.setFocusPainted(false);
editorToggle.setCursor(new Cursor(Cursor.HAND_CURSOR));
editorToggle.addItemListener(e -> {
if (e.getStateChange() == ItemEvent.SELECTED) {
SwingUtilities.invokeLater(() -> {
if (serpentEditor == null)
serpentEditor = new SerpentEditor(ToolBar.this);
serpentEditor.setVisible(true);
});
} else if (e.getStateChange() == ItemEvent.DESELECTED) {
serpentEditor.setVisible(false);
}
});
logToggle = new JToggleButton();
logToggle.setIcon(image_2);
logToggle.setToolTipText("Connect");
logToggle.setContentAreaFilled(true);
logToggle.setBackground(Color.WHITE);
logToggle.setBorderPainted(false);
logToggle.setFocusPainted(false);
logToggle.setCursor(new Cursor(Cursor.HAND_CURSOR));
logToggle.addItemListener(e -> {
if (e.getStateChange() == ItemEvent.SELECTED) {
SwingUtilities.invokeLater(() -> {
if (connectionConsoleWindow == null)
connectionConsoleWindow = new ConnectionConsoleWindow(ToolBar.this);
connectionConsoleWindow.setVisible(true);
});
} else if (e.getStateChange() == ItemEvent.DESELECTED) {
connectionConsoleWindow.setVisible(false);
}
});
peersToggle = new JToggleButton();
peersToggle.setIcon(image_3);
peersToggle.setToolTipText("Peers");
peersToggle.setContentAreaFilled(true);
peersToggle.setBackground(Color.WHITE);
peersToggle.setBorderPainted(false);
peersToggle.setFocusPainted(false);
peersToggle.setCursor(new Cursor(Cursor.HAND_CURSOR));
peersToggle.addItemListener(e -> {
if (e.getStateChange() == ItemEvent.SELECTED) {
SwingUtilities.invokeLater(() -> {
if (mainFrame == null)
mainFrame = new PeersTableWindow(ToolBar.this);
mainFrame.setVisible(true);
});
} else if (e.getStateChange() == ItemEvent.DESELECTED) {
mainFrame.setVisible(false);
}
});
chainToggle = new JToggleButton();
chainToggle.setIcon(image_4);
chainToggle.setToolTipText("Block Chain");
chainToggle.setContentAreaFilled(true);
chainToggle.setBackground(Color.WHITE);
chainToggle.setBorderPainted(false);
chainToggle.setFocusPainted(false);
chainToggle.setCursor(new Cursor(Cursor.HAND_CURSOR));
chainToggle.addItemListener(e -> {
if (e.getStateChange() == ItemEvent.SELECTED) {
SwingUtilities.invokeLater(() -> {
if (blockchainWindow == null)
blockchainWindow = new BlockChainTable(ToolBar.this);
blockchainWindow.setVisible(true);
});
} else if (e.getStateChange() == ItemEvent.DESELECTED) {
blockchainWindow.setVisible(false);
}
});
walletToggle = new JToggleButton();
walletToggle.setIcon(image_5);
walletToggle.setToolTipText("Wallet");
walletToggle.setContentAreaFilled(true);
walletToggle.setBackground(Color.WHITE);
walletToggle.setBorderPainted(false);
walletToggle.setFocusPainted(false);
walletToggle.setCursor(new Cursor(Cursor.HAND_CURSOR));
walletToggle.addItemListener(
e -> {
if (e.getStateChange() == ItemEvent.SELECTED) {
SwingUtilities.invokeLater(() -> {
if (walletWindow == null)
walletWindow = new WalletWindow(ToolBar.this);
walletWindow.setVisible(true);
});
} else if (e.getStateChange() == ItemEvent.DESELECTED) {
walletWindow.setVisible(false);
}
}
);
stateExplorer = new JToggleButton();
stateExplorer.setIcon(image_6);
stateExplorer.setToolTipText("State Explorer");
stateExplorer.setContentAreaFilled(true);
stateExplorer.setBackground(Color.WHITE);
stateExplorer.setBorderPainted(false);
stateExplorer.setFocusPainted(false);
stateExplorer.setCursor(new Cursor(Cursor.HAND_CURSOR));
stateExplorer.addItemListener(
e -> {
if (e.getStateChange() == ItemEvent.SELECTED) {
SwingUtilities.invokeLater(() -> {
if (stateExplorerWindow == null)
stateExplorerWindow = new StateExplorerWindow(ToolBar.this);
stateExplorerWindow.setVisible(true);
});
} else if (e.getStateChange() == ItemEvent.DESELECTED) {
stateExplorerWindow.setVisible(false);
}
}
);
cp.add(editorToggle);
cp.add(logToggle);
cp.add(peersToggle);
cp.add(chainToggle);
cp.add(walletToggle);
cp.add(stateExplorer);
Ethereum ethereum = UIEthereumManager.ethereum;
}
public static void main(String args[]) {
SwingUtilities.invokeLater(() -> new ToolBar().setVisible(true));
}
}

View File

@ -1,63 +0,0 @@
package org.ethereum.gui;
import org.ethereum.util.ByteUtil;
import java.awt.*;
import javax.swing.*;
import javax.swing.text.BadLocationException;
import javax.swing.text.Highlighter;
/**
* @author Adrian Benko
* @since 27.08.14
*/
public class TransactionData extends JFrame {
private JPanel topPanel;
private JTextArea dataTextArea;
public TransactionData(BlockChainTable blockChainTable) {
setTitle("Data");
setSize(400, 400);
setLocation(350, 200);
setBackground(Color.gray);
java.net.URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
// Create a panel to hold all other components
topPanel = new JPanel(new BorderLayout());
getContentPane().add(topPanel);
dataTextArea = new JTextArea();
dataTextArea.setEditable(false);
dataTextArea.setLineWrap(true);
dataTextArea.setOpaque(false);
dataTextArea.setWrapStyleWord(false);
dataTextArea.setFont(BlockChainTable.plain);
JScrollPane scrollPane = new JScrollPane(dataTextArea);
topPanel.add(scrollPane, BorderLayout.CENTER);
}
public void setData(byte[] data) {
dataTextArea.setText(ByteUtil.toHexString(data));
topPanel.repaint();
}
public void highlightText(String findText, Highlighter.HighlightPainter painter) {
if (findText.length() > 0 && dataTextArea.getText().contains(findText)) {
int begin = dataTextArea.getText().indexOf(findText);
int end = begin + findText.length();
try {
dataTextArea.getHighlighter().addHighlight(begin, end, painter);
} catch (BadLocationException e) {
}
dataTextArea.setCaretPosition(end);
}
}
}

View File

@ -1,12 +0,0 @@
package org.ethereum.gui;
import org.ethereum.facade.Ethereum;
import org.ethereum.facade.EthereumFactory;
/**
* @author Roman Mandeleil
* @since 01.09.2014
*/
public class UIEthereumManager {
public static Ethereum ethereum = EthereumFactory.createEthereum();
}

View File

@ -1,79 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.Account;
import org.ethereum.util.Utils;
import org.spongycastle.util.encoders.Hex;
import java.awt.*;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.math.BigInteger;
import java.net.URL;
import javax.swing.*;
import javax.swing.border.Border;
import javax.swing.border.CompoundBorder;
import javax.swing.border.EmptyBorder;
/**
* @author Roman Mandeleil
* @since 17.05.14
*/
public class WalletAddressPanel extends JPanel {
public WalletAddressPanel(final Account account) {
final WalletAddressPanel walletAddressPanel = this;
this.setBackground(Color.WHITE);
this.setPreferredSize(new Dimension(500, 45));
JTextField addressField = new JTextField();
Border line = BorderFactory.createLineBorder(Color.LIGHT_GRAY);
Border empty = new EmptyBorder(5, 8, 5, 8);
CompoundBorder border = new CompoundBorder(line, empty);
addressField.setBorder(border);
addressField.setEnabled(true);
addressField.setEditable(false);
addressField.setText(Hex.toHexString(account.getEcKey().getAddress()).toUpperCase());
addressField.setForeground(new Color(143, 170, 220));
addressField.setFont(new Font("Monospaced", 0, 12));
addressField.setPreferredSize(new Dimension(300, 35));
addressField.setBackground(Color.WHITE);
this.add(addressField);
JTextField amount = new JTextField();
amount.setBorder(border);
amount.setEnabled(true);
amount.setEditable(false);
BigInteger balance = account.getBalance();
amount.setText(Utils.getValueShortString(balance));
amount.setForeground(new Color(143, 170, 220));
amount.setBackground(Color.WHITE);
amount.setPreferredSize(new Dimension(100, 35));
amount.setFont(new Font("Monospaced", 0, 13));
amount.setHorizontalAlignment(SwingConstants.RIGHT);
this.add(amount);
URL payoutIconURL = ClassLoader.getSystemResource("buttons/wallet-pay.png");
ImageIcon payOutIcon = new ImageIcon(payoutIconURL);
JLabel payOutLabel = new JLabel(payOutIcon);
payOutLabel.setToolTipText("Payout for address");
payOutLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
payOutLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
PayOutDialog payOutDialog =
new PayOutDialog((Frame) SwingUtilities.getAncestorOfClass(JFrame.class,
walletAddressPanel), account);
}
});
this.add(payOutLabel);
}
}

View File

@ -1,64 +0,0 @@
package org.ethereum.gui;
import org.ethereum.util.Utils;
import java.awt.*;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.math.BigInteger;
import java.net.URL;
import javax.swing.*;
import javax.swing.border.Border;
import javax.swing.border.CompoundBorder;
import javax.swing.border.EmptyBorder;
/**
* @author Roman Mandeleil
* @since 17.05.14
*/
public class WalletSumPanel extends JPanel {
public WalletSumPanel(BigInteger balance) {
this.setBackground(Color.WHITE);
double width = this.getSize().getWidth();
this.setPreferredSize(new Dimension(500, 50));
Border line = BorderFactory.createLineBorder(Color.LIGHT_GRAY);
Border empty = new EmptyBorder(5, 8, 5, 8);
CompoundBorder border = new CompoundBorder(line, empty);
JLabel addressField = new JLabel();
addressField.setPreferredSize(new Dimension(300, 35));
this.add(addressField);
JTextField amount = new JTextField();
amount.setBorder(border);
amount.setEnabled(true);
amount.setEditable(false);
amount.setText(Utils.getValueShortString(balance));
amount.setPreferredSize(new Dimension(100, 35));
amount.setForeground(new Color(143, 170, 220));
amount.setHorizontalAlignment(SwingConstants.RIGHT);
amount.setFont(new Font("Monospaced", 0, 13));
amount.setBackground(Color.WHITE);
this.add(amount);
URL payoutIconURL = ClassLoader.getSystemResource("buttons/wallet-pay.png");
ImageIcon payOutIcon = new ImageIcon(payoutIconURL);
JLabel payOutLabel = new JLabel(payOutIcon);
payOutLabel.setToolTipText("Payout for all address list");
payOutLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
payOutLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
JOptionPane.showMessageDialog(null, "Under construction");
}
});
this.add(payOutLabel);
}
}

View File

@ -1,108 +0,0 @@
package org.ethereum.gui;
import org.ethereum.core.Account;
import org.ethereum.core.Wallet;
import java.awt.*;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.net.URL;
import javax.swing.*;
/**
* @author Roman Mandeleil
* @since 17.05.14
*/
public class WalletWindow extends JFrame implements Wallet.WalletListener {
WalletWindow walletWindow;
ToolBar toolBar;
public WalletWindow(ToolBar toolBar) {
addCloseAction();
this.toolBar = toolBar;
walletWindow = this;
URL url = ClassLoader.getSystemResource("ethereum-icon.png");
Toolkit kit = Toolkit.getDefaultToolkit();
Image img = kit.createImage(url);
this.setIconImage(img);
setTitle("Ethereum Wallet");
setSize(550, 280);
setLocation(215, 280);
setResizable(false);
Container contentPane = this.getContentPane();
contentPane.setBackground(new Color(255, 255, 255));
Wallet wallet = UIEthereumManager.ethereum.getWallet();
wallet.addListener(this);
loadWallet();
}
private void loadWallet() {
Container contentPane = this.getContentPane();
contentPane.removeAll();
contentPane.setLayout(new FlowLayout());
Wallet wallet = UIEthereumManager.ethereum.getWallet();
for (Account account : wallet.getAccountCollection()) {
WalletAddressPanel rowPanel = new WalletAddressPanel(account);
contentPane.add(rowPanel);
}
WalletSumPanel sumPanel = new WalletSumPanel(wallet.totalBalance());
contentPane.add(sumPanel);
// TODO: move this to some add button method
URL addAddressIconURL = ClassLoader.getSystemResource("buttons/add-address.png");
ImageIcon addAddressIcon = new ImageIcon(addAddressIconURL);
JLabel addAddressLabel = new JLabel(addAddressIcon);
addAddressLabel.setToolTipText("Add new address");
addAddressLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
addAddressLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
Wallet wallet = UIEthereumManager.ethereum.getWallet();
if (wallet.getAccountCollection().size() >= 5) {
JOptionPane.showMessageDialog(walletWindow,
"Hey do you really need more than 5 address for a demo wallet");
return;
}
wallet.addNewAccount();
Dimension dimension = walletWindow.getSize();
int height = dimension.height;
int width = dimension.width;
Dimension newDimension = new Dimension(width, (height + 45));
walletWindow.setSize(newDimension);
}
});
contentPane.add(addAddressLabel);
contentPane.revalidate();
contentPane.repaint();
}
public void addCloseAction() {
this.addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
toolBar.walletToggle.setSelected(false);
}
});
}
@Override
public void valueChanged() {
loadWallet();
}
}

View File

@ -1 +0,0 @@
java -Xmx6144M -Dlog4j.configuration=file:./config/log4j.properties -jar ./lib/ethereumj-0.7.9.jar org.ethereum.Start %*

View File

@ -1 +0,0 @@
java -Xmx6144M -Dlog4j.configuration=file:./config/log4j.properties -jar ./lib/ethereumj-0.7.9*.jar org.ethereum.Start -o true $@

View File

@ -1,2 +0,0 @@
call javaw -Xmx6144M -Dlog4j.configuration=file:./config/log4j.properties -jar ethereumj-studio.jar
pause

View File

@ -1 +0,0 @@
java -Xmx6144M -Dlog4j.configuration=file:./config/log4j.properties -jar ethereumj-studio.jar -o true

Some files were not shown because too many files have changed in this diff Show More