001: /**
002: * LibreSource
003: * Copyright (C) 2004-2008 Artenum SARL / INRIA
004: * http://www.libresource.org - contact@artenum.com
005: *
006: * This file is part of the LibreSource software,
007: * which can be used and distributed under license conditions.
008: * The license conditions are provided in the LICENSE.TXT file
009: * at the root path of the packaging that enclose this file.
010: * More information can be found at
011: * - http://dev.libresource.org/home/license
012: *
013: * Initial authors :
014: *
015: * Guillaume Bort / INRIA
016: * Francois Charoy / Universite Nancy 2
017: * Julien Forest / Artenum
018: * Claude Godart / Universite Henry Poincare
019: * Florent Jouille / INRIA
020: * Sebastien Jourdain / INRIA / Artenum
021: * Yves Lerumeur / Artenum
022: * Pascal Molli / Universite Henry Poincare
023: * Gerald Oster / INRIA
024: * Mariarosa Penzi / Artenum
025: * Gerard Sookahet / Artenum
026: * Raphael Tani / INRIA
027: *
028: * Contributors :
029: *
030: * Stephane Bagnier / Artenum
031: * Amadou Dia / Artenum-IUP Blois
032: * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
033: */package org.libresource.so6.application.studio;
034:
035: import org.libresource.so6.core.Workspace;
036: import org.libresource.so6.core.WsConnection;
037: import org.libresource.so6.core.engine.util.FileUtils;
038: import org.libresource.so6.core.exec.ui.Commit;
039: import org.libresource.so6.core.exec.ui.ConflictEditor;
040: import org.libresource.so6.core.exec.ui.Diff;
041: import org.libresource.so6.core.exec.ui.PatchInspector;
042: import org.libresource.so6.core.exec.ui.Rename;
043: import org.libresource.so6.core.exec.ui.Update;
044: import org.libresource.so6.core.interfaces.Closer;
045: import org.libresource.so6.core.interfaces.ConflictViewer;
046: import org.libresource.so6.core.interfaces.FileTreeActionListener;
047: import org.libresource.so6.core.ui.ConflictView;
048:
049: import java.awt.BorderLayout;
050: import java.awt.Color;
051: import java.awt.Toolkit;
052: import java.awt.event.ActionEvent;
053: import java.awt.event.ActionListener;
054: import java.awt.event.WindowAdapter;
055: import java.awt.event.WindowEvent;
056:
057: import java.io.File;
058:
059: import java.util.ArrayList;
060:
061: import javax.swing.JComponent;
062: import javax.swing.JDesktopPane;
063: import javax.swing.JFileChooser;
064: import javax.swing.JFrame;
065: import javax.swing.JInternalFrame;
066: import javax.swing.JMenu;
067: import javax.swing.JMenuBar;
068: import javax.swing.JMenuItem;
069: import javax.swing.JOptionPane;
070: import javax.swing.JScrollPane;
071:
072: /**
073: * @author smack
074: */
075: public class Studio extends JFrame {
076: private String basePath;
077: private String wscPath;
078: private So6StudioMenu menu;
079: private JDesktopPane desktop;
080:
081: public Studio() {
082: desktop = new JDesktopPane();
083: menu = new So6StudioMenu();
084: getContentPane().add(menu, BorderLayout.NORTH);
085: getContentPane().add(new JScrollPane(desktop),
086: BorderLayout.CENTER);
087: }
088:
089: public void setWorkspace(String basePath) throws Exception {
090: this .basePath = basePath;
091: menu.setWorkspace(basePath);
092: setTitle("Base path: " + basePath);
093: }
094:
095: public void setSelectedConnectionPath(String wscPath) {
096: this .wscPath = wscPath;
097: setTitle("Selected connection: " + wscPath);
098: }
099:
100: public JInternalFrame createInternalFrame(JComponent content,
101: String title) {
102: return createInternalFrame(content, title,
103: desktop.getWidth() / 4, desktop.getHeight() / 4);
104: }
105:
106: public JInternalFrame createInternalFrame(JComponent content,
107: String title, int width, int height) {
108: JInternalFrame internalFrame = new JInternalFrame();
109: internalFrame.getContentPane().setLayout(new BorderLayout());
110: internalFrame.getContentPane()
111: .add(content, BorderLayout.CENTER);
112: internalFrame.setClosable(true);
113: internalFrame.setMaximizable(true);
114: internalFrame.setResizable(true);
115: internalFrame.setIconifiable(true);
116: internalFrame.setTitle(title + " : " + wscPath);
117: internalFrame.setLocation(10, 10);
118: internalFrame.setSize(width, height);
119:
120: return internalFrame;
121: }
122:
123: public void addInternalFrame(JInternalFrame internalFrame) {
124: desktop.add(internalFrame);
125:
126: //desktop.show();
127: internalFrame.setVisible(true);
128:
129: try {
130: internalFrame.setSelected(true);
131: } catch (java.beans.PropertyVetoException e) {
132: e.printStackTrace();
133: }
134: }
135:
136: public static void main(String[] args) throws Exception {
137: Studio studio = new Studio();
138: studio.setSize(400, 400);
139: studio.addWindowListener(new WindowAdapter() {
140: public void windowClosing(WindowEvent e) {
141: System.exit(0);
142: }
143: });
144: studio.setLocation(((int) Toolkit.getDefaultToolkit()
145: .getScreenSize().getWidth() - studio.getWidth()) / 2,
146: ((int) Toolkit.getDefaultToolkit().getScreenSize()
147: .getHeight() - studio.getHeight()) / 2);
148: studio.setVisible(true);
149: }
150:
151: public class So6StudioMenu extends JMenuBar implements
152: ActionListener, FileTreeActionListener, ConflictViewer {
153: private Workspace ws;
154: private String selectedDataPath;
155:
156: //
157: private JMenu file;
158: private JMenuItem open;
159: private JMenuItem clean;
160: private JMenuItem quit;
161:
162: //
163: private JMenu edit;
164: private ArrayList connectionsMenu;
165:
166: //
167: private JMenu view;
168: private JMenuItem wsTree; // conflict - undo/redo
169: private JMenuItem findConflict;
170: private JMenuItem vdiff;
171: private JMenuItem patchInspector;
172: private JMenuItem update;
173: private JMenuItem commit;
174: private JMenuItem restore;
175:
176: public So6StudioMenu() {
177: file = new JMenu("File");
178:
179: //
180: open = new JMenuItem("Open");
181: open.setActionCommand("OPEN");
182: open.addActionListener(this );
183:
184: //
185: clean = new JMenuItem("Clean so6 tmp files");
186: clean.setActionCommand("CLEAN");
187: clean.addActionListener(this );
188:
189: //
190: quit = new JMenuItem("Quit");
191: quit.setActionCommand("EXIT");
192: quit.addActionListener(this );
193:
194: //
195: file.add(open);
196: file.add(clean);
197: file.addSeparator();
198: file.add(quit);
199: add(file);
200:
201: //
202: edit = new JMenu("Connections");
203: edit.setEnabled(false);
204: add(edit);
205:
206: //
207: view = new JMenu("View");
208: view.setEnabled(false);
209:
210: //
211: wsTree = new JMenuItem("File tree");
212: wsTree.setActionCommand("FILE_TREE");
213: wsTree.addActionListener(this );
214:
215: //
216: findConflict = new JMenuItem("Find conflict");
217: findConflict.setActionCommand("CONFLICT");
218: findConflict.addActionListener(this );
219:
220: //
221: vdiff = new JMenuItem("Diff");
222: vdiff.setActionCommand("DIFF");
223: vdiff.addActionListener(this );
224:
225: //
226: patchInspector = new JMenuItem("Patch inspector");
227: patchInspector.setActionCommand("INSPECT");
228: patchInspector.addActionListener(this );
229:
230: //
231: update = new JMenuItem("Update");
232: update.setActionCommand("UPDATE");
233: update.addActionListener(this );
234:
235: //
236: commit = new JMenuItem("Commit");
237: commit.setActionCommand("COMMIT");
238: commit.addActionListener(this );
239:
240: //
241: restore = new JMenuItem("Restore");
242: restore.setActionCommand("RESTORE");
243: restore.addActionListener(this );
244:
245: //
246: view.add(wsTree);
247: view.add(findConflict);
248: view.addSeparator();
249: view.add(vdiff);
250: view.add(patchInspector);
251: view.addSeparator();
252: view.add(update);
253: view.add(commit);
254: view.addSeparator();
255: view.add(restore);
256: add(view);
257: }
258:
259: public void setWorkspace(String wsPath) throws Exception {
260: ws = new Workspace(wsPath);
261:
262: WsConnection[] wsc = ws.listConnections();
263:
264: for (int i = 0; i < wsc.length; i++) {
265: String label = wsc[i].getWsName() + " ("
266: + new File(wsc[i].getDataPath()).getName()
267: + ")";
268: JMenuItem item = new JMenuItem(label);
269: item.setActionCommand("WSC " + wsc[i].getDataPath());
270: item.addActionListener(this );
271: edit.add(item);
272: }
273:
274: open.setEnabled(false);
275: edit.setEnabled(true);
276: }
277:
278: public void actionPerformed(ActionEvent e) {
279: String command = e.getActionCommand();
280:
281: try {
282: if (command.equals("EXIT")) {
283: System.exit(0);
284: } else if (command.equals("CLEAN")) {
285: FileUtils.cleanSo6TmpFiles();
286: } else if (command.equals("OPEN")) {
287: JFileChooser chooser = new JFileChooser();
288: chooser
289: .setDialogTitle("Open the workspace base path...");
290: chooser
291: .setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
292:
293: if (chooser.showOpenDialog(this ) == JFileChooser.APPROVE_OPTION) {
294: File baseDir = chooser.getSelectedFile();
295:
296: try {
297: Studio.this .setWorkspace(baseDir.getPath());
298: } catch (Exception e1) {
299: JOptionPane.showMessageDialog(this ,
300: "Error while trying to open workspace: "
301: + e1.getMessage());
302: }
303: }
304: } else if (command.equals("FILE_TREE")) {
305: ConnectionFileTree fileTree = new ConnectionFileTree(
306: wscPath);
307: fileTree.setFileTreeActionListener(this );
308:
309: JInternalFrame jif = createInternalFrame(fileTree,
310: "Workspace file tree");
311: jif.setLocation(0, 0);
312:
313: int width = desktop.getWidth();
314:
315: if (width > 300) {
316: width = 300;
317: }
318:
319: jif.setSize(width, desktop.getHeight());
320: addInternalFrame(jif);
321: } else if (command.equals("CONFLICT")) {
322: ConflictView cv = new ConflictView(wscPath);
323: cv.setConflictViewer(this );
324:
325: JInternalFrame jif = createInternalFrame(cv,
326: "Conflict list");
327: jif.setSize(desktop.getWidth() / 2, desktop
328: .getHeight() / 2);
329: jif.setLocation(desktop.getWidth() / 4, desktop
330: .getHeight() / 4);
331: addInternalFrame(jif);
332: } else if (command.equals("UPDATE")) {
333: Update update = new Update(wscPath);
334: update.setStyle(Color.white, Color
335: .decode("#eeeeee"));
336: update.setConflictViewer(this );
337:
338: JInternalFrame jif = createInternalFrame(update,
339: "Update " + wscPath, 400, 215);
340: update.setCloser(new InternalFrameCloser(jif));
341: addInternalFrame(jif);
342: } else if (command.equals("COMMIT")) {
343: Commit commit = new Commit(wscPath);
344: commit.setStyle(Color.white, Color
345: .decode("#eeeeee"));
346:
347: JInternalFrame jif = createInternalFrame(commit,
348: "Commit " + wscPath, 400, 215);
349: commit.setCloser(new InternalFrameCloser(jif));
350: addInternalFrame(jif);
351: } else if (command.equals("RESTORE")) {
352: try {
353: new WsConnection(wscPath).restore();
354: JOptionPane
355: .showMessageDialog(this ,
356: "Your workspace has been restored correctly");
357: } catch (Exception e2) {
358: JOptionPane.showMessageDialog(this , e2
359: .getMessage());
360: }
361: } else if (command.startsWith("WSC ")) {
362: selectedDataPath = command.substring(4);
363: setSelectedConnectionPath(selectedDataPath
364: + File.separator
365: + WsConnection.SO6_WSC_FILE);
366: view.setEnabled(true);
367: } else if (command.startsWith("INSPECT")) {
368: JFileChooser chooser = new JFileChooser();
369: chooser.setDialogTitle("Open a patch...");
370: chooser.setCurrentDirectory(new File(wscPath));
371: chooser
372: .setFileSelectionMode(JFileChooser.FILES_ONLY);
373:
374: if (chooser.showOpenDialog(this ) == JFileChooser.APPROVE_OPTION) {
375: File patch = chooser.getSelectedFile();
376:
377: try {
378: PatchInspector pi = new PatchInspector();
379: pi.setStyle(Color.white, Color
380: .decode("#eeeeee"));
381: pi.load(patch.getPath());
382: pi.setSplitLocation(desktop.getWidth() / 4);
383:
384: JInternalFrame jif = createInternalFrame(
385: pi, "Patch inspector");
386: jif.setSize(desktop.getWidth() / 2, desktop
387: .getHeight() / 2);
388: jif.setLocation(desktop.getWidth() / 4,
389: desktop.getHeight() / 4);
390: addInternalFrame(jif);
391: } catch (Exception e1) {
392: JOptionPane.showMessageDialog(this ,
393: "Error while trying to open workspace: "
394: + e1.getMessage());
395: }
396: }
397: } else if (command.startsWith("DIFF")) {
398: diff(new WsConnection(wscPath), "");
399: }
400: } catch (Exception e1) {
401: e1.printStackTrace();
402: JOptionPane.showMessageDialog(this , "Error on action "
403: + command + " : " + e1.getMessage());
404: }
405: }
406:
407: public void editConflictOnFile(String filePath)
408: throws Exception {
409: ConflictEditor ce = new ConflictEditor(filePath);
410: JInternalFrame jif = createInternalFrame(ce,
411: "Conflict editor: " + filePath);
412: jif.setLocation(300, 0);
413: jif.setSize(desktop.getWidth() - 300, desktop.getHeight());
414: addInternalFrame(jif);
415: }
416:
417: public void showFileHistory(WsConnection wsc, String filePath)
418: throws Exception {
419: FileHistoryViewer fhv = new FileHistoryViewer(wsc
420: .getDataPath()
421: + File.separator + WsConnection.SO6_WSC_FILE,
422: filePath.replaceAll("\\\\", "/"));
423: JInternalFrame jif = createInternalFrame(fhv,
424: "File history: " + filePath);
425: jif.setLocation(300, 0);
426: jif.setSize(desktop.getWidth() - 300, desktop.getHeight());
427: addInternalFrame(jif);
428: }
429:
430: public void showConflictEditor(String filePath)
431: throws Exception {
432: ConflictEditor ce = new ConflictEditor(filePath);
433: JInternalFrame jif = createInternalFrame(ce,
434: "Conflict editor: " + filePath);
435: jif.setLocation(300, 0);
436: jif.setSize(desktop.getWidth() - 300, desktop.getHeight());
437: addInternalFrame(jif);
438: }
439:
440: public void rename(WsConnection wsc, String filePath)
441: throws Exception {
442: Rename mv = new Rename(wsc.getDataPath() + File.separator
443: + WsConnection.SO6_WSC_FILE, filePath, "");
444: mv.setStyle(Color.white, Color.decode("#eeeeee"));
445:
446: JInternalFrame jif = createInternalFrame(mv,
447: "Rename file for connection: " + wsc.getDataPath(),
448: 400, 180);
449: mv.setCloser(new InternalFrameCloser(jif));
450: jif.setLocation(300, 10);
451: addInternalFrame(jif);
452: }
453:
454: public void diff(WsConnection wsc, String filePath)
455: throws Exception {
456: Diff diff = new Diff(wsc.getRefCopyPath() + File.separator
457: + filePath, wsc.getPath() + File.separator
458: + filePath);
459: diff.setStyle(Color.white, Color.decode("#eeeeee"));
460:
461: JInternalFrame jif = createInternalFrame(diff,
462: "Rename file for connection: " + wsc.getDataPath(),
463: 400, 180);
464: diff.setCloser(new InternalFrameCloser(jif));
465: jif.setLocation(300, 10);
466: addInternalFrame(jif);
467: }
468: }
469:
470: public class InternalFrameCloser implements Closer {
471: private JInternalFrame internalFrame;
472:
473: public InternalFrameCloser(JInternalFrame jif) {
474: internalFrame = jif;
475: }
476:
477: public void exit() {
478: internalFrame.dispose();
479: }
480: }
481: }
|