package no.ntnu.idatt1002.demo.controller; import java.io.IOException; import java.time.LocalDate; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import java.util.stream.Collectors; import javafx.collections.FXCollections; import javafx.collections.ObservableList; import javafx.event.ActionEvent; import javafx.fxml.FXML; import javafx.fxml.FXMLLoader; import javafx.geometry.Rectangle2D; import javafx.scene.Node; import javafx.scene.Parent; import javafx.scene.Scene; import javafx.scene.control.Alert; import javafx.scene.control.Alert.AlertType; import javafx.scene.control.Button; import javafx.scene.control.DatePicker; import javafx.scene.control.Label; import javafx.scene.control.ProgressBar; import javafx.scene.layout.AnchorPane; import javafx.scene.layout.HBox; import javafx.scene.layout.VBox; import javafx.scene.paint.Color; import javafx.stage.Screen; import javafx.stage.Stage; import no.ntnu.idatt1002.demo.data.Budget.BudgetItem; import no.ntnu.idatt1002.demo.data.Budget.FileHandlingBudget; import no.ntnu.idatt1002.demo.data.Budget.FileHandlingSelectedBudget; import no.ntnu.idatt1002.demo.data.Budget.GeneralBudget; import no.ntnu.idatt1002.demo.data.Economics.ExpenseCategory; import no.ntnu.idatt1002.demo.data.Economics.ExpenseRegister; import no.ntnu.idatt1002.demo.data.Economics.FileHandling; import no.ntnu.idatt1002.demo.data.Economics.IncomeRegister; import no.ntnu.idatt1002.demo.data.Economics.Overview; import no.ntnu.idatt1002.demo.data.recipes.Recipe; public class MainMenu { @FXML private Label balanceLbl; @FXML private ProgressBar bookBar; @FXML private Label bookLbl; @FXML private Button budgetBtn; @FXML private ProgressBar clothesBar; @FXML private Label clothesLbl; @FXML private DatePicker date; @FXML private Button expenseBtn; @FXML private ProgressBar foodBar; @FXML private Button foodBtn; @FXML private Label foodLbl; @FXML private Button incomeBtn; @FXML private ProgressBar mainBar; @FXML private ProgressBar otherBar; @FXML private Label otherLbl; @FXML private Button returnBtn; @FXML private Label title; @FXML private Label usageLbl; @FXML private AnchorPane root; @FXML private Label daysLeftLbl; @FXML private VBox miniBarScroll; GeneralBudget generalBudget; ExpenseRegister expenseRegister; IncomeRegister incomeRegister; Overview overview; @FXML public void initialize() { //Initialize all registers + overview try { incomeRegister = loadIncomeDataFromFile( "budgets/" + FileHandlingSelectedBudget.readSelectedBudget() + "/Income"); expenseRegister = loadExpenseDataFromFile( "budgets/" + FileHandlingSelectedBudget.readSelectedBudget() + "/Expense"); generalBudget = loadBudgetDataFromFile( "budgets/" + FileHandlingSelectedBudget.readSelectedBudget() + "/Budget"); } catch (IOException ioe) { Alert alert = new Alert(AlertType.ERROR); alert.setTitle("Could not load register data"); alert.setHeaderText("Could not load register data"); alert.setContentText("There was an error loading in the registers"); alert.showAndWait(); } overview = new Overview(incomeRegister, expenseRegister, generalBudget); mainBar.setStyle("-fx-accent: rgb(48,215,106);"); refreshProgressBars(); refreshLabels(); //Set progress when opening scene double maxAmount = generalBudget.getMaxAmount(); double expenseSum = expenseRegister.getTotalSum(); //Displaying month title.setText("BUDGET " + (LocalDate.now().getMonth())); double balance = maxAmount - expenseSum; //Set balance balanceLbl.setText("Balance: " + (balance)); //Displaying how much of the monthly budget has been spent. usageLbl.setText("Used " + expenseSum + " out of " + generalBudget.getMaxAmount()); if (balance < 0) { balanceLbl.setTextFill(Color.RED); } //Make calendar uneditable formatDatePicker(); daysLeftLbl.setText("Days left: 31"); //date.restrict } private void refreshLabels() { } /** * Sets the progress of the progress bars to their most updated data. */ private void refreshProgressBars() { mainBar.setProgress(expenseRegister.getTotalSum()/generalBudget.getMaxAmount()); if (mainBar.getProgress() >= 1) { mainBar.setStyle("-fx-accent: #fa5959;"); } ArrayList<BudgetItem> budgets = generalBudget.getBudgetItems().stream() .filter(budget -> budget.getBudgetAmount() > 0) .collect(Collectors.toCollection(ArrayList::new)); for(BudgetItem bi : budgets) { FXMLLoader loader = new FXMLLoader(); loader.setLocation(getClass().getResource("/view/BudgetBar.fxml")); try { HBox hBox = loader.load(); BudgetBarController budgetBarController = loader.getController(); double leftovers = overview.getBudgetItemMinusExpense(bi.getBudgetCategory()); budgetBarController.setData(bi, leftovers); miniBarScroll.getChildren().add(hBox); }catch (IOException e) { throw new RuntimeException(e); } } } /** * Method that either reads data from a file with which it fills an income register, if older changes exist, or instantiates an income register if the file is empty. * @param fileDestination The name of the file that is being read from. * @return An object of type IncomeRegister. * @throws IOException If an error occurs while reading from the file. */ public IncomeRegister loadIncomeDataFromFile(String fileDestination) throws IOException { //Instantiate incomeRegister if (FileHandling.isEmpty(fileDestination)) { incomeRegister = new IncomeRegister(); } else { //Load previous income register try { incomeRegister = FileHandling.readIncomeRegisterFromFile(fileDestination); } catch (IOException e) { e.printStackTrace(); } } return incomeRegister; } /** * Method that either reads data from a file with which it fills an expense register, if older changes exist, or instantiates an expense register if the file is empty. * @param fileDestination The name of the file that is being read from. * @return An object of type IncomeRegister. * @throws IOException If an error occurs while reading from the file. */ public ExpenseRegister loadExpenseDataFromFile(String fileDestination) throws IOException { //Instantiate expense register if (FileHandling.isEmpty(fileDestination)) { expenseRegister = new ExpenseRegister(); } else { try { expenseRegister = FileHandling.readExpenseRegisterFromFile(fileDestination); } catch (IOException e) { e.printStackTrace(); } } return expenseRegister; } /** * Method that either reads data from a file with which it fills a budget register, if this is an old budget, or instantiates a budget register if this is a new budget. * @param fileDestination The name of the file that is being read from. * @return An object of type GeneralBudget. * @throws IOException If an error occurs while reading from the file. */ public GeneralBudget loadBudgetDataFromFile(String fileDestination) throws IOException { //Instantiate new budget if (FileHandlingBudget.isEmpty(fileDestination)) { System.out.println("hey"); generalBudget = new GeneralBudget(1000); } else { //Load previous budget try { generalBudget = FileHandlingBudget.readGeneralBudgetFromFile(fileDestination); } catch (IOException e) { e.printStackTrace(); } } return generalBudget; } /** * Method for disabling the date picker, yet having its opacity at max. */ private void formatDatePicker() { date.setValue(LocalDate.now()); date.setDisable(true); date.setStyle("-fx-opacity: 1"); date.getEditor().setStyle("-fx-opacity: 1"); } @FXML private void switchScene(ActionEvent event) throws IOException { FXMLLoader loader = new FXMLLoader(); if (event.getSource() == foodBtn) { loader.setLocation(getClass().getResource("/view/SuggestRecipes.fxml")); } else if (event.getSource() == expenseBtn) { loader.setLocation(getClass().getResource("/view/IncomeAndExpenses.fxml")); } else if (event.getSource() == incomeBtn) { loader.setLocation(getClass().getResource("/view/IncomeAndExpenses.fxml")); } else if (event.getSource() == budgetBtn) { loader.setLocation(getClass().getResource("/view/BudgetNewest.fxml")); } else if (event.getSource() == returnBtn) { loader.setLocation(getClass().getResource("/view/FirstMenu.fxml")); } Parent root = loader.load(); Stage stage = (Stage) ((Node) event.getSource()).getScene().getWindow(); Scene scene = new Scene(root); stage.setScene(scene); //Centralize the new screen Rectangle2D primScreenBounds = Screen.getPrimary().getVisualBounds(); stage.setX((primScreenBounds.getWidth() - stage.getWidth()) / 2); stage.setY((primScreenBounds.getHeight() - stage.getHeight()) / 2); stage.setResizable(false); stage.show(); } }