001 /** 002 * 003 */ 004 package edu.wwu.tobikley.acgc.ui; 005 006 import javax.swing.JFileChooser; 007 import javax.swing.SwingUtilities; 008 import javax.swing.JPanel; 009 import javax.swing.JFrame; 010 import javax.swing.JButton; 011 import javax.swing.SwingWorker; 012 013 import edu.uci.ics.jung.graph.Graph; 014 import edu.uci.ics.jung.io.GraphFile; 015 import edu.uci.ics.jung.io.GraphMLFile; 016 import edu.wwu.tobikley.acgc.algorithms.*; 017 018 import java.awt.Rectangle; 019 import java.awt.event.KeyEvent; 020 import java.beans.PropertyChangeEvent; 021 import java.beans.PropertyChangeListener; 022 import java.io.File; 023 import java.math.BigInteger; 024 import java.util.concurrent.ExecutorService; 025 import java.util.concurrent.Executors; 026 import java.util.concurrent.Future; 027 028 import javax.swing.JLabel; 029 import javax.swing.JTextField; 030 import javax.swing.JProgressBar; 031 import javax.swing.JComboBox; 032 import javax.swing.JTextArea; 033 import javax.swing.JScrollPane; 034 import java.awt.Font; 035 036 /** 037 * GUI for the Approximate Counting and Graph Coloring algorithms. 038 * 039 * @version 1.0 040 * @author Tobias Kley 041 */ 042 public class ACGC extends JFrame implements PropertyChangeListener { 043 044 private static final long serialVersionUID = 1L; 045 046 private JPanel jContentPane = null; 047 048 private JButton selectGraphButton = null; 049 050 private CountingAlgorithm countingAlgorithm = null; // @jve:decl-index=0: 051 052 private JLabel selectedGraphFile = null; 053 054 private JLabel numberColoringsLabel = null; 055 056 private JLabel numberOfColorings = null; 057 058 private JLabel runTimeLabel = null; 059 060 private JLabel runTime = null; 061 062 private JButton countButton = null; 063 064 private JLabel numberOfColorsLabel = null; 065 066 private JTextField numberOfColors = null; 067 068 private JProgressBar progressBar = null; 069 070 private static ACGC thisClass = null; 071 072 private ExecutorService executor = Executors.newCachedThreadPool(); // @jve:decl-index=0: 073 private Future<BigInteger> res = null; 074 private Graph graph; 075 private CountingTask task = null; 076 077 private JLabel precisionLabel = null; 078 079 private JLabel probabilityLabel = null; 080 081 private JTextField precision = null; 082 083 private JTextField probability = null; 084 085 private JComboBox algSelected = null; 086 087 private JButton showGraphButton = null; 088 089 private JTextArea resultList = null; 090 091 private JScrollPane resultScrollPane = null; 092 093 private JLabel progressText = null; 094 095 private JLabel iterationsLabel = null; 096 097 private JTextField iterations = null; 098 099 private JLabel resultsLabel = null; 100 101 private JLabel parametersLabel = null; 102 103 private JLabel graphLabel = null; 104 105 private JLabel selectAlgorithmLabel = null; 106 107 class CountingTask extends SwingWorker<Void,Void> { 108 109 @Override 110 public Void doInBackground() throws Exception { 111 res = executor.submit(countingAlgorithm); 112 while(!res.isDone()) { 113 int n = countingAlgorithm.getProgress(); 114 setProgress(n); 115 thisClass.setProgressText(countingAlgorithm.getProgressText()); 116 } 117 return null; 118 } 119 120 @Override 121 public void done() { 122 try { 123 numberOfColorings.setText(res.get().toString()); 124 runTime.setText(new Long(countingAlgorithm.getRunTime()).toString()); 125 for (CountingResult result : countingAlgorithm.getDetailedResults()) { 126 getResultList().append(result.toString()+"\n"); 127 } 128 getResultList().append("========================================\n\n"); 129 progressText.setText("Calculation finished."); 130 progressBar.setValue(100); 131 countButton.setEnabled(true); 132 } catch (Exception exception) { 133 getResultList().append(exception.getMessage()+"\n"); 134 } 135 } 136 } 137 138 private synchronized void setProgressText(String progressText) { 139 this.progressText.setText(progressText); 140 } 141 142 /** 143 * This method initializes selectGraphButton 144 * 145 * @return javax.swing.JButton 146 */ 147 private JButton getSelectGraphButton() { 148 if (selectGraphButton == null) { 149 selectGraphButton = new JButton(); 150 selectGraphButton.setBounds(new Rectangle(13, 34, 119, 21)); 151 selectGraphButton.setMnemonic(KeyEvent.VK_UNDEFINED); 152 selectGraphButton.setText("Select Graph"); 153 selectGraphButton.setName(""); 154 selectGraphButton.addActionListener(new java.awt.event.ActionListener() { 155 public void actionPerformed(java.awt.event.ActionEvent e) { 156 File file = null; 157 JFileChooser fc = new JFileChooser("W:/ews-graphenseminar"); 158 int returnVal = fc.showOpenDialog(ACGC.this); 159 160 if (returnVal == JFileChooser.APPROVE_OPTION) { 161 file = fc.getSelectedFile(); 162 GraphFile gf = new GraphMLFile(); 163 graph = gf.load(file.getAbsolutePath()); 164 } else { 165 //nix da. 166 } 167 selectedGraphFile.setText(file.getAbsolutePath()); 168 } 169 }); 170 } 171 return selectGraphButton; 172 } 173 174 /** 175 * This method initializes countButton 176 * 177 * @return javax.swing.JButton 178 */ 179 private JButton getCountButton() { 180 if (countButton == null) { 181 countButton = new JButton(); 182 countButton.setBounds(new Rectangle(589, 471, 87, 28)); 183 countButton.setText("Count!"); 184 countButton.addActionListener(new java.awt.event.ActionListener() { 185 public void actionPerformed(java.awt.event.ActionEvent e) { 186 try { 187 progressBar.setValue(0); 188 countButton.setEnabled(false); 189 int numberOfColors = Integer.parseInt(getNumberOfColors().getText()); 190 double epsilon = Double.parseDouble(getPrecision().getText()); 191 double alpha = 1 - Double.parseDouble(getProbability().getText()); 192 int T = Integer.parseInt(getIterations().getText()); 193 194 resultList.append("========================================\n"); 195 resultList.append(">> "+(String)algSelected.getSelectedItem()+" with Parameters:\n"); 196 resultList.append(">> q="+numberOfColors+" "); 197 198 if (algSelected.getSelectedItem() == "Naive Counting Algorithm") { 199 countingAlgorithm = new NaiveCountingAlgorithm(graph, numberOfColors); 200 } 201 if (algSelected.getSelectedItem() == "Algorithm by JERRUM") { 202 resultList.append("epsilon="+epsilon+" "); 203 if (alpha < 0.25) { 204 resultList.append("alpha="+alpha); 205 countingAlgorithm = new JerrumCountingAlgorithm(graph, numberOfColors, epsilon, alpha); 206 } else { 207 if (T > 1) { 208 resultList.append("T="+T); 209 countingAlgorithm = new JerrumCountingAlgorithm(graph, numberOfColors, epsilon, T); 210 } else { 211 resultList.append("T="+1); 212 countingAlgorithm = new JerrumCountingAlgorithm(graph, numberOfColors, epsilon); 213 } 214 } 215 } 216 if (algSelected.getSelectedItem() == "Algorithm by JERRUM (Heat Bath Variant)") { 217 resultList.append("epsilon="+epsilon+" "); 218 if (alpha < 0.25) { 219 resultList.append("alpha="+alpha); 220 countingAlgorithm = new JerrumHeatBathCountingAlgorithm(graph, numberOfColors, epsilon, alpha); 221 } else { 222 if (T > 1) { 223 resultList.append("T="+T); 224 countingAlgorithm = new JerrumHeatBathCountingAlgorithm(graph, numberOfColors, epsilon, T); 225 } else { 226 resultList.append("T="+1); 227 countingAlgorithm = new JerrumHeatBathCountingAlgorithm(graph, numberOfColors, epsilon); 228 } 229 } 230 } 231 232 resultList.append("\n========================================\n"); 233 234 task = new CountingTask(); 235 task.addPropertyChangeListener(thisClass); 236 task.execute(); 237 } catch (Exception exception) { 238 getResultList().append(exception.getMessage()); 239 } 240 } 241 }); 242 } 243 return countButton; 244 } 245 246 public void propertyChange(PropertyChangeEvent evt) { 247 if ("progress" == evt.getPropertyName()) { 248 int progress = (Integer) evt.getNewValue(); 249 progressBar.setValue(progress); 250 } 251 } 252 253 /** 254 * This method initializes numberOfColors 255 * 256 * @return javax.swing.JTextField 257 */ 258 private JTextField getNumberOfColors() { 259 if (numberOfColors == null) { 260 numberOfColors = new JTextField(); 261 numberOfColors.setBounds(new Rectangle(175, 190, 44, 20)); 262 numberOfColors.setText("5"); 263 } 264 return numberOfColors; 265 } 266 267 /** 268 * This method initializes progressBar 269 * 270 * @return javax.swing.JProgressBar 271 */ 272 private JProgressBar getProgressBar() { 273 if (progressBar == null) { 274 progressBar = new JProgressBar(); 275 progressBar.setBounds(new Rectangle(10, 464, 573, 22)); 276 } 277 return progressBar; 278 } 279 280 /** 281 * This method initializes precision 282 * 283 * @return javax.swing.JTextField 284 */ 285 private JTextField getPrecision() { 286 if (precision == null) { 287 precision = new JTextField(); 288 precision.setBounds(new Rectangle(174, 220, 44, 20)); 289 precision.setText("0.5"); 290 } 291 return precision; 292 } 293 294 /** 295 * This method initializes probability 296 * 297 * @return javax.swing.JTextField 298 */ 299 private JTextField getProbability() { 300 if (probability == null) { 301 probability = new JTextField(); 302 probability.setBounds(new Rectangle(176, 250, 42, 20)); 303 probability.setText("0.75"); 304 } 305 return probability; 306 } 307 308 /** 309 * This method initializes algSelected 310 * 311 * @return javax.swing.JComboBox 312 */ 313 private JComboBox getAlgSelected() { 314 if (algSelected == null) { 315 algSelected = new JComboBox(); 316 algSelected.setBounds(new Rectangle(5, 120, 213, 25)); 317 algSelected.addItem("Naive Counting Algorithm"); 318 algSelected.addItem("Algorithm by JERRUM"); 319 algSelected.addItem("Algorithm by JERRUM (Heat Bath Variant)"); 320 //algSelected.addItem("Algorithm by DYER/GREENHILL"); 321 } 322 return algSelected; 323 } 324 325 /** 326 * This method initializes showGraphButton 327 * 328 * @return javax.swing.JButton 329 */ 330 private JButton getShowGraphButton() { 331 if (showGraphButton == null) { 332 showGraphButton = new JButton(); 333 showGraphButton.setBounds(new Rectangle(13, 58, 119, 22)); 334 showGraphButton.setText("Check Graph"); 335 showGraphButton.addActionListener(new java.awt.event.ActionListener() { 336 public void actionPerformed(java.awt.event.ActionEvent e) { 337 GraphViewer graphViewer = new GraphViewer(graph); 338 graphViewer.setVisible(true); 339 } 340 }); 341 } 342 return showGraphButton; 343 } 344 345 /** 346 * This method initializes resultList 347 * 348 * @return javax.swing.JTextArea 349 */ 350 private JTextArea getResultList() { 351 if (resultList == null) { 352 resultList = new JTextArea(); 353 } 354 return resultList; 355 } 356 357 /** 358 * This method initializes resultScrollPane 359 * 360 * @return javax.swing.JScrollPane 361 */ 362 private JScrollPane getResultScrollPane() { 363 if (resultScrollPane == null) { 364 resultScrollPane = new JScrollPane(); 365 resultScrollPane.setBounds(new Rectangle(258, 74, 421, 382)); 366 resultScrollPane.setViewportView(getResultList()); 367 } 368 return resultScrollPane; 369 } 370 371 /** 372 * This method initializes iterations 373 * 374 * @return javax.swing.JTextField 375 */ 376 private JTextField getIterations() { 377 if (iterations == null) { 378 iterations = new JTextField(); 379 iterations.setBounds(new Rectangle(176, 274, 41, 20)); 380 iterations.setText("0"); 381 } 382 return iterations; 383 } 384 385 /** 386 * This method initializes parametersLabel 387 * 388 * @return javax.swing.JLabel 389 */ 390 private JLabel getParametersLabel() { 391 if (parametersLabel == null) { 392 parametersLabel = new JLabel(); 393 parametersLabel.setText("C. Specify the Parameters."); 394 parametersLabel.setFont(new Font("Dialog", Font.BOLD | Font.ITALIC, 14)); 395 parametersLabel.setBounds(new Rectangle(6, 161, 211, 21)); 396 } 397 return parametersLabel; 398 } 399 400 /** 401 * @param args 402 */ 403 public static void main(String[] args) { 404 // TODO Auto-generated method stub 405 SwingUtilities.invokeLater(new Runnable() { 406 public void run() { 407 thisClass = new ACGC(); 408 thisClass.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 409 thisClass.setVisible(true); 410 } 411 }); 412 } 413 414 /** 415 * This is the default constructor 416 */ 417 public ACGC() { 418 super(); 419 initialize(); 420 } 421 422 /** 423 * This method initializes this 424 * 425 * @return void 426 */ 427 private void initialize() { 428 this.setSize(700, 550); 429 this.setResizable(false); 430 this.setContentPane(getJContentPane()); 431 this.setTitle("Approximate Counting of Graph Colorings"); 432 this.setVisible(true); 433 } 434 435 /** 436 * This method initializes jContentPane 437 * 438 * @return javax.swing.JPanel 439 */ 440 private JPanel getJContentPane() { 441 if (jContentPane == null) { 442 selectAlgorithmLabel = new JLabel(); 443 selectAlgorithmLabel.setBounds(new Rectangle(11, 95, 241, 21)); 444 selectAlgorithmLabel.setFont(new Font("Dialog", Font.BOLD | Font.ITALIC, 14)); 445 selectAlgorithmLabel.setText("B. Select an algorithm."); 446 graphLabel = new JLabel(); 447 graphLabel.setBounds(new Rectangle(16, 10, 357, 22)); 448 graphLabel.setFont(new Font("Dialog", Font.BOLD | Font.ITALIC, 14)); 449 graphLabel.setText("A. Specify Graph by loading a GraphML-file first."); 450 resultsLabel = new JLabel(); 451 resultsLabel.setBounds(new Rectangle(9, 307, 227, 21)); 452 resultsLabel.setFont(new Font("Dialog", Font.BOLD | Font.ITALIC, 14)); 453 resultsLabel.setText("D. Results will be shown here:"); 454 iterationsLabel = new JLabel(); 455 iterationsLabel.setBounds(new Rectangle(8, 274, 159, 21)); 456 iterationsLabel.setText("(3b) Number of iterations T:"); 457 progressText = new JLabel(); 458 progressText.setBounds(new Rectangle(10, 489, 573, 20)); 459 progressText.setFont(new Font("Dialog", Font.PLAIN, 12)); 460 progressText.setText("No calculations performed yet."); 461 probabilityLabel = new JLabel(); 462 probabilityLabel.setBounds(new Rectangle(8, 246, 158, 24)); 463 probabilityLabel.setText("(3a) Probability alpha:"); 464 precisionLabel = new JLabel(); 465 precisionLabel.setBounds(new Rectangle(7, 217, 159, 23)); 466 precisionLabel.setText("(2) Precision epsilon:"); 467 numberOfColorsLabel = new JLabel(); 468 numberOfColorsLabel.setBounds(new Rectangle(7, 187, 158, 25)); 469 numberOfColorsLabel.setText("(1) Number of colors q:"); 470 runTime = new JLabel(); 471 runTime.setBounds(new Rectangle(10, 422, 231, 26)); 472 runTime.setText(""); 473 runTimeLabel = new JLabel(); 474 runTimeLabel.setBounds(new Rectangle(10, 393, 129, 27)); 475 runTimeLabel.setText("Run Time:"); 476 numberOfColorings = new JLabel(); 477 numberOfColorings.setBounds(new Rectangle(9, 358, 230, 24)); 478 numberOfColorings.setFont(new Font("Dialog", Font.BOLD, 12)); 479 numberOfColorings.setText(""); 480 numberColoringsLabel = new JLabel(); 481 numberColoringsLabel.setBounds(new Rectangle(9, 331, 128, 26)); 482 numberColoringsLabel.setText("Number of Colorings:"); 483 selectedGraphFile = new JLabel(); 484 selectedGraphFile.setBounds(new Rectangle(141, 35, 537, 24)); 485 selectedGraphFile.setFont(new Font("Dialog", Font.PLAIN, 12)); 486 selectedGraphFile.setText("No graph selected yet."); 487 jContentPane = new JPanel(); 488 jContentPane.setLayout(null); 489 jContentPane.add(getSelectGraphButton(), null); 490 jContentPane.add(selectedGraphFile, null); 491 jContentPane.add(numberColoringsLabel, null); 492 jContentPane.add(numberOfColorings, null); 493 jContentPane.add(runTimeLabel, null); 494 jContentPane.add(runTime, null); 495 jContentPane.add(getCountButton(), null); 496 jContentPane.add(numberOfColorsLabel, null); 497 jContentPane.add(getNumberOfColors(), null); 498 jContentPane.add(getProgressBar(), null); 499 jContentPane.add(precisionLabel, null); 500 jContentPane.add(probabilityLabel, null); 501 jContentPane.add(getPrecision(), null); 502 jContentPane.add(getProbability(), null); 503 jContentPane.add(getAlgSelected(), null); 504 jContentPane.add(getShowGraphButton(), null); 505 jContentPane.add(getResultScrollPane(), null); 506 jContentPane.add(progressText, null); 507 jContentPane.add(iterationsLabel, null); 508 jContentPane.add(getIterations(), null); 509 jContentPane.add(resultsLabel, null); 510 jContentPane.add(getParametersLabel(), null); 511 jContentPane.add(graphLabel, null); 512 jContentPane.add(selectAlgorithmLabel, null); 513 } 514 return jContentPane; 515 } 516 517 } // @jve:decl-index=0:visual-constraint="10,10"