+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/Papers-icon.png b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/Papers-icon.png
new file mode 100644
index 00000000..ea6bd3ee
Binary files /dev/null and b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/Papers-icon.png differ
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/README-Icons b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/README-Icons
new file mode 100644
index 00000000..407409cf
--- /dev/null
+++ b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/README-Icons
@@ -0,0 +1,12 @@
+Tango Icon Theme
+----------------
+
+This is an icon theme that follows the Tango visual guidelines [1]. Currently
+it depends on Imagemagick for creation of 24x24 bitmaps by adding a 1px padding
+around the 22x22px version. For GNOME and KDE you will also need
+icon-naming-utils that allow the theme to work in these environments before
+they follow the new naming scheme [2].
+
+
+[1] http://tango-project.org/Tango_Icon_Theme_Guidelines
+[2] http://tango-project.org/Standard_Icon_Naming_Specification
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/Utilities.java b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/Utilities.java
new file mode 100644
index 00000000..bb2a83c5
--- /dev/null
+++ b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/Utilities.java
@@ -0,0 +1,118 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.ui;
+
+import java.io.File;
+import java.net.URL;
+
+import javax.swing.BorderFactory;
+import javax.swing.ImageIcon;
+import javax.swing.JButton;
+import javax.swing.JFrame;
+import javax.swing.SwingConstants;
+
+/**
+ * General helper methods related to building a user interface with Swing.
+ *
+ * @author Michael Eichberg
+ */
+public class Utilities {
+
+ private Utilities() {
+ // do nothing - just defined to avoid accidental instance creations
+ }
+
+ /**
+ * Sets the frame title based on the name of the file.
+ *
+ * @param frame
+ * The frame's title.
+ * @param file
+ * The document's file (which is edited in the frame.)
+ */
+ public static void setFrameTitle(JFrame frame, File file) {
+
+ if (file != null) {
+ frame.setTitle(file.getName().substring(0,
+ file.getName().lastIndexOf('.')));
+ frame.getRootPane().putClientProperty("Window.documentFile", file);
+ } else
+ frame.setTitle("untitled");
+ }
+
+ /**
+ * Creates a JButton object that can be placed in toolbars.
+ *
+ * @param title
+ * The (very short) title of the button. The title will be
+ * displayed below the button.
+ * @param iconPath
+ * The path to the ImageIcon.
+ * @param iconDescription
+ * A short description of the icon / the action.
+ * @return A new JButton.
+ * @see #createImageIcon(String, String)
+ */
+ public static JButton createToolBarButton(String title, String iconPath,
+ String iconDescription) {
+
+ JButton button = new JButton(title, createImageIcon(iconPath,
+ iconDescription));
+ button.setVerticalTextPosition(SwingConstants.BOTTOM);
+ button.setHorizontalTextPosition(SwingConstants.CENTER);
+ button.setOpaque(false);
+ button.setBorder(BorderFactory.createEmptyBorder());
+ return button;
+ }
+
+ /**
+ * Creates an image icon. If the resource is no longer / not available, an
+ * exception is thrown.
+ *
+ * @param path
+ * A path relative to the location of this classes compiled class
+ * file.
+ * @param description
+ * A short description of the icon.
+ */
+ public static ImageIcon createImageIcon(String path, String description) {
+
+ URL imgURL = Utilities.class.getResource(path);
+ if (imgURL != null) {
+ return new ImageIcon(imgURL, description);
+ } else {
+ throw new UnknownError("Missing resource: " + path + "("
+ + description + ")");
+ }
+ }
+}
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/accessories-text-editor.png b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/accessories-text-editor.png
new file mode 100644
index 00000000..c6b62851
Binary files /dev/null and b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/accessories-text-editor.png differ
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/go-next.png b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/go-next.png
new file mode 100644
index 00000000..6f3f65d3
Binary files /dev/null and b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/go-next.png differ
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/list-add.png b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/list-add.png
new file mode 100644
index 00000000..2acdd8f5
Binary files /dev/null and b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/list-add.png differ
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/list-remove.png b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/list-remove.png
new file mode 100644
index 00000000..c5524f72
Binary files /dev/null and b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/list-remove.png differ
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/media-playback-start.png b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/media-playback-start.png
new file mode 100644
index 00000000..66f32d89
Binary files /dev/null and b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/media-playback-start.png differ
diff --git a/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/process-stop.png b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/process-stop.png
new file mode 100644
index 00000000..b68290bf
Binary files /dev/null and b/ws2010/se/u4/src/de/tud/cs/se/flashcards/ui/process-stop.png differ
diff --git a/ws2010/se/u5/.classpath b/ws2010/se/u5/.classpath
new file mode 100644
index 00000000..9c57e5f5
--- /dev/null
+++ b/ws2010/se/u5/.classpath
@@ -0,0 +1,9 @@
+
+
+
+
+
+
+
+
+
diff --git a/ws2010/se/u5/.project b/ws2010/se/u5/.project
new file mode 100644
index 00000000..c3b5d117
--- /dev/null
+++ b/ws2010/se/u5/.project
@@ -0,0 +1,17 @@
+
+
+ EiSE-Exercise05
+
+
+
+
+
+ org.eclipse.jdt.core.javabuilder
+
+
+
+
+
+ org.eclipse.jdt.core.javanature
+
+
diff --git a/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/AllTests.java b/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/AllTests.java
new file mode 100644
index 00000000..bf47c5bf
--- /dev/null
+++ b/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/AllTests.java
@@ -0,0 +1,46 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.model;
+
+import org.junit.runner.RunWith;
+import org.junit.runners.Suite;
+
+@RunWith(Suite.class)
+@Suite.SuiteClasses({
+ FlashcardSeriesTest.class,
+ FlashcardTest.class,
+ ConditionCoverageTest.class }
+)
+public class AllTests {
+
+}
diff --git a/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/ConditionCoverageTest.java b/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/ConditionCoverageTest.java
new file mode 100644
index 00000000..2b2ddf56
--- /dev/null
+++ b/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/ConditionCoverageTest.java
@@ -0,0 +1,5 @@
+package de.tud.cs.se.flashcards.model;
+
+public class ConditionCoverageTest {
+
+}
diff --git a/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/FlashcardSeriesTest.java b/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/FlashcardSeriesTest.java
new file mode 100644
index 00000000..678a77d3
--- /dev/null
+++ b/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/FlashcardSeriesTest.java
@@ -0,0 +1,17 @@
+package de.tud.cs.se.flashcards.model;
+
+import static org.junit.Assert.assertTrue;
+
+import org.junit.Test;
+
+public class FlashcardSeriesTest {
+
+ /**
+ * Example of JUnit4 Usage
+ */
+ @Test
+ public void testMethod() {
+
+ // assertTrue(// some condition);
+ }
+}
diff --git a/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/FlashcardTest.java b/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/FlashcardTest.java
new file mode 100644
index 00000000..55013e8f
--- /dev/null
+++ b/ws2010/se/u5/test/de/tud/cs/se/flashcards/model/FlashcardTest.java
@@ -0,0 +1,5 @@
+package de.tud.cs.se.flashcards.model;
+
+public class FlashcardTest {
+
+}
diff --git a/ws2010/se/u7/.classpath b/ws2010/se/u7/.classpath
new file mode 100644
index 00000000..9e7a9072
--- /dev/null
+++ b/ws2010/se/u7/.classpath
@@ -0,0 +1,8 @@
+
+
+
+
+
+
+
+
diff --git a/ws2010/se/u7/.project b/ws2010/se/u7/.project
new file mode 100644
index 00000000..0a40c5cf
--- /dev/null
+++ b/ws2010/se/u7/.project
@@ -0,0 +1,17 @@
+
+
+ EiSE-Exercise07
+
+
+
+
+
+ org.eclipse.jdt.core.javabuilder
+
+
+
+
+
+ org.eclipse.jdt.core.javanature
+
+
diff --git a/ws2010/se/u7/project/.classpath b/ws2010/se/u7/project/.classpath
new file mode 100644
index 00000000..096b8292
--- /dev/null
+++ b/ws2010/se/u7/project/.classpath
@@ -0,0 +1,9 @@
+
+
+
+
+
+
+
+
+
diff --git a/ws2010/se/u7/project/.project b/ws2010/se/u7/project/.project
new file mode 100644
index 00000000..752d3f84
--- /dev/null
+++ b/ws2010/se/u7/project/.project
@@ -0,0 +1,17 @@
+
+
+ EiSE-Exercise04
+
+
+
+
+
+ org.eclipse.jdt.core.javabuilder
+
+
+
+
+
+ org.eclipse.jdt.core.javanature
+
+
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/MacOSXAdapter$1.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/MacOSXAdapter$1.class
new file mode 100644
index 00000000..e87382cc
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/MacOSXAdapter$1.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/MacOSXAdapter.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/MacOSXAdapter.class
new file mode 100644
index 00000000..ca5a2f6b
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/MacOSXAdapter.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/Main.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/Main.class
new file mode 100644
index 00000000..48d5b050
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/Main.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/model/Flashcard.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/model/Flashcard.class
new file mode 100644
index 00000000..9d003c42
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/model/Flashcard.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/model/FlashcardSeries.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/model/FlashcardSeries.class
new file mode 100644
index 00000000..16863e76
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/model/FlashcardSeries.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/persistence/Store.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/persistence/Store.class
new file mode 100644
index 00000000..759f2e5d
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/persistence/Store.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor$1.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor$1.class
new file mode 100644
index 00000000..e18c827a
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor$1.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor$2.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor$2.class
new file mode 100644
index 00000000..83b9eff1
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor$2.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor.class
new file mode 100644
index 00000000..f53a0e0f
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardEditor.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$1.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$1.class
new file mode 100644
index 00000000..3aa9fd01
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$1.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$10.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$10.class
new file mode 100644
index 00000000..1d29dacb
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$10.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$11.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$11.class
new file mode 100644
index 00000000..a7a98c78
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$11.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$12$1.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$12$1.class
new file mode 100644
index 00000000..1e288b89
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$12$1.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$12.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$12.class
new file mode 100644
index 00000000..293ad42e
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$12.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$2.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$2.class
new file mode 100644
index 00000000..c8aa37f6
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$2.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$3.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$3.class
new file mode 100644
index 00000000..9e151cc7
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$3.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$4.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$4.class
new file mode 100644
index 00000000..da30923d
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$4.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$5.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$5.class
new file mode 100644
index 00000000..1b94b102
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$5.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$6.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$6.class
new file mode 100644
index 00000000..5f9ac2a0
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$6.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$7.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$7.class
new file mode 100644
index 00000000..f5e6d598
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$7.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$8.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$8.class
new file mode 100644
index 00000000..af12c9bd
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$8.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$9.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$9.class
new file mode 100644
index 00000000..65cbda02
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow$9.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow.class
new file mode 100644
index 00000000..ecf1b8c0
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/FlashcardsWindow.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$1.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$1.class
new file mode 100644
index 00000000..7885f299
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$1.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$2.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$2.class
new file mode 100644
index 00000000..d0e64af0
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$2.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$State.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$State.class
new file mode 100644
index 00000000..f8d71c9e
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog$State.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog.class
new file mode 100644
index 00000000..c4fc62ec
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/LearnDialog.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Papers-icon-readme.html b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Papers-icon-readme.html
new file mode 100644
index 00000000..8315f751
--- /dev/null
+++ b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Papers-icon-readme.html
@@ -0,0 +1,67 @@
+
+
+
+
+Dimension Of Deskmod :: Icon Design
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Papers-icon.png b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Papers-icon.png
new file mode 100644
index 00000000..ea6bd3ee
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Papers-icon.png differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/README-Icons b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/README-Icons
new file mode 100644
index 00000000..407409cf
--- /dev/null
+++ b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/README-Icons
@@ -0,0 +1,12 @@
+Tango Icon Theme
+----------------
+
+This is an icon theme that follows the Tango visual guidelines [1]. Currently
+it depends on Imagemagick for creation of 24x24 bitmaps by adding a 1px padding
+around the 22x22px version. For GNOME and KDE you will also need
+icon-naming-utils that allow the theme to work in these environments before
+they follow the new naming scheme [2].
+
+
+[1] http://tango-project.org/Tango_Icon_Theme_Guidelines
+[2] http://tango-project.org/Standard_Icon_Naming_Specification
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Utilities.class b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Utilities.class
new file mode 100644
index 00000000..b6e36044
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/Utilities.class differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/accessories-text-editor.png b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/accessories-text-editor.png
new file mode 100644
index 00000000..c6b62851
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/accessories-text-editor.png differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/go-next.png b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/go-next.png
new file mode 100644
index 00000000..6f3f65d3
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/go-next.png differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/list-add.png b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/list-add.png
new file mode 100644
index 00000000..2acdd8f5
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/list-add.png differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/list-remove.png b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/list-remove.png
new file mode 100644
index 00000000..c5524f72
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/list-remove.png differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/media-playback-start.png b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/media-playback-start.png
new file mode 100644
index 00000000..66f32d89
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/media-playback-start.png differ
diff --git a/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/process-stop.png b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/process-stop.png
new file mode 100644
index 00000000..b68290bf
Binary files /dev/null and b/ws2010/se/u7/project/bin/de/tud/cs/se/flashcards/ui/process-stop.png differ
diff --git a/ws2010/se/u7/project/lib/commons-io-1.4.jar b/ws2010/se/u7/project/lib/commons-io-1.4.jar
new file mode 100644
index 00000000..133dc6cb
Binary files /dev/null and b/ws2010/se/u7/project/lib/commons-io-1.4.jar differ
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/MacOSXAdapter.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/MacOSXAdapter.java
new file mode 100644
index 00000000..5a31a00c
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/MacOSXAdapter.java
@@ -0,0 +1,124 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Michael Eichberg (Software Engineering)
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards;
+
+import java.awt.Image;
+import java.lang.reflect.InvocationHandler;
+import java.lang.reflect.Method;
+import java.lang.reflect.Proxy;
+
+import javax.swing.JOptionPane;
+
+import de.tud.cs.se.flashcards.ui.Utilities;
+
+/**
+ * This class provides the major part of the Mac OS X integration of the
+ * flashcards app.
+ *
+ * This class does not introduce any coupling on Mac OS X specific classes
+ * or technologies.
+ *
+ *
+ * @author Michael Eichberg
+ */
+public class MacOSXAdapter {
+
+ static {
+
+ // properties to make the application look more similar to a native Mac
+ // OS X application
+ System.setProperty("apple.laf.useScreenMenuBar", "true");
+ System.setProperty("com.apple.mrj.application.growbox.intrudes",
+ "false");
+ System.setProperty("com.apple.mrj.application.apple.menu.about.name",
+ "Flashcards");
+
+ try {
+ Class> applicationClass = Class
+ .forName("com.apple.eawt.Application");
+ Object application = applicationClass.getMethod("getApplication")
+ .invoke(null);
+ applicationClass.getMethod("setEnabledPreferencesMenu",
+ boolean.class).invoke(application, Boolean.FALSE);
+
+ Image appImage = java.awt.Toolkit.getDefaultToolkit().getImage(
+ Utilities.class.getResource("Papers-icon.png"));
+ applicationClass.getMethod("setDockIconImage", Image.class).invoke(
+ application, appImage);
+
+ Class> applicationAdapterClass = Class
+ .forName("com.apple.eawt.ApplicationListener");
+ Object applicationAdapter = Proxy.newProxyInstance(
+ System.class.getClassLoader(),
+ new Class>[] { applicationAdapterClass },
+ new InvocationHandler() {
+
+ public Object invoke(Object proxy, Method method,
+ Object[] args) throws Throwable {
+ if (method.getName().equals("handleAbout")) {
+ JOptionPane
+ .showMessageDialog(
+ null,
+ "(c) 2010 Michael Eichberg,\nDepartment of Computer Science,\nTechnische Universität Darmstadt",
+ "Flashcards",
+ JOptionPane.INFORMATION_MESSAGE,
+ Utilities.createImageIcon(
+ "Papers-icon.png",
+ "The Flashcards Icon"));
+ args[0].getClass()
+ .getMethod("setHandled", boolean.class)
+ .invoke(args[0], Boolean.TRUE);
+ } else if (method.getName().equals("handleQuit")) {
+ // Check to see if the user has unsaved
+ // changes.
+ // If the user does not have unhandled changes
+ // call
+ // setHandled(true) otherwise call
+ // setHandled(false).
+ args[0].getClass()
+ .getMethod("setHandled", boolean.class)
+ .invoke(args[0], Boolean.TRUE);
+ }
+ return null;
+ }
+ });
+
+ applicationClass.getMethod("addApplicationListener",
+ Class.forName("com.apple.eawt.ApplicationListener"))
+ .invoke(application, applicationAdapter);
+ } catch (Exception e) {
+ System.err.println("Mac OS X integration failed: "
+ + e.getLocalizedMessage() + ".");
+ }
+ }
+}
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/Main.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/Main.java
new file mode 100644
index 00000000..a4362108
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/Main.java
@@ -0,0 +1,105 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Michael Eichberg (Software Engineering)
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards;
+
+import java.io.File;
+import java.util.Iterator;
+import java.util.Map.Entry;
+
+import javax.swing.UIManager;
+
+import de.tud.cs.se.flashcards.model.FlashcardSeries;
+import de.tud.cs.se.flashcards.ui.FlashcardsWindow;
+
+/**
+ * Starts the flashcard application. Basically, each given file is associated
+ * with its own Frame.
+ *
+ * @author Michael Eichberg
+ */
+public class Main {
+
+ /**
+ * Starts the application.
+ *
+ * @param args
+ * a list of filenames, a new editor frame is created for each
+ * file.
+ */
+ public static void main(String[] args) {
+
+ if (System.getProperty("os.name").startsWith("Mac OS X")) {
+ // we have to avoid tight coupling to make the project usable on
+ // different platforms
+ try {
+ Class.forName("de.tud.cs.se.flashcards.MacOSXAdapter");
+ } catch (ClassNotFoundException cnfe) {
+ System.err
+ .println("Setting up the Mac OS X integration failed. Error:");
+ cnfe.printStackTrace(System.err);
+ }
+ } else {
+ try {
+ UIManager.setLookAndFeel(UIManager
+ .getSystemLookAndFeelClassName());
+ } catch (Exception e) {
+ System.err
+ .println("The native system look and feel is not available ("
+ + e.getLocalizedMessage() + ").");
+ }
+ }
+
+ // show all user interface related properties
+ Iterator> properties = javax.swing.UIManager
+ .getDefaults().entrySet().iterator();
+ while (properties.hasNext()) {
+ Entry property = properties.next();
+ System.out.println(property.getKey() + " = " + property.getValue());
+ }
+
+ // let's try to open one of the documents specified on the command line
+ boolean documentOpened = false;
+ if (args.length > 0) {
+ for (String arg : args) {
+ if (FlashcardsWindow.createFlashcardsEditor(new File(arg)))
+ documentOpened = true;
+ }
+ }
+ // either the user didn't specify a document on the command line or all
+ // specified documents
+ // were unreadable
+ if (!documentOpened) {
+ new FlashcardsWindow(FlashcardSeries.createInitialFlashcardSeries());
+ }
+ }
+}
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/model/Flashcard.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/model/Flashcard.java
new file mode 100644
index 00000000..9f7962c2
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/model/Flashcard.java
@@ -0,0 +1,102 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.model;
+
+import java.awt.Dimension;
+import java.io.Serializable;
+
+/**
+ * A very simple flashcard.
+ *
+ * @author Michael Eichberg
+ */
+public class Flashcard implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * The width of a flashcard.
+ */
+ public static int WIDTH = 600;
+
+ /**
+ * The height of a flashcard.
+ */
+ public static int HEIGHT = 400;
+
+ /**
+ * The dimension of flashcards.
+ *
+ * @see #WIDTH
+ * @see #HEIGHT
+ */
+ public static final Dimension FLASHCARD_DIMENSION = new Dimension(WIDTH,
+ HEIGHT);
+
+ private String question;
+
+ private String answer;
+
+ public Flashcard(String question, String answer) {
+
+ this.question = question;
+ this.answer = answer;
+ }
+
+ // convenience constructor
+ public Flashcard() {
+
+ this("", "");
+ }
+
+ public String getAnswer() {
+
+ return answer;
+ }
+
+ public String getQuestion() {
+
+ return question;
+ }
+
+ public void setAnswer(String answer) {
+
+ this.answer = answer;
+ }
+
+ public void setQuestion(String question) {
+
+ this.question = question;
+ }
+
+}
\ No newline at end of file
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/model/FlashcardSeries.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/model/FlashcardSeries.java
new file mode 100644
index 00000000..42b02003
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/model/FlashcardSeries.java
@@ -0,0 +1,169 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.model;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.swing.ListModel;
+import javax.swing.event.ListDataEvent;
+import javax.swing.event.ListDataListener;
+
+/**
+ * A series represents a set of flashcards and basically provides a set of
+ * management functions.
+ *
+ * @author Michael Eichberg
+ */
+public class FlashcardSeries implements ListModel {
+ // We did deliberately not extend "AbstractListModel" to avoid that Java
+ // Serialization of this
+ // (then Serializable) class would store references to listeners that do not
+ // belong to the model.
+
+ /**
+ * Convenience method to create an initial flashcard series.
+ */
+ public static FlashcardSeries createInitialFlashcardSeries() {
+
+ FlashcardSeries flashcards = new FlashcardSeries();
+ flashcards.addCard(new Flashcard("lose Kopplung", "loose coupling"));
+ flashcards.addCard(new Flashcard("hoher Zusammenhalt", "high cohesion"));
+ flashcards.addCard(new Flashcard("Stellvertreter", "Proxy"));
+ flashcards.addCard(new Flashcard("Entwurfsmuster", "Design Pattern"));
+ flashcards.addCard(new Flashcard("Beispiel", "Example"));
+ flashcards.addCard(new Flashcard("Haus", "House"));
+ flashcards.addCard(new Flashcard("Hund", "Dog"));
+
+ return flashcards;
+ }
+
+ public static final ListDataListener[] NO_LIST_DATA_LISTENERS = new ListDataListener[0];
+
+ // This array is treated as immutable (i.e., its content never changes!)
+ private ListDataListener[] listDataListeners = NO_LIST_DATA_LISTENERS;
+
+ private final List flashcards = new ArrayList();
+
+ public synchronized void addListDataListener(ListDataListener l) {
+
+ // It is an error to register the same listener twice!
+
+ ListDataListener[] newListDataListeners = new ListDataListener[this.listDataListeners.length + 1];
+ System.arraycopy(this.listDataListeners, 0, newListDataListeners, 0,
+ this.listDataListeners.length);
+ newListDataListeners[this.listDataListeners.length] = l;
+
+ this.listDataListeners = newListDataListeners;
+ }
+
+ public synchronized void removeListDataListener(ListDataListener l) {
+
+ // It is an error to try to remove a listener that is not (no longer)
+ // registered.
+
+ ListDataListener[] newListDataListeners = new ListDataListener[this.listDataListeners.length - 1];
+ int index = 0;
+ for (; index < listDataListeners.length; index++) {
+ if (listDataListeners[index] == l)
+ break;
+ }
+ System.arraycopy(listDataListeners, 0, newListDataListeners, 0, index);
+ if (index < (listDataListeners.length - 1)) {
+ System.arraycopy(listDataListeners, index + 1,
+ newListDataListeners, index, listDataListeners.length
+ - (index + 1));
+ }
+
+ this.listDataListeners = newListDataListeners;
+ }
+
+ protected ListDataListener[] getListDataListeners() {
+
+ return listDataListeners;
+ }
+
+ protected void fireIntervalAdded(Object source, int index0, int index1) {
+
+ if (listDataListeners != NO_LIST_DATA_LISTENERS) {
+ ListDataListener[] listeners = listDataListeners;
+ ListDataEvent e = new ListDataEvent(source,
+ ListDataEvent.INTERVAL_ADDED, index0, index1);
+
+ for (int i = listeners.length - 1; i >= 0; i -= 1) {
+ listeners[i].intervalAdded(e);
+ }
+ }
+ }
+
+ protected void fireIntervalRemoved(Object source, int index0, int index1) {
+
+ if (listDataListeners != NO_LIST_DATA_LISTENERS) {
+ ListDataListener[] listeners = listDataListeners;
+ ListDataEvent e = new ListDataEvent(source,
+ ListDataEvent.INTERVAL_REMOVED, index0, index1);
+
+ for (int i = listeners.length - 1; i >= 0; i -= 1) {
+ listeners[i].intervalRemoved(e);
+ }
+ }
+ }
+
+ public void addCard(Flashcard flashcard) {
+
+ flashcards.add(0, flashcard);
+ fireIntervalAdded(this, 0, 0);
+ }
+
+ public void removeCards(int[] indices) {
+
+ int i = indices.length - 1;
+ while (i >= 0) {
+ int index = indices[i];
+ flashcards.remove(index);
+ fireIntervalRemoved(this, index, index);
+ i -= 1;
+ }
+ }
+
+ public Flashcard getElementAt(int i) {
+
+ return flashcards.get(i);
+ }
+
+ public int getSize() {
+
+ return flashcards.size();
+ }
+
+}
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/persistence/Store.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/persistence/Store.java
new file mode 100644
index 00000000..1f99e771
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/persistence/Store.java
@@ -0,0 +1,135 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.persistence;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+
+import org.apache.commons.io.IOUtils;
+
+import de.tud.cs.se.flashcards.model.Flashcard;
+import de.tud.cs.se.flashcards.model.FlashcardSeries;
+
+/**
+ * Some helper methods related to persisting a flashcard series.
+ *
+ * Persistence is currently not handled properly! Do never
+ * use Java Serialization for long term storage!
+ *
+ *
+ * @author Michael Eichberg
+ */
+public class Store {
+
+ public static final String FILE_ENDING = ".flashcards";
+
+ public static FlashcardSeries openSeries(File file) throws IOException {
+
+ ObjectInputStream oin = null;
+ try {
+
+ FlashcardSeries series = new FlashcardSeries();
+
+ oin = new ObjectInputStream(new FileInputStream(file));
+ int size = oin.readInt();
+ for (int i = 0; i < size; i++) {
+ series.addCard((Flashcard) oin.readObject());
+ }
+
+ return series;
+ } catch (ClassNotFoundException e) {
+ // the file did contain something unexpected...
+ throw new IOException(e);
+ } finally {
+ if (oin != null)
+ IOUtils.closeQuietly(oin);
+ }
+ }
+
+ public static void importSeries(FlashcardSeries series, File file) throws IOException {
+
+ ObjectInputStream oin = null;
+ try {
+
+ oin = new ObjectInputStream(new FileInputStream(file));
+ int size = oin.readInt();
+ for (int i = 0; i < size; i++) {
+
+ Flashcard import_card = (Flashcard) oin.readObject();
+
+ boolean b = false; //is card found in my own series?
+ for(int j = 0; j < series.getSize(); j++){
+ if(series.getElementAt(j).getQuestion().equals(import_card.getQuestion())){
+ b = true;
+ break;
+ }
+ }
+
+ if(!b){
+ series.addCard(import_card);
+ }
+ }
+
+ return;
+ } catch (ClassNotFoundException e) {
+ // the file did contain something unexpected...
+ throw new IOException(e);
+ } finally {
+ if (oin != null)
+ IOUtils.closeQuietly(oin);
+ }
+
+ }
+
+ public static void saveSeries(FlashcardSeries series, File file)
+ throws IOException {
+
+ ObjectOutputStream oout = null;
+ try {
+ oout = new ObjectOutputStream(new FileOutputStream(file));
+ oout.writeInt(series.getSize());
+ for (int i = series.getSize() - 1; i >= 0; i -= 1) {
+ oout.writeObject(series.getElementAt(i));
+ }
+ } finally {
+ if (oout != null)
+ oout.close();
+ }
+
+ }
+
+}
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/FlashcardEditor.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/FlashcardEditor.java
new file mode 100644
index 00000000..ec499dfa
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/FlashcardEditor.java
@@ -0,0 +1,214 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.ui;
+
+import java.awt.BorderLayout;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+
+import javax.swing.BorderFactory;
+import javax.swing.Box;
+import javax.swing.JButton;
+import javax.swing.JDialog;
+import javax.swing.JLabel;
+import javax.swing.JScrollPane;
+import javax.swing.JTextArea;
+import javax.swing.JTextField;
+import javax.swing.ScrollPaneConstants;
+import javax.swing.UIManager;
+import javax.swing.border.BevelBorder;
+
+import de.tud.cs.se.flashcards.model.Flashcard;
+
+/**
+ * An editor to edit basic flashcards.
+ *
+ * @author Michael Eichberg
+ */
+public class FlashcardEditor {
+
+ private final FlashcardsWindow owner;
+
+ // GUI components
+
+ private final JDialog dialog;
+
+ private final Box questionBox;
+
+ private final JLabel questionLabel;
+
+ private final JTextField questionField;
+
+ private final Box answerBox;
+
+ private final JLabel answerLabel;
+
+ private final JScrollPane answerTextAreaScrollPane;
+
+ private final JTextArea answerTextArea;
+
+ private final Box okCancelBox;
+
+ private final JButton okButton;
+
+ private final JButton cancelButton;
+
+ /**
+ * Creates a new editor that can be used to edit flashcards.
+ *
+ * @param owner
+ * This editor's parent frame.
+ */
+ public FlashcardEditor(FlashcardsWindow owner) {
+
+ this.owner = owner;
+
+ // Setup the components:
+
+ questionField = new JTextField();
+ questionField.setAlignmentX(0.0f);
+
+ questionLabel = new JLabel("Question");
+ questionLabel.setBorder(BorderFactory.createEmptyBorder(2, 2, 2, 2));
+ questionLabel.setAlignmentX(0.0f);
+
+ questionBox = Box.createVerticalBox();
+ questionBox.setBorder(BorderFactory.createCompoundBorder(
+ BorderFactory.createEmptyBorder(10, 10, 10, 10),
+ BorderFactory.createBevelBorder(BevelBorder.LOWERED)));
+ questionBox.add(questionLabel);
+ questionBox.add(Box.createVerticalStrut(5));
+ questionBox.add(questionField);
+
+ answerLabel = new JLabel("Answer");
+ answerLabel.setAlignmentX(0.0f);
+ answerLabel.setBorder(BorderFactory.createEmptyBorder(2, 2, 2, 2));
+
+ answerTextArea = new JTextArea();
+ answerTextArea.setLineWrap(true);
+ answerTextArea.setWrapStyleWord(true);
+
+ answerTextAreaScrollPane = new JScrollPane(answerTextArea);
+ answerTextAreaScrollPane.setAlignmentX(0.0f);
+ answerTextAreaScrollPane.setBorder(UIManager
+ .getBorder("ScrollPane.border"));
+ answerTextAreaScrollPane
+ .setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS);
+
+ answerBox = Box.createVerticalBox();
+ answerBox.setBorder(BorderFactory.createCompoundBorder(
+ BorderFactory.createEmptyBorder(10, 10, 10, 10),
+ BorderFactory.createBevelBorder(BevelBorder.LOWERED)));
+ answerBox.add(answerLabel);
+ answerBox.add(Box.createVerticalStrut(5));
+ answerBox.add(answerTextAreaScrollPane);
+
+ okButton = new JButton("Ok");
+
+ cancelButton = new JButton("Cancel");
+
+ okCancelBox = Box.createHorizontalBox();
+ okCancelBox.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));
+ okCancelBox.add(Box.createGlue());
+ okCancelBox.add(cancelButton);
+ okCancelBox.add(okButton);
+
+ dialog = new JDialog(this.owner.getFrame(), "Edit Flashcard", true);
+ dialog.getRootPane().putClientProperty("Window.style", "small");
+ dialog.setDefaultCloseOperation(JDialog.HIDE_ON_CLOSE);
+ dialog.setMinimumSize(new java.awt.Dimension(320, 240));
+ dialog.setSize(640, 480);
+ dialog.setLocationRelativeTo(this.owner.getFrame());
+ dialog.getContentPane().add(questionBox, BorderLayout.NORTH);
+ dialog.getContentPane().add(answerBox);
+ dialog.getContentPane().add(okCancelBox, BorderLayout.SOUTH);
+
+ // Configure the event handling:
+
+ cancelButton.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+
+ update = false;
+ dialog.setVisible(false);
+ }
+ });
+ okButton.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+
+ update = true;
+ dialog.setVisible(false);
+ }
+ });
+ }
+
+ /**
+ * True if the card needs to be udpated, false otherwise. This variable is
+ * set when the dialog is closed.
+ */
+ private boolean update = false;
+
+ /**
+ * Edits a given flashcard. If the flashcard was edited, then
+ * true is returned.
+ *
+ * @param card
+ * The flashcard that may be edited. The flashcard is used to
+ * initialize this dialog.
+ * @return true if the card was edited; false otherwise.
+ */
+ public boolean edit(Flashcard card) {
+
+ // set to false to make sure that the card is not updated, when the
+ // dialog is closed
+ // using the dialogs "close" button
+ update = false;
+
+ // configure the editor
+ questionField.setText(card.getQuestion());
+ answerTextArea.setText(card.getAnswer());
+
+ // show the dialog to enable the user to edit the flashcard
+ dialog.setVisible(true);
+
+ // the dialog is closed
+ if (update) {
+ card.setQuestion(questionField.getText());
+ card.setAnswer(answerTextArea.getText());
+ }
+
+ return update;
+ }
+
+}
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/FlashcardsWindow.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/FlashcardsWindow.java
new file mode 100644
index 00000000..9b1506a8
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/FlashcardsWindow.java
@@ -0,0 +1,551 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.ui;
+
+import java.awt.BorderLayout;
+import java.awt.Component;
+import java.awt.FileDialog;
+import java.awt.Toolkit;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+import java.awt.event.ItemEvent;
+import java.awt.event.KeyEvent;
+import java.awt.event.WindowAdapter;
+import java.awt.event.WindowEvent;
+import java.io.File;
+import java.io.FilenameFilter;
+import java.io.IOException;
+
+import javax.swing.BorderFactory;
+import javax.swing.Box;
+import javax.swing.JButton;
+import javax.swing.JFrame;
+import javax.swing.JList;
+import javax.swing.JMenu;
+import javax.swing.JMenuBar;
+import javax.swing.JMenuItem;
+import javax.swing.JOptionPane;
+import javax.swing.JScrollPane;
+import javax.swing.JToolBar;
+import javax.swing.KeyStroke;
+import javax.swing.ScrollPaneConstants;
+import javax.swing.SwingUtilities;
+import javax.swing.event.ChangeEvent;
+import javax.swing.event.ListDataEvent;
+import javax.swing.event.ListDataListener;
+import javax.swing.event.ListSelectionEvent;
+import javax.swing.event.ListSelectionListener;
+
+import de.tud.cs.se.flashcards.model.Flashcard;
+import de.tud.cs.se.flashcards.model.FlashcardSeries;
+import de.tud.cs.se.flashcards.persistence.Store;
+import java.awt.event.ItemListener;
+import javax.swing.JLabel;
+import javax.swing.ListCellRenderer;
+import javax.swing.event.ChangeListener;
+
+/**
+ * A Frame is always associated with exactly one document and it is the parent
+ * of all related dialogs etc.
+ *
+ * @author Michael Eichberg
+ * @author Ralf Mitschke
+ */
+public class FlashcardsWindow {
+
+ // The UI components:
+
+ private final JFrame frame;
+
+ private final JMenuBar menuBar;
+
+ private final JMenu fileMenu;
+
+ private final JMenuItem newFileMenuItem;
+
+ private final JMenuItem openFileMenuItem;
+
+ private final JMenuItem importFileMenuItem;
+
+ private final JMenuItem saveFileMenuItem;
+
+ private final JMenuItem saveAsFileMenuItem;
+
+ private final JMenuItem closeFileMenuItem;
+
+ private final JToolBar toolbar;
+
+ private final JButton addButton;
+
+ private final JButton removeButton;
+
+ private final JButton editButton;
+
+ private final JButton playButton;
+
+ private final JScrollPane listScrollPane;
+
+ private final JList list;
+
+ private final FlashcardEditor flashcardEditor;
+
+ private final LearnDialog learnDialog;
+
+ private final FileDialog fileDialog;
+
+ // State of the editor:
+
+ private final FlashcardSeries series;
+
+ private File file;
+
+ protected FlashcardsWindow(File file) throws IOException {
+ this(Store.openSeries(file));
+
+ this.file = file;
+ Utilities.setFrameTitle(frame, file);
+ }
+
+ public static boolean createFlashcardsEditor(File file) {
+ try {
+ new FlashcardsWindow(file);
+ return true;
+ } catch (Exception e) {
+ JOptionPane.showMessageDialog(
+ null,
+ "The document \"" + file.getName()
+ + "\" could not be read." + "\n"
+ + e.getLocalizedMessage(), "",
+ JOptionPane.WARNING_MESSAGE);
+ return false;
+ }
+ }
+
+ public FlashcardsWindow(FlashcardSeries series) {
+
+ /*
+ * General Design Decision(s):
+ *
+ * ActionListener do not contain domain logic; they always delegate to
+ * corresponding methods.
+ *
+ * All errors are handled as early as possible.
+ *
+ * A Frame is associated with exactly one FlashcardSeries.
+ */
+
+ this.series = series;
+
+ // setup of this frame; we need to do it here since the rootpane's
+ // client property has to set before the other components are created
+ frame = new JFrame();
+ frame.getRootPane().putClientProperty("apple.awt.brushMetalLook",
+ java.lang.Boolean.TRUE);
+
+ Utilities.setFrameTitle(frame, file);
+
+ // dialogs and other components that are related to this frame
+ flashcardEditor = new FlashcardEditor(this);
+
+ learnDialog = new LearnDialog(this);
+
+ fileDialog = new java.awt.FileDialog(frame);
+ fileDialog.setFilenameFilter(new FilenameFilter() {
+
+ public boolean accept(File directory, String name) {
+ return name.endsWith(Store.FILE_ENDING);
+ }
+ });
+
+ // setup the menu and its listeners
+ newFileMenuItem = new JMenuItem("New");
+ newFileMenuItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_N,
+ Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));
+
+ newFileMenuItem.addActionListener(new ActionListener() {
+
+ @Override
+ public void actionPerformed(ActionEvent e) {
+ new FlashcardsWindow(FlashcardSeries.createInitialFlashcardSeries());
+ }
+
+ });
+
+ openFileMenuItem = new JMenuItem("Open File...");
+ openFileMenuItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_O,
+ Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));
+ openFileMenuItem.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+ openFlashcardSeries();
+ }
+ });
+
+ importFileMenuItem = new JMenuItem("Import File...");
+ importFileMenuItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_I,
+ Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));
+ importFileMenuItem.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+ importFlashcardSeries();
+ }
+ });
+
+ saveFileMenuItem = new JMenuItem("Save");
+ saveFileMenuItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_S,
+ Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));
+ saveFileMenuItem.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+ saveFlashcardSeries();
+ }
+ });
+
+ saveAsFileMenuItem = new JMenuItem("Save As...");
+ saveAsFileMenuItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_S,
+ (java.awt.event.InputEvent.SHIFT_MASK | Toolkit
+ .getDefaultToolkit().getMenuShortcutKeyMask())));
+ saveAsFileMenuItem.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+ saveAsFlashcardSeries();
+ }
+ });
+
+ closeFileMenuItem = new JMenuItem("Close Window");
+ closeFileMenuItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_W,
+ Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));
+ closeFileMenuItem.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+ closeFlashcardEditor();
+ }
+ });
+
+ fileMenu = new JMenu("File");
+ fileMenu.add(newFileMenuItem);
+ fileMenu.addSeparator();
+ fileMenu.add(openFileMenuItem);
+ fileMenu.add(importFileMenuItem);
+ fileMenu.addSeparator();
+ fileMenu.add(saveFileMenuItem);
+ fileMenu.add(saveAsFileMenuItem);
+ fileMenu.addSeparator();
+ fileMenu.add(closeFileMenuItem);
+
+ menuBar = new JMenuBar();
+ menuBar.add(fileMenu);
+
+ addButton = Utilities.createToolBarButton(" Create ", "list-add.png",
+ "create new flashcard");
+ addButton.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+
+ createFlashcard();
+ }
+ });
+
+ removeButton = Utilities.createToolBarButton(" Delete ",
+ "list-remove.png", "remove selected flashcards");
+ removeButton.setEnabled(false);
+ removeButton.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+
+ removeFlashcards();
+ }
+ });
+
+ editButton = Utilities.createToolBarButton(" Edit ",
+ "accessories-text-editor.png", "edit selected flashcard");
+ editButton.setEnabled(false);
+ editButton.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+
+ editFlashcard();
+ }
+ });
+
+ list = new JList(series);
+
+ list.setCellRenderer(new ListCellRenderer(){
+ public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
+ JLabel label = new JLabel(((Flashcard)value).getQuestion());
+ label.setEnabled(list.isEnabled());
+ label.setFont(list.getFont());
+ label.setOpaque(true);
+
+ if (isSelected) {
+ label.setBackground(list.getSelectionBackground());
+ label.setForeground(list.getSelectionForeground());
+ } else {
+ label.setBackground(list.getBackground());
+ label.setForeground(list.getForeground());
+ }
+
+ return label;
+ }
+ });
+
+ list.addListSelectionListener(new ListSelectionListener() {
+
+ public void valueChanged(ListSelectionEvent event) {
+ // Only GUI related functionality:
+ if (list.getSelectedIndex() != -1) {
+ removeButton.setEnabled(true);
+ editButton.setEnabled(true);
+ } else {
+ removeButton.setEnabled(false);
+ editButton.setEnabled(false);
+ }
+ }
+ });
+
+ listScrollPane = new JScrollPane(list);
+ listScrollPane.setBorder(BorderFactory.createEmptyBorder());
+ listScrollPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS);
+
+ playButton = Utilities.createToolBarButton(" Learn ",
+ "media-playback-start.png", "learn flashcards");
+
+
+ playButton.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent event) {
+
+ learn();
+ }
+ });
+
+ playButton.addItemListener(new ItemListener() {
+
+ public void itemStateChanged(ItemEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+ } );
+
+
+
+ series.addListDataListener(new ListDataListener() {
+ public void intervalAdded(ListDataEvent e) {
+ if(((FlashcardSeries)e.getSource()).getSize() <= 0){
+ playButton.setEnabled(false);
+ } else {
+ playButton.setEnabled(true);
+ }
+ }
+
+ public void intervalRemoved(ListDataEvent e) {
+ if(((FlashcardSeries)e.getSource()).getSize() <= 0){
+ playButton.setEnabled(false);
+ } else {
+ playButton.setEnabled(true);
+ }
+ }
+
+ public void contentsChanged(ListDataEvent e) {}
+ });
+
+
+
+
+ toolbar = new JToolBar();
+ toolbar.putClientProperty("JToolBar.isRollover", Boolean.FALSE);
+ toolbar.add(addButton);
+ toolbar.add(removeButton);
+ toolbar.addSeparator();
+ toolbar.add(editButton);
+ toolbar.add(Box.createHorizontalGlue());
+ toolbar.add(playButton);
+
+ toolbar.setFloatable(false);
+
+ frame.setJMenuBar(menuBar);
+ frame.getContentPane().add(listScrollPane);
+ frame.getContentPane().add(toolbar, BorderLayout.NORTH);
+ frame.setSize(640, 480);
+ frame.setLocationByPlatform(true);
+ frame.setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);
+ frame.addWindowListener(new WindowAdapter() {
+
+ @Override
+ public void windowClosed(WindowEvent event) {
+
+ SwingUtilities.invokeLater(new Runnable() {
+
+ public void run() {
+ // we have to make sure that the JFrame object will be
+ // collected...
+ // (the VM terminates if all frames are disposed and
+ // finally collected)
+ System.gc();
+ }
+ });
+ }
+
+ });
+
+ // Everything is setup; show the window:
+ frame.setVisible(true);
+ }
+
+ // Implementation of the "logic":
+
+ public FlashcardSeries getSeries() {
+ return series;
+ }
+
+ public JFrame getFrame() {
+ return frame;
+ }
+
+ protected void openFlashcardSeries() {
+ fileDialog.setMode(FileDialog.LOAD);
+ fileDialog.setVisible(true);
+ String filename = fileDialog.getFile();
+ if (filename != null) {
+ if (!filename.endsWith(Store.FILE_ENDING))
+ filename += Store.FILE_ENDING;
+ File file = new File(fileDialog.getDirectory(), filename);
+ createFlashcardsEditor(file);
+ }
+ }
+
+ public void importFlashcardSeries() {
+ fileDialog.setMode(FileDialog.LOAD);
+ fileDialog.setVisible(true);
+ String filename = fileDialog.getFile();
+
+ if(series == null){
+ JOptionPane.showMessageDialog(
+ null,
+ "You have to open a series first.", "",
+ JOptionPane.WARNING_MESSAGE);
+ return;
+ }
+
+ if (filename != null) {
+ if (!filename.endsWith(Store.FILE_ENDING))
+ filename += Store.FILE_ENDING;
+ File file = new File(fileDialog.getDirectory(), filename);
+ try {
+ Store.importSeries(this.series, file);
+ } catch (IOException e) {
+ JOptionPane.showMessageDialog(
+ null,
+ "The document \"" + file.getName()
+ + "\" could not be read." + "\n"
+ + e.getLocalizedMessage(), "",
+ JOptionPane.WARNING_MESSAGE);
+
+ return;
+ }
+ }
+ }
+
+ protected void saveFlashcardSeries() {
+ if (file == null)
+ saveAsFlashcardSeries();
+ else
+ doSave(file);
+ }
+
+ protected void saveAsFlashcardSeries() {
+ fileDialog.setMode(FileDialog.SAVE);
+ fileDialog.setVisible(true);
+ String filename = fileDialog.getFile();
+ if (filename != null) {
+ if (!filename.endsWith(Store.FILE_ENDING))
+ filename += Store.FILE_ENDING;
+
+ File newFile = new File(fileDialog.getDirectory(), filename);
+ if (newFile.exists()) {
+ if (JOptionPane
+ .showConfirmDialog(
+ frame,
+ "The file with the name:\n"
+ + filename
+ + "\nalready exists.\nDo you want to overwrite the file?",
+ "Warning", JOptionPane.YES_NO_OPTION,
+ JOptionPane.WARNING_MESSAGE) == JOptionPane.NO_OPTION)
+ return;
+ }
+ doSave(newFile);
+ }
+
+ }
+
+ protected void doSave(File file) {
+ try {
+
+ Store.saveSeries(series, file);
+
+ // Saving the file was successful:
+ this.file = file;
+ Utilities.setFrameTitle(frame, file);
+
+ } catch (IOException e) {
+ JOptionPane.showMessageDialog(frame, "Could not save flashcards",
+ "Saving the flashcards to :\n" + file.getName()
+ + "\nfailed.", JOptionPane.ERROR_MESSAGE);
+ }
+ }
+
+ public void learn() {
+ learnDialog.show();
+ }
+
+ protected void closeFlashcardEditor() {
+ frame.setVisible(false);
+ frame.dispose(); // required to give up all resources
+ }
+
+ protected void createFlashcard() {
+ Flashcard card = new Flashcard();
+ if (flashcardEditor.edit(card))
+ series.addCard(card);
+ }
+
+ protected void removeFlashcards() {
+ FlashcardsWindow.this.series.removeCards(list.getSelectedIndices());
+ list.clearSelection();
+ }
+
+ protected void editFlashcard() {
+ int index = list.getSelectedIndex();
+ flashcardEditor.edit(series.getElementAt(index));
+ }
+
+}
\ No newline at end of file
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/LearnDialog.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/LearnDialog.java
new file mode 100644
index 00000000..70d86d38
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/LearnDialog.java
@@ -0,0 +1,236 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.ui;
+
+import static de.tud.cs.se.flashcards.ui.Utilities.createImageIcon;
+
+import java.awt.BorderLayout;
+import java.awt.Dimension;
+import java.awt.Toolkit;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+
+import javax.swing.BorderFactory;
+import javax.swing.Box;
+import javax.swing.JButton;
+import javax.swing.JComponent;
+import javax.swing.JDialog;
+import javax.swing.JLabel;
+import javax.swing.SwingConstants;
+import javax.swing.Timer;
+import javax.swing.UIManager;
+import javax.swing.border.BevelBorder;
+import javax.swing.border.EtchedBorder;
+
+import de.tud.cs.se.flashcards.model.Flashcard;
+import de.tud.cs.se.flashcards.model.FlashcardSeries;
+
+/**
+ * This dialog first renders a flashcard's question and then the answer.
+ * Additionally, the logic to step through a series of flashcards is provided.
+ *
+ * @author Michael Eichberg
+ */
+public class LearnDialog {
+
+ private final FlashcardsWindow owner;
+
+ private final JDialog dialog;
+
+ protected final Box headerBox;
+
+ protected final JLabel titleLabel;
+
+ protected final JButton cancelButton;
+
+ protected final JLabel contentLabel;
+
+ protected final Box navigationBox;
+
+ protected final JButton nextButton;
+
+ protected final JLabel timeLabel;
+
+ protected final Timer timer;
+
+ protected int secondCounter = 0;
+
+ public LearnDialog(FlashcardsWindow owner) {
+
+ this.owner = owner;
+
+ dialog = new JDialog(owner.getFrame(), true);
+ dialog.getRootPane().putClientProperty(
+ "apple.awt.draggableWindowBackground", Boolean.TRUE);
+ dialog.setDefaultCloseOperation(JDialog.HIDE_ON_CLOSE);
+
+ // Create the header components:
+ titleLabel = new JLabel(); // need to be initialized...
+ titleLabel.setBorder(BorderFactory.createEmptyBorder(2, 2, 10, 10));
+ titleLabel.setVerticalAlignment(SwingConstants.CENTER);
+ titleLabel
+ .setPreferredSize(new JLabel("XXXXXXXXXX").getPreferredSize());
+
+ cancelButton = new JButton(createImageIcon("process-stop.png",
+ "stop learning"));
+ cancelButton.setBorderPainted(false);
+ cancelButton.addActionListener(new ActionListener() {
+
+ public void actionPerformed(ActionEvent e) {
+ dialog.setVisible(false);
+ }
+ });
+
+ headerBox = Box.createHorizontalBox();
+ headerBox.add(titleLabel);
+ headerBox.add(Box.createHorizontalGlue());
+ headerBox.add(cancelButton);
+
+ contentLabel = new JLabel(); // need to be initialized...
+ contentLabel.setSize(Flashcard.FLASHCARD_DIMENSION);
+ contentLabel.setPreferredSize(Flashcard.FLASHCARD_DIMENSION);
+ contentLabel.setBorder(BorderFactory
+ .createEtchedBorder(EtchedBorder.LOWERED));
+ contentLabel.setFont(UIManager.getFont("FormattedTextField.font"));
+ contentLabel.setHorizontalAlignment(SwingConstants.CENTER);
+
+ // setup the footer
+ nextButton = new JButton(createImageIcon("go-next.png", "next"));
+
+ timer = new Timer(1000, new ActionListener() {
+
+ @Override
+ public void actionPerformed(ActionEvent e) {
+ secondCounter++;
+ timeLabel.setText(" Time: " + secondCounter + "s");
+
+ }
+ });
+
+ timeLabel = new JLabel();
+
+
+ navigationBox = Box.createHorizontalBox();
+ navigationBox.add(timeLabel);
+ navigationBox.add(Box.createHorizontalGlue());
+ navigationBox.add(nextButton);
+ nextButton.addActionListener(new ActionListener() {
+ public void actionPerformed(ActionEvent event) {
+ next();
+ }
+ });
+
+ dialog.getContentPane().setLayout(new BorderLayout());
+ dialog.getContentPane().add(headerBox, BorderLayout.NORTH);
+ dialog.getContentPane().add(contentLabel, BorderLayout.CENTER);
+ dialog.getContentPane().add(navigationBox, BorderLayout.SOUTH);
+
+ Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
+ // dialog.setLocationRelativeTo(owner.getFrame());
+ dialog.setLocation(screenSize.width / 2 - (320),
+ screenSize.height / 2 - 240);
+ dialog.setUndecorated(true);
+ ((JComponent) dialog.getContentPane()).setBorder(BorderFactory
+ .createBevelBorder(BevelBorder.RAISED));
+ dialog.pack();
+ }
+
+ // The "core" logic:
+
+ enum State {
+ QUESTION, ANSWER
+ }
+
+ private State state = null; // initialized by "show"
+
+ private int index = 0; // initialized by "show"
+
+ public void show() {
+ timerStart();
+ state = State.QUESTION;
+ index = -1;
+ showNextQuestion();
+ dialog.setVisible(true);
+
+ }
+
+
+ private void timerStart(){
+ secondCounter = 0;
+ timer.restart();
+ timeLabel.setText(" Time: 0s");
+ timeLabel.setVisible(true);
+
+ }
+
+ private void timerStop(){
+ timer.stop();
+ timeLabel.setVisible(false);
+
+ }
+
+ private void next() {
+ switch (state) {
+
+ case ANSWER:
+ showNextQuestion();
+ timerStart();
+ state = State.QUESTION;
+ break;
+
+ case QUESTION:
+ showAnswer();
+ timerStop();
+ state = State.ANSWER;
+ break;
+ }
+ }
+
+ private void showNextQuestion() {
+ index++;
+ FlashcardSeries fs = owner.getSeries();
+ if (fs.getSize() > index) {
+ titleLabel.setText("Question");
+ contentLabel.setText(fs.getElementAt(index).getQuestion());
+ } else {
+ dialog.setVisible(false);
+ }
+ }
+
+ private void showAnswer() {
+ FlashcardSeries fs = owner.getSeries();
+ titleLabel.setText("Answer");
+ contentLabel.setText(fs.getElementAt(index).getAnswer());
+ }
+
+}
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Papers-icon-readme.html b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Papers-icon-readme.html
new file mode 100644
index 00000000..8315f751
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Papers-icon-readme.html
@@ -0,0 +1,67 @@
+
+
+
+
+Dimension Of Deskmod :: Icon Design
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Papers-icon.png b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Papers-icon.png
new file mode 100644
index 00000000..ea6bd3ee
Binary files /dev/null and b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Papers-icon.png differ
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/README-Icons b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/README-Icons
new file mode 100644
index 00000000..407409cf
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/README-Icons
@@ -0,0 +1,12 @@
+Tango Icon Theme
+----------------
+
+This is an icon theme that follows the Tango visual guidelines [1]. Currently
+it depends on Imagemagick for creation of 24x24 bitmaps by adding a 1px padding
+around the 22x22px version. For GNOME and KDE you will also need
+icon-naming-utils that allow the theme to work in these environments before
+they follow the new naming scheme [2].
+
+
+[1] http://tango-project.org/Tango_Icon_Theme_Guidelines
+[2] http://tango-project.org/Standard_Icon_Naming_Specification
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Utilities.java b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Utilities.java
new file mode 100644
index 00000000..bb2a83c5
--- /dev/null
+++ b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/Utilities.java
@@ -0,0 +1,118 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.ui;
+
+import java.io.File;
+import java.net.URL;
+
+import javax.swing.BorderFactory;
+import javax.swing.ImageIcon;
+import javax.swing.JButton;
+import javax.swing.JFrame;
+import javax.swing.SwingConstants;
+
+/**
+ * General helper methods related to building a user interface with Swing.
+ *
+ * @author Michael Eichberg
+ */
+public class Utilities {
+
+ private Utilities() {
+ // do nothing - just defined to avoid accidental instance creations
+ }
+
+ /**
+ * Sets the frame title based on the name of the file.
+ *
+ * @param frame
+ * The frame's title.
+ * @param file
+ * The document's file (which is edited in the frame.)
+ */
+ public static void setFrameTitle(JFrame frame, File file) {
+
+ if (file != null) {
+ frame.setTitle(file.getName().substring(0,
+ file.getName().lastIndexOf('.')));
+ frame.getRootPane().putClientProperty("Window.documentFile", file);
+ } else
+ frame.setTitle("untitled");
+ }
+
+ /**
+ * Creates a JButton object that can be placed in toolbars.
+ *
+ * @param title
+ * The (very short) title of the button. The title will be
+ * displayed below the button.
+ * @param iconPath
+ * The path to the ImageIcon.
+ * @param iconDescription
+ * A short description of the icon / the action.
+ * @return A new JButton.
+ * @see #createImageIcon(String, String)
+ */
+ public static JButton createToolBarButton(String title, String iconPath,
+ String iconDescription) {
+
+ JButton button = new JButton(title, createImageIcon(iconPath,
+ iconDescription));
+ button.setVerticalTextPosition(SwingConstants.BOTTOM);
+ button.setHorizontalTextPosition(SwingConstants.CENTER);
+ button.setOpaque(false);
+ button.setBorder(BorderFactory.createEmptyBorder());
+ return button;
+ }
+
+ /**
+ * Creates an image icon. If the resource is no longer / not available, an
+ * exception is thrown.
+ *
+ * @param path
+ * A path relative to the location of this classes compiled class
+ * file.
+ * @param description
+ * A short description of the icon.
+ */
+ public static ImageIcon createImageIcon(String path, String description) {
+
+ URL imgURL = Utilities.class.getResource(path);
+ if (imgURL != null) {
+ return new ImageIcon(imgURL, description);
+ } else {
+ throw new UnknownError("Missing resource: " + path + "("
+ + description + ")");
+ }
+ }
+}
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/accessories-text-editor.png b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/accessories-text-editor.png
new file mode 100644
index 00000000..c6b62851
Binary files /dev/null and b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/accessories-text-editor.png differ
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/go-next.png b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/go-next.png
new file mode 100644
index 00000000..6f3f65d3
Binary files /dev/null and b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/go-next.png differ
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/list-add.png b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/list-add.png
new file mode 100644
index 00000000..2acdd8f5
Binary files /dev/null and b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/list-add.png differ
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/list-remove.png b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/list-remove.png
new file mode 100644
index 00000000..c5524f72
Binary files /dev/null and b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/list-remove.png differ
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/media-playback-start.png b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/media-playback-start.png
new file mode 100644
index 00000000..66f32d89
Binary files /dev/null and b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/media-playback-start.png differ
diff --git a/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/process-stop.png b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/process-stop.png
new file mode 100644
index 00000000..b68290bf
Binary files /dev/null and b/ws2010/se/u7/project/src/de/tud/cs/se/flashcards/ui/process-stop.png differ
diff --git a/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/AllTests.java b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/AllTests.java
new file mode 100644
index 00000000..6734f8ad
--- /dev/null
+++ b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/AllTests.java
@@ -0,0 +1,51 @@
+/** License (BSD Style License):
+ * Copyright (c) 2010
+ * Software Engineering
+ * Department of Computer Science
+ * Technische Universität Darmstadt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * - Neither the name of the Software Engineering Group or Technische
+ * Universität Darmstadt nor the names of its contributors may be used to
+ * endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+package de.tud.cs.se.flashcards.model;
+
+import org.junit.runner.RunWith;
+import org.junit.runners.Suite;
+import de.tud.cs.se.flashcards.model.FlashcardSeriesTest;
+import de.tud.cs.se.flashcards.model.FlashcardTest;
+import de.tud.cs.se.flashcards.model.ConditionCoverageTest;
+import de.tud.cs.se.flashcards.model.ImportTest;
+
+@RunWith(Suite.class)
+@Suite.SuiteClasses({
+ FlashcardSeriesTest.class,
+ FlashcardTest.class,
+ ConditionCoverageTest.class,
+ ImportTest.class}
+)
+public class AllTests {
+
+}
diff --git a/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/ConditionCoverageTest.java b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/ConditionCoverageTest.java
new file mode 100644
index 00000000..39c17186
--- /dev/null
+++ b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/ConditionCoverageTest.java
@@ -0,0 +1,124 @@
+package de.tud.cs.se.flashcards.model;
+
+import javax.swing.event.ListDataEvent;
+import javax.swing.event.ListDataListener;
+import static org.junit.Assert.*;
+import org.junit.Test;
+import org.junit.Before;
+
+public class ConditionCoverageTest {
+
+ private FlashcardSeries m_flashcard_a;
+ private FlashcardSeries m_flashcard_b;
+
+@Before public void _setup(){
+ m_flashcard_a = new FlashcardSeries();
+ m_flashcard_b = new FlashcardSeries();
+
+ m_flashcard_a.addListDataListener(null);
+ }
+
+@Test public void test_removeListDataListener() {
+
+ //covers (true/false)
+ //if (listDataListeners[index] == l) -> true //index = 0
+ //if (index < (listDataListeners.length - 1)) -> false //index = 0; // listDataListeners.length - 1 = 0;
+
+ assertEquals(1, m_flashcard_a.getListDataListeners().length);
+
+ m_flashcard_a.removeListDataListener(null);
+
+ assertEquals(0, m_flashcard_a.getListDataListeners().length);
+ }
+
+@Test (expected = java.lang.NegativeArraySizeException.class)
+ public void test_removeListDataListener2() {
+
+
+ //covers (???/???)
+ //if (listDataListeners[index] == l) -> ??? (Wird nicht evaluiert)
+ //if (index < (listDataListeners.length - 1)) -> ??? (Wird nicht evaluiert)
+
+ assertEquals(0, m_flashcard_b.getListDataListeners().length);
+
+ m_flashcard_b.removeListDataListener(null);
+
+ assertEquals(0, m_flashcard_b.getListDataListeners().length);
+ }
+
+@Test (expected = java.lang.ArrayIndexOutOfBoundsException.class)
+ public void test_removeListDataListener3() {
+
+ //covers (false/false)
+ //if (listDataListeners[index] == l) -> false //index = 0
+ //if (index < (listDataListeners.length - 1)) -> false //index = 0; // listDataListeners.length - 1 = 0;
+
+ assertEquals(1, m_flashcard_a.getListDataListeners().length);
+
+ ListDataListener listener = new ListDataListener() {
+
+ public void intervalAdded(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ public void intervalRemoved(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ public void contentsChanged(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+ };
+
+ m_flashcard_a.removeListDataListener(listener);
+
+ assertEquals(1, m_flashcard_b.getListDataListeners().length);
+ }
+
+@Test public void test_removeListDataListener4() {
+
+ //covers (true/true)
+ //if (listDataListeners[index] == listner) -> true
+ //if (index < (listDataListeners.length - 1)) -> true //index = 1; // listDataListeners.length - 1 = 2;
+
+ assertEquals(1, m_flashcard_a.getListDataListeners().length);
+
+ ListDataListener listener = new ListDataListener() {
+
+ public void intervalAdded(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ public void intervalRemoved(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ public void contentsChanged(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+ };
+ ListDataListener listener2 = new ListDataListener() {
+
+ public void intervalAdded(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ public void intervalRemoved(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ public void contentsChanged(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+ };
+
+ m_flashcard_a.addListDataListener(listener);
+ m_flashcard_a.addListDataListener(listener2);
+
+ assertEquals(3, m_flashcard_a.getListDataListeners().length);
+
+ m_flashcard_a.removeListDataListener(listener);
+
+ assertEquals(2, m_flashcard_a.getListDataListeners().length);
+ }
+}
diff --git a/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/FlashcardSeriesTest.java b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/FlashcardSeriesTest.java
new file mode 100644
index 00000000..abe4a619
--- /dev/null
+++ b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/FlashcardSeriesTest.java
@@ -0,0 +1,131 @@
+package de.tud.cs.se.flashcards.model;
+
+import javax.swing.event.ListDataEvent;
+import javax.swing.event.ListDataListener;
+import static org.junit.Assert.*;
+import org.junit.Test;
+import org.junit.Before;
+
+public class FlashcardSeriesTest {
+
+ private FlashcardSeries m_flashcard_std_cards;
+ private FlashcardSeries m_flashcard_no_cards;
+
+@Before public void _setup(){
+ m_flashcard_std_cards = FlashcardSeries.createInitialFlashcardSeries();
+ m_flashcard_no_cards = new FlashcardSeries();
+ }
+
+@Test public void test_createInitialFlashcardSeries(){
+ assertFalse(m_flashcard_std_cards == null);
+ assertEquals("Hund", m_flashcard_std_cards.getElementAt(0).getQuestion());
+ assertEquals("Haus", m_flashcard_std_cards.getElementAt(1).getQuestion());
+ assertEquals("Beispiel", m_flashcard_std_cards.getElementAt(2).getQuestion());
+ assertEquals("Entwurfsmuster", m_flashcard_std_cards.getElementAt(3).getQuestion());
+ assertEquals("Stellvertreter", m_flashcard_std_cards.getElementAt(4).getQuestion());
+ assertEquals("hoher Zusammenhalt", m_flashcard_std_cards.getElementAt(5).getQuestion());
+ assertEquals("lose Kopplung", m_flashcard_std_cards.getElementAt(6).getQuestion());
+ }
+
+@Test public void test_addremoveListDataListener(){
+ m_flashcard_no_cards.addListDataListener(null);
+ assertEquals(null,m_flashcard_no_cards.getListDataListeners()[0]);
+
+ ListDataListener listener = new ListDataListener() {
+
+ public void intervalAdded(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ public void intervalRemoved(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ public void contentsChanged(ListDataEvent e) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+ };
+
+
+ m_flashcard_no_cards.addListDataListener(listener);
+ assertEquals(listener,m_flashcard_no_cards.getListDataListeners()[1]);
+ assertEquals(2, m_flashcard_no_cards.getListDataListeners().length);
+
+ m_flashcard_no_cards.removeListDataListener(listener);
+ assertEquals(1, m_flashcard_no_cards.getListDataListeners().length);
+ assertEquals(null,m_flashcard_no_cards.getListDataListeners()[0]);
+
+ m_flashcard_no_cards.removeListDataListener(null);
+ assertEquals(0, m_flashcard_no_cards.getListDataListeners().length);
+
+ m_flashcard_no_cards.addListDataListener(null);
+ m_flashcard_no_cards.addListDataListener(listener);
+ m_flashcard_no_cards.removeListDataListener(null);
+ m_flashcard_no_cards.removeListDataListener(listener);
+ assertEquals(0, m_flashcard_no_cards.getListDataListeners().length);
+ }
+
+@Test public void test_addremoveCard() {
+
+ assertEquals(0,m_flashcard_no_cards.getSize());
+ assertEquals(7, m_flashcard_std_cards.getSize());
+
+ m_flashcard_no_cards.addCard(new Flashcard("abc","ABC"));
+ assertEquals(1,m_flashcard_no_cards.getSize());
+
+ int[] i = {0};
+ m_flashcard_no_cards.removeCards(i);
+
+ assertEquals(0,m_flashcard_no_cards.getSize());
+ }
+
+@Test public void test_fireInterval() {
+ ListDataListener listener = new ListDataListener() {
+
+ public void intervalAdded(ListDataEvent e) {
+ assertEquals("ABC",((FlashcardSeries)e.getSource()).getElementAt(0).getAnswer());
+ }
+
+ public void intervalRemoved(ListDataEvent e) {
+ assertEquals("Dog",((FlashcardSeries)e.getSource()).getElementAt(0).getAnswer());
+ }
+
+ public void contentsChanged(ListDataEvent e) {}
+ };
+
+ m_flashcard_std_cards.addListDataListener(listener);
+ m_flashcard_std_cards.addCard(new Flashcard("abc","ABC"));
+ int[] i = {0};
+ m_flashcard_std_cards.removeCards(i);
+ m_flashcard_std_cards.getElementAt(0).setAnswer("Delphin");
+
+ }
+
+/*
+ protected void fireIntervalAdded(Object source, int index0, int index1) {
+
+ if (listDataListeners != NO_LIST_DATA_LISTENERS) {
+ ListDataListener[] listeners = listDataListeners;
+ ListDataEvent e = new ListDataEvent(source,
+ ListDataEvent.INTERVAL_ADDED, index0, index1);
+
+ for (int i = listeners.length - 1; i >= 0; i -= 1) {
+ listeners[i].intervalAdded(e);
+ }
+ }
+ }
+
+ protected void fireIntervalRemoved(Object source, int index0, int index1) {
+
+ if (listDataListeners != NO_LIST_DATA_LISTENERS) {
+ ListDataListener[] listeners = listDataListeners;
+ ListDataEvent e = new ListDataEvent(source,
+ ListDataEvent.INTERVAL_REMOVED, index0, index1);
+
+ for (int i = listeners.length - 1; i >= 0; i -= 1) {
+ listeners[i].intervalRemoved(e);
+ }
+ }
+ }
+ */
+}
diff --git a/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/FlashcardTest.java b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/FlashcardTest.java
new file mode 100644
index 00000000..6a8e8d49
--- /dev/null
+++ b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/FlashcardTest.java
@@ -0,0 +1,43 @@
+package de.tud.cs.se.flashcards.model;
+
+import org.junit.Test;
+import org.junit.Before;
+import static org.junit.Assert.*;
+
+public class FlashcardTest {
+
+ private Flashcard m_flashcard_text;
+ private Flashcard m_flashcard_no_text;
+
+@Before public void _setup(){
+
+ m_flashcard_text = new Flashcard("Wurde diese Karte getestet?","ja");
+ m_flashcard_no_text = new Flashcard();
+
+}
+
+@Test public void test_getAnswer() {
+
+ assertEquals("ja",m_flashcard_text.getAnswer());
+ assertEquals("",m_flashcard_no_text.getAnswer());
+ }
+
+@Test public void test_getQuestion() {
+
+ assertEquals("Wurde diese Karte getestet?",m_flashcard_text.getQuestion());
+ assertEquals("",m_flashcard_no_text.getQuestion());
+ }
+
+@Test public void test_setAnswer() {
+
+ m_flashcard_no_text.setAnswer("Not an empty answer");
+ assertEquals("Not an empty answer",m_flashcard_no_text.getAnswer());
+ }
+
+@Test public void test_setQuestion() {
+
+ m_flashcard_no_text.setQuestion("Not an empty question");
+ assertEquals("Not an empty question",m_flashcard_no_text.getQuestion());
+ }
+
+}
diff --git a/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/ImportTest.java b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/ImportTest.java
new file mode 100644
index 00000000..255af3bf
--- /dev/null
+++ b/ws2010/se/u7/project/test/de/tud/cs/se/flashcards/model/ImportTest.java
@@ -0,0 +1,103 @@
+package de.tud.cs.se.flashcards.model;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.Vector;
+
+import org.junit.Test;
+import org.junit.Before;
+import static org.junit.Assert.*;
+
+import de.tud.cs.se.flashcards.model.Flashcard;
+import de.tud.cs.se.flashcards.model.FlashcardSeries;
+import de.tud.cs.se.flashcards.persistence.Store;
+import de.tud.cs.se.flashcards.ui.FlashcardsWindow;
+
+public class ImportTest {
+
+ private FlashcardsWindow window;
+
+@Before public void _setup(){
+ window = new FlashcardsWindow(FlashcardSeries.createInitialFlashcardSeries());
+ }
+
+@Test (expected = IOException.class)
+ public void test_filenotfound() throws IOException {
+ Store.importSeries(window.getSeries(), new File(""));
+ }
+
+@Test public void test_keepowncard() throws IOException {
+ FlashcardSeries s = new FlashcardSeries();
+ s.addCard(new Flashcard("Hund", ""));
+
+ File file = new File("test_keepowncard" + Store.FILE_ENDING);
+ Store.saveSeries(s, file);
+
+ int cardcount = window.getSeries().getSize();
+
+ Store.importSeries(window.getSeries(), file);
+
+ for(int i=0; i < window.getSeries().getSize(); i++){
+ if(window.getSeries().getElementAt(i).getQuestion().equals("Hund")){
+ assertFalse(window.getSeries().getElementAt(i).getAnswer().equals(""));
+ }
+ }
+ assertEquals(window.getSeries().getSize(), cardcount);
+}
+
+@Test public void test_noduplicates() throws IOException {
+
+ FlashcardSeries s = FlashcardSeries.createInitialFlashcardSeries();
+
+ File file = new File("test_noduplicates" + Store.FILE_ENDING);
+ Store.saveSeries(s, file);
+
+ int cardcount = window.getSeries().getSize();
+
+ Store.importSeries(window.getSeries(), file);
+
+ Vector temp = new Vector();
+
+ for(int i=0; i < window.getSeries().getSize(); i++){
+ for(int j=0; j < temp.size(); j++){
+ assertFalse(temp.get(j).equals(window.getSeries().getElementAt(i).getQuestion()));
+ }
+
+ temp.add(window.getSeries().getElementAt(i).getQuestion());
+ }
+
+ assertEquals(window.getSeries().getSize(), cardcount);
+
+}
+
+@Test public void test_importnothing() throws IOException {
+
+ FlashcardSeries s = new FlashcardSeries();
+
+ File file = new File("test_importnothing" + Store.FILE_ENDING);
+ Store.saveSeries(s, file);
+
+ int cardcount = window.getSeries().getSize();
+
+ Store.importSeries(window.getSeries(), file);
+
+ assertEquals(window.getSeries().getSize(), cardcount);
+}
+
+@Test public void test_normalimport() throws IOException {
+
+ FlashcardSeries s = new FlashcardSeries();
+ s.addCard(new Flashcard("fwretxcdrhtet234xdf", "gsfdg"));
+
+ File file = new File("test_normalimport" + Store.FILE_ENDING);
+ Store.saveSeries(s, file);
+
+ int cardcount = window.getSeries().getSize();
+
+ Store.importSeries(window.getSeries(), file);
+
+ assertEquals(window.getSeries().getSize(), cardcount+1);
+
+}
+
+}
diff --git a/ws2010/se/voluntary-exercise/voluntary-exercise.pdf b/ws2010/se/voluntary-exercise/voluntary-exercise.pdf
new file mode 100644
index 00000000..7bc27107
Binary files /dev/null and b/ws2010/se/voluntary-exercise/voluntary-exercise.pdf differ