From 04e72003dee2a77fd82c7ee039379b4f3168a074 Mon Sep 17 00:00:00 2001 From: AndrewTrieu Date: Thu, 15 Dec 2022 17:31:20 +0200 Subject: [PATCH] Final --- .vscode/settings.json | 3 + README.md | 33 +++++ src/Main.java | 311 ++++++++++++++++++++++++++++++++++++++++++ src/Movie.java | 61 +++++++++ src/Seat.java | 41 ++++++ src/Showtime.java | 51 +++++++ src/Theater.java | 103 ++++++++++++++ src/TmdbExample.java | 53 +++++++ src/Venue.java | 28 ++++ 9 files changed, 684 insertions(+) create mode 100644 .vscode/settings.json create mode 100644 README.md create mode 100644 src/Main.java create mode 100644 src/Movie.java create mode 100644 src/Seat.java create mode 100644 src/Showtime.java create mode 100644 src/Theater.java create mode 100644 src/TmdbExample.java create mode 100644 src/Venue.java diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..a312124 --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,3 @@ +{ + "java.project.referencedLibraries": ["lib/**/*.jar", "/lib/json-20220924.jar"] +} diff --git a/README.md b/README.md new file mode 100644 index 0000000..0ec6457 --- /dev/null +++ b/README.md @@ -0,0 +1,33 @@ +# Movie Theater Management System + +This is a Java project that allows the user to manage a movie theater. The project consists of four classes: `Main`, `Venue`, `Theater`, `Seat`,`Movie`, and `Showtime`. + +The `Main` class contains the main method and is responsible for the user interface and interaction. It presents a menu with various options, such as adding and removing movies and showtimes, buying tickets, and viewing movie and seating information. The `Main` class also uses __The Movie Database (TMDB)__ API to fetch movie details and populate the Movie objects. + +The `Theater` class represents a movie theater. It has several attributes, including a list of `Movie` objects, a list of Showtime objects, and a two-dimensional array of `Seat` objects. The `Theater` class has several methods that allow the user to add, remove, and view movies, showtimes, and seating information. It also has methods that allow the user to buy tickets and find movies and showtimes by title, time, and date. + +The `Seat` class represents a seat in a movie theater. It has several attributes, including the seat's row and column number, and a boolean indicating whether the seat is available or not. The `Seat` class has several getter and setter methods that allow the user to access and modify these attributes. + +The `Movie` class represents a movie. It has several attributes, including the movie's title, release year, director, duration, and genre. The `Movie` class has several getter and setter methods that allow the user to access and modify these attributes. + +The `Showtime` class represents a showtime for a movie in a movie theater. It has several attributes, including the `Movie` object for the movie, the showtime's time and date, and the ticket price. The `Showtime` class has several getter and setter methods that allow the user to access and modify these attributes. + +The `Venue` class is a simple class that represents a venue such as a theater, stadium, or arena. It has name and location attributes and corresponding get and set methods. It is intended to be used as a base class that other classes such as `Theater` can extend to inherit its attributes and methods. + +## Object-Oriented Programming Principles +The project uses the four principles of object-oriented programming (OOP): + +- The principle of __Abstraction__ is used in the `Movie`, `Showtime`, and `Seat` classes, which provide a high-level interface for working with movie, showtime, and seat objects. This allows the user to interact with these objects without having to worry about the underlying details of their implementation. + +- The principle of __Encapsulation__ is used in the `Movie`, `Showtime`, and `Seat` classes, which define their attributes as private and provide public getter and setter methods for accessing and modifying these attributes. This allows the class to control how its attributes can be accessed and modified, which can help prevent data corruption and maintain the integrity of the objects. + +- The principle of __Inheritance__ is used in the `Theater` class, which extends the `Venue` class. This allows the Theater class to inherit the attributes and methods of the `Venue` class, which makes it easier to access the name and the location of the theater. + +- The principle of __Polymorphism__ is used in the `Theater` class, which contains a list of `Movie` objects and a list of `Showtime` objects. This allows the `Theater` class to treat these objects as if they were of the same type, which allows it to use the same methods (such as add and remove) to manage both types of objects. + +## Notes + +- This solution is intended to be a reference only. It is not intended to be a complete solution that will work for all possible inputs. It is possible to break the program by entering invalid inputs or by modifying the data files directly. The program is not intended to be robust enough to handle all possible inputs or to recover from all possible errors. +- The project uses the __The Movie Database (TMDB)__ API to fetch movie details and populate the `Movie` objects. The API key is stored in the `API_KEY` variable. To run the project, you must set this variable to your TMDB API key. You can get an API key by signing up for a free TMDB account. +- JSON files are used to store the data for the `Movie`, `Showtime`, and `Seat` objects. The `Movie` and `Showtime` objects are stored in the `movies.json` and `showtimes.json` files, respectively. The `Seat` objects are stored in the `seats.json` file. The `Theater` class uses the `Gson` library to read and write these files. Make sure to add the `json-xxx.jar` file to the project's classpath. +- The `TmdbExample` class is used to test the TMDB API. It is not part of the project. It is included in the project only for testing purposes. \ No newline at end of file diff --git a/src/Main.java b/src/Main.java new file mode 100644 index 0000000..3a5497c --- /dev/null +++ b/src/Main.java @@ -0,0 +1,311 @@ +package src; + +import java.io.BufferedReader; +import java.io.IOException; +import java.io.InputStreamReader; +import java.net.HttpURLConnection; +import java.net.URL; +import java.util.Scanner; +import org.json.JSONArray; +import org.json.JSONException; +import org.json.JSONObject; + +// Main class +public class Main { + // attributes + private static final String API_KEY = "YOUR_API_KEY"; + private static Theater theater; + static Scanner scanner = new Scanner(System.in); + + public static void main(String[] args) { + // create a theater with 10 rows and 10 columns + theater = new Theater("LUT Kino", "Yliopistonkatu", 10, 10); + + // create a menu for customers of the theater + + while (true) { + System.out.println("\nWelcome to the " + theater.getName() + "at" + theater.getLocation() + "!"); + System.out.println("1. Add a movie"); + System.out.println("2. Remove a movie"); + System.out.println("3. View a movie"); + System.out.println("4. View all movies"); + System.out.println("5. Add a showtime"); + System.out.println("6. Remove a showtime"); + System.out.println("7. View a showtime"); + System.out.println("8. View all showtimes"); + System.out.println("9. Buy a ticket"); + System.out.println("10. View seating"); + System.out.println("0. Exit"); + System.out.print("Enter your choice: "); + int choice = scanner.nextInt(); + scanner.nextLine(); + switch (choice) { + case 1: + addMovie(); + break; + case 2: + removeMovie(); + break; + case 3: + viewMovie(); + break; + case 4: + viewAllMovies(); + break; + case 5: + addShowtime(); + break; + case 6: + removeShowtime(); + break; + case 7: + viewShowtime(); + break; + case 8: + viewAllShowtimes(); + break; + case 9: + buyTicket(); + break; + case 10: + viewSeating(); + break; + case 0: + System.out.println("Goodbye!"); + return; + default: + System.out.println("Invalid choice!"); + } + } + } + + // add a movie + public static void addMovie() { + System.out.print("Enter the movie title: "); + String title = scanner.nextLine(); + System.out.print("Enter the release year: "); + String releaseYear = scanner.nextLine(); + System.out.print("Enter the director: "); + String director = scanner.nextLine(); + System.out.print("Enter the duration: "); + int duration = scanner.nextInt(); + scanner.nextLine(); + System.out.print("Enter the genre: "); + String genre = scanner.nextLine(); + + // use The Movie Database API to fetch movie details + try { + // construct the API URL + String temp = title.replaceAll(" ", "+"); + String url = "https://api.themoviedb.org/3/search/movie?api_key=" + API_KEY + "&query=" + + temp; + // make the HTTP request and parse the response + URL obj = new URL(url); + HttpURLConnection con = (HttpURLConnection) obj.openConnection(); + con.setRequestMethod("GET"); + con.setRequestProperty("Accept", "application/json"); + con.setRequestProperty("Content-Type", "application/json"); + con.connect(); + int responseCode = con.getResponseCode(); + if (responseCode == HttpURLConnection.HTTP_OK) { // success + BufferedReader in = new BufferedReader(new InputStreamReader(con.getInputStream())); + String inputLine; + StringBuffer response = new StringBuffer(); + while ((inputLine = in.readLine()) != null) { + response.append(inputLine); + } + in.close(); + // parse the JSON response + JSONObject jsonObject = new JSONObject(response.toString()); + JSONArray jsonArray = jsonObject.getJSONArray("results"); + if (jsonArray.length() > 0) { + JSONObject movie = jsonArray.getJSONObject(0); + // update the movie details with the API response + title = movie.getString("title"); + releaseYear = movie.getString("release_date"); + /* + * The Movie Database API does not provide these details + * director = movie.getString("director"); + * duration = movie.getInt("runtime"); + * genre = movie.getString("genre"); + */ + } + } else { + System.out.println("Failed to fetch movie details from the API!"); + return; + } + } catch (IOException | JSONException e) { + e.printStackTrace(); + } + // create a movie object and add it to the theater's catalog + Movie movie = new Movie(title, releaseYear, director, duration, genre); + theater.addMovie(movie); + System.out.println("Movie added successfully!"); + } + + public static void removeMovie() { + System.out.print("Enter the title of the movie to remove: "); + String title = scanner.nextLine(); + + // remove the movie from the theater's catalog + Movie movie = theater.getMovieByTitle(title); + if (movie == null) { + System.out.println("Movie not found!"); + return; + } + theater.removeMovie(movie); + System.out.println("Movie removed successfully!"); + } + + public static void viewMovie() { + System.out.print("Enter the title of the movie to view: "); + String title = scanner.nextLine(); + + // view the movie's details + Movie movie = theater.getMovieByTitle(title); + if (movie == null) { + System.out.println("Movie not found!"); + return; + } + theater.viewMovie(movie); + } + + public static void viewAllMovies() { + theater.viewAllMovies(); + } + + public static void addShowtime() { + System.out.print("Enter the title of the movie: "); + String title = scanner.nextLine(); + System.out.print("Enter the time of the showtime (e.g. 7:00 PM): "); + String time = scanner.nextLine(); + System.out.print("Enter the date of the showtime (e.g. 2022-12-15): "); + String date = scanner.nextLine(); + System.out.print("Enter the ticket price for the showtime: "); + double price = scanner.nextDouble(); + scanner.nextLine(); + + // find the movie in the theater's catalog + Movie movie = theater.getMovieByTitle(title); + if (movie == null) { + System.out.println("Movie not found!"); + return; + } + + // create a showtime object and add it to the theater + Showtime showtime = new Showtime(movie, time, date, price); + theater.addShowtime(showtime); + System.out.println("Showtime added successfully!"); + } + + public static void removeShowtime() { + System.out.print("Enter the title of the movie: "); + String title = scanner.nextLine(); + System.out.print("Enter the time of the showtime (e.g. 7:00 PM): "); + String time = scanner.nextLine(); + System.out.print("Enter the date of the showtime (e.g. 2022-12-15): "); + String date = scanner.nextLine(); + + // find the movie in the theater's catalog + Movie movie = theater.getMovieByTitle(title); + if (movie == null) { + System.out.println("Movie not found!"); + return; + } + + // remove the showtime from the theater + Showtime showtime = theater.getShowtimeByMovieAndTimeAndDate(movie, time, date); + if (showtime == null) { + System.out.println("Showtime not found!"); + return; + } + theater.removeShowtime(showtime); + System.out.println("Showtime removed successfully!"); + } + + public static void viewShowtime() { + System.out.print("Enter the title of the movie: "); + String title = scanner.nextLine(); + System.out.print("Enter the time of the showtime (e.g. 7:00 PM): "); + String time = scanner.nextLine(); + System.out.print("Enter the date of the showtime (e.g. 2022-12-15): "); + String date = scanner.nextLine(); + + // find the movie in the theater's catalog + Movie movie = theater.getMovieByTitle(title); + if (movie == null) { + System.out.println("Movie not found!"); + return; + } + + // view the showtime's details + Showtime showtime = theater.getShowtimeByMovieAndTimeAndDate(movie, time, date); + if (showtime == null) { + System.out.println("Showtime not found!"); + return; + } + theater.viewShowtime(showtime); + } + + public static void viewAllShowtimes() { + theater.viewAllShowtimes(); + } + + public static void buyTicket() { + System.out.print("Enter the movie title: "); + String movieTitle = scanner.nextLine(); + System.out.print("Enter the showtime (time): "); + String time = scanner.nextLine(); + System.out.print("Enter the showtime (date): "); + String date = scanner.nextLine(); + System.out.print("Enter the seat (row and column): "); + String seat = scanner.nextLine(); + + // find the movie and showtime + Movie movie = theater.getMovieByTitle(movieTitle); + if (movie == null) { + System.out.println("Movie not found!"); + return; + } + Showtime showtime = theater.getShowtimeByMovieAndTimeAndDate(movie, time, date); + if (showtime == null) { + System.out.println("Showtime not found!"); + return; + } + + // parse the seat input + String[] seatParts = seat.split(" "); + int row = Integer.parseInt(seatParts[0]); + int column = Integer.parseInt(seatParts[1]); + + // buy the ticket + Seat seatChosen = theater.seats[row][column]; + theater.buyTicket(showtime, seatChosen); + System.out.println("Ticket bought!"); + } + + public static void viewSeating() { + System.out.print("Enter the movie title: "); + String movieTitle = scanner.nextLine(); + System.out.print("Enter the showtime (time): "); + String time = scanner.nextLine(); + System.out.print("Enter the showtime (date): "); + String date = scanner.nextLine(); + + // find the movie and showtime + Movie movie = theater.getMovieByTitle(movieTitle); + if (movie == null) { + System.out.println("Movie not found!"); + return; + } + Showtime showtime = theater.getShowtimeByMovieAndTimeAndDate(movie, time, date); + if (showtime == null) { + System.out.println("Showtime not found!"); + return; + } + + // view the seating + theater.viewSeating(showtime); + } + +} diff --git a/src/Movie.java b/src/Movie.java new file mode 100644 index 0000000..35b73a3 --- /dev/null +++ b/src/Movie.java @@ -0,0 +1,61 @@ +package src; + +// Movie class +public class Movie { + // attributes + private String title; + private String releaseYear; + private String director; + private int duration; + private String genre; + + // constructor + public Movie(String title, String releaseYear, String director, int duration, String genre) { + this.title = title; + this.releaseYear = releaseYear; + this.director = director; + this.duration = duration; + this.genre = genre; + } + + // getters and setters + public String getTitle() { + return title; + } + + public void setTitle(String title) { + this.title = title; + } + + public String getReleaseYear() { + return releaseYear; + } + + public void setReleaseYear(String releaseYear) { + this.releaseYear = releaseYear; + } + + public String getDirector() { + return director; + } + + public void setDirector(String director) { + this.director = director; + } + + public int getDuration() { + return duration; + } + + public void setDuration(int duration) { + this.duration = duration; + } + + public String getGenre() { + return genre; + } + + public void setGenre(String genre) { + this.genre = genre; + } +} diff --git a/src/Seat.java b/src/Seat.java new file mode 100644 index 0000000..4a6a738 --- /dev/null +++ b/src/Seat.java @@ -0,0 +1,41 @@ +package src; + +// Seat class +public class Seat { + // attributes + private int row; + private int column; + private boolean available; + + // constructor + public Seat(int row, int column, boolean available) { + this.row = row; + this.column = column; + this.available = available; + } + + // getters and setters + public int getRow() { + return row; + } + + public void setRow(int row) { + this.row = row; + } + + public int getColumn() { + return column; + } + + public void setColumn(int column) { + this.column = column; + } + + public boolean isAvailable() { + return available; + } + + public void setAvailable(boolean available) { + this.available = available; + } +} diff --git a/src/Showtime.java b/src/Showtime.java new file mode 100644 index 0000000..1d3d77b --- /dev/null +++ b/src/Showtime.java @@ -0,0 +1,51 @@ +package src; + +// Showtime class +public class Showtime { + // attributes + private Movie movie; + private String time; + private String date; + private double price; + + // constructor + public Showtime(Movie movie, String time, String date, double price) { + this.movie = movie; + this.time = time; + this.date = date; + this.price = price; + } + + // getters and setters + public Movie getMovie() { + return movie; + } + + public void setMovie(Movie movie) { + this.movie = movie; + } + + public String getTime() { + return time; + } + + public void setTime(String time) { + this.time = time; + } + + public String getDate() { + return date; + } + + public void setDate(String date) { + this.date = date; + } + + public double getPrice() { + return price; + } + + public void setPrice(double price) { + this.price = price; + } +} \ No newline at end of file diff --git a/src/Theater.java b/src/Theater.java new file mode 100644 index 0000000..5333ebd --- /dev/null +++ b/src/Theater.java @@ -0,0 +1,103 @@ +package src; + +import java.util.ArrayList; +import java.util.List; + +// Theater class +public class Theater extends Venue { + // attributes + protected List movies; + protected List showtimes; + protected Seat[][] seats; + + // constructor + public Theater(String name, String location, int rows, int columns) { + super(name, location); + this.movies = new ArrayList<>(); + this.showtimes = new ArrayList<>(); + this.seats = new Seat[rows][columns]; + for (int i = 0; i < rows; i++) { + for (int j = 0; j < columns; j++) { + seats[i][j] = new Seat(i, j, true); + } + } + } + + // methods + public void addMovie(Movie movie) { + this.movies.add(movie); + } + + public void removeMovie(Movie movie) { + this.movies.remove(movie); + } + + public void viewMovie(Movie movie) { + System.out.println("Title: " + movie.getTitle()); + System.out.println("Release Year: " + movie.getReleaseYear()); + System.out.println("Director: " + movie.getDirector()); + System.out.println("Duration: " + movie.getDuration()); + System.out.println("Genre: " + movie.getGenre()); + } + + public void viewAllMovies() { + for (Movie movie : movies) { + viewMovie(movie); + System.out.println(); + } + } + + public void addShowtime(Showtime showtime) { + this.showtimes.add(showtime); + } + + public void removeShowtime(Showtime showtime) { + this.showtimes.remove(showtime); + } + + public void viewShowtime(Showtime showtime) { + System.out.println("Movie: " + showtime.getMovie().getTitle()); + System.out.println("Time: " + showtime.getTime()); + System.out.println("Date: " + showtime.getDate()); + System.out.println("Price: " + showtime.getPrice()); + } + + public void viewAllShowtimes() { + for (Showtime showtime : showtimes) { + viewShowtime(showtime); + System.out.println(); + } + } + + public void buyTicket(Showtime showtime, Seat seat) { + seat.setAvailable(false); + } + + public void viewSeating(Showtime showtime) { + for (int i = 0; i < seats.length; i++) { + for (int j = 0; j < seats[0].length; j++) { + System.out.print(seats[i][j].isAvailable() ? "[O] " : "[X] "); + } + System.out.println(); + } + } + + public Movie getMovieByTitle(String title) { + for (Movie movie : movies) { + if (movie.getTitle().equals(title)) { + return movie; + } + } + return null; + } + + public Showtime getShowtimeByMovieAndTimeAndDate(Movie movie, String time, String date) { + for (Showtime showtime : showtimes) { + if (showtime.getMovie().equals(movie) && showtime.getTime().equals(time) + && showtime.getDate().equals(date)) { + return showtime; + } + } + return null; + } +} diff --git a/src/TmdbExample.java b/src/TmdbExample.java new file mode 100644 index 0000000..da7c692 --- /dev/null +++ b/src/TmdbExample.java @@ -0,0 +1,53 @@ +/* For testing the API, not in use */ +package src; + +// Import the necessary Java libraries +import java.io.*; +import java.net.*; +import org.json.JSONObject; + +public class TmdbExample { + + // Replace with your own TMDb API key + private static final String API_KEY = "YOUR_API_KEY"; + + public static void main(String[] args) { + try { + // Set the URL for the TMDb API endpoint + URL tmdbApiUrl = new URL( + "https://api.themoviedb.org/3/search/movie?api_key=" + API_KEY + "&query=Fate+of+Furious"); + + // Open a connection to the TMDb API endpoint + HttpURLConnection connection = (HttpURLConnection) tmdbApiUrl.openConnection(); + + // Set the request method to GET + connection.setRequestMethod("GET"); + + // Set the request headers + connection.setRequestProperty("Accept", "application/json"); + connection.setRequestProperty("Content-Type", "application/json"); + + // Send the GET request to the TMDb API endpoint + connection.connect(); + + // Read the response from the TMDb API endpoint + InputStream inputStream = connection.getInputStream(); + InputStreamReader inputStreamReader = new InputStreamReader(inputStream); + BufferedReader reader = new BufferedReader(inputStreamReader); + StringBuilder response = new StringBuilder(); + String line; + while ((line = reader.readLine()) != null) { + response.append(line); + } + reader.close(); + // Parse the response as a JSON object + JSONObject json = new JSONObject(response.toString()); + System.out.println(json.getJSONArray("results").getJSONObject(0).getString("genre")); + + // Print the movie title + System.out.println(json.getString("title")); + } catch (IOException e) { + System.err.println("An error occurred while fetching the movie details: " + e.getMessage()); + } + } +} diff --git a/src/Venue.java b/src/Venue.java new file mode 100644 index 0000000..815416a --- /dev/null +++ b/src/Venue.java @@ -0,0 +1,28 @@ +public class Venue { + // attributes + protected String name; + protected String location; + + // constructor + public Venue(String name, String location) { + this.name = name; + this.location = location; + } + + // methods + public String getName() { + return this.name; + } + + public void setName(String name) { + this.name = name; + } + + public String getLocation() { + return this.location; + } + + public void setLocation(String location) { + this.location = location; + } +}