Java tutorial
/** * This file is part of Pau's Asset Manager Project. * * Pau's Asset Manager Project is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * Pau's Asset Manager Project is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Pau's Asset Manager Project. If not, see <http://www.gnu.org/licenses/>. */ package org.pau.assetmanager.viewmodel.chart; import java.text.SimpleDateFormat; import java.util.Calendar; import java.util.Collection; import java.util.Collections; import java.util.Date; import java.util.GregorianCalendar; import java.util.HashMap; import java.util.HashSet; import java.util.LinkedList; import java.util.List; import java.util.Map; import java.util.Set; import org.jfree.data.category.CategoryDataset; import org.jfree.data.category.DefaultCategoryDataset; import org.jfree.data.general.DefaultPieDataset; import org.jfree.data.general.PieDataset; import org.pau.assetmanager.entities.Annotation; import org.pau.assetmanager.entities.Book; import org.pau.assetmanager.entities.ExpensesAnnotation; import org.pau.assetmanager.entities.GeneralExpensesAnnotation; import org.pau.assetmanager.entities.GeneralIncomeAnnotation; import org.pau.assetmanager.entities.IncomeAnnotation; import org.pau.assetmanager.entities.MovementExpensesAnnotation; import org.pau.assetmanager.entities.MovementIncomeAnnotation; import org.pau.assetmanager.entities.PropertyBook; import org.pau.assetmanager.entities.PropertyExpensesAnnotation; import org.pau.assetmanager.entities.PropertyIncomeAnnotation; import org.pau.assetmanager.entities.StockExpensesAnnotation; import org.pau.assetmanager.entities.StockIncomeAnnotation; import org.pau.assetmanager.entities.StocksBook; import org.pau.assetmanager.viewmodel.stocks.HistoricalStockBalanceState; import org.pau.assetmanager.viewmodel.stocks.StockConceptPerformance; import org.pau.assetmanager.viewmodel.stocks.StockState; import org.pau.assetmanager.viewmodel.type.BookSelectionType; import org.pau.assetmanager.viewmodel.utils.BookSelection; import org.pau.assetmanager.viewmodel.utils.ProperitesChartDataModel; import com.google.common.base.Function; import com.google.common.base.Optional; import com.google.common.base.Predicate; import com.google.common.collect.Collections2; import com.google.common.collect.Lists; import com.google.common.collect.Maps; import com.google.common.collect.Multimap; import com.google.common.collect.Multimaps; import com.google.common.collect.Table; /** * This class is a factory of data models that are used by the charts * * @author Pau Carr Cardona * */ public class ChartDataModel { public static final String INCOME_STOCKS = "Ingresos en bolsa"; public static final String EXPENSES_STOCKS = "Gastos en bolsa"; public static final String INCOME_OWN = "Ingresos generales"; public static final String EXPENSES_OWN = "Gastos generales"; public static final String INCOME_PROPERTIES = "Ingresos de propiedades"; public static final String EXPENSES_PROPERITES = "Gastos de propiedades"; public static final String INCOME_MOVEMENT = "Ingresos de movimientos"; public static final String EXPENSES_MOVEMENT = "Gastos de movimientos"; public static final String INCOME = "Ingresos"; public static final String EXPENSES = "Gastos"; public static final String TOTAL = "Total Mensual"; public static final String TOTAL_CUMULATIVE = "Total Acumulado"; public static final String TOTAL_CUMULATIVE_STOCKS_PURCHASED = "Capital latente de acciones compradas"; public static final String TOTAL_CUMULATIVE_STOCKS_COMBINED = "Beneficios o pedidas en acciones compradas"; public static final String HACIENDA = "Hacienda"; /** * @param expensesDataForBook * expenses concept to amount map * @return the pie chart data model */ public static PieDataset expensesPieChartDataset(Map<String, Double> expensesDataForBook) { DefaultPieDataset dataset = new DefaultPieDataset(); Double total = 0.0; for (String concept : expensesDataForBook.keySet()) { total += expensesDataForBook.get(concept); } Double otros = 0.0; for (String concept : expensesDataForBook.keySet()) { Double value = expensesDataForBook.get(concept); if (value / total > 0.01) { dataset.setValue(concept, expensesDataForBook.get(concept)); } else { otros += expensesDataForBook.get(concept); } } if (otros > 0.0) { dataset.setValue("Gastos que representan menos de un 1%", otros); } return dataset; } /** * Returns the graph model of a grouping bar for each month along a year. * Each monthly group contains a bar that represent the totals for each of * the selected properties (Incomes - Expenses) The selected property will * be the one from the properties book or all the properties for a client in * case the selection is for all the books * * @return the grouping bar model */ public static DefaultCategoryDataset getTotalsOverTimePerBook(List<Annotation> annotations, int year, Book selectedBook, List<PropertyBook> listOfProperties) { ProperitesChartDataModel properitesChartDataModel = getTotalsPerBookChartDataModel(annotations, year, listOfProperties); List<String> listOfLabels = getListOfMonthTimeLabelsForYear(year); DefaultCategoryDataset model = new DefaultCategoryDataset(); for (String bookName : properitesChartDataModel.getChartData().keySet()) { Map<String, Double> valuesMapHacienda = properitesChartDataModel.getChartData().get(bookName); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapHacienda.get(currentLabel); model.addValue(currentValue, bookName, currentLabel); } } return model; } private static Double getYearBeforeFinalVirtualStockBalance(Integer year, Table<Integer, Integer, Set<StockState>> historicalStockBalanceStateTable) { Double balance = 0.0; final Integer yearBefore = year - 1; Map<Integer, Map<Integer, Set<StockState>>> historicalStockBalanceStateRowMap = historicalStockBalanceStateTable .rowMap(); historicalStockBalanceStateRowMap = Maps.filterKeys(historicalStockBalanceStateRowMap, new Predicate<Integer>() { @Override public boolean apply(Integer year) { return year <= yearBefore; } }); List<Integer> years = Lists.newArrayList(historicalStockBalanceStateRowMap.keySet()); if (years.size() > 0) { Collections.sort(years); // get last year Integer lastYear = years.get(years.size() - 1); Map<Integer, Set<StockState>> historicalStockBalanceStateLastYear = historicalStockBalanceStateRowMap .get(lastYear); List<Integer> months = Lists.newArrayList(historicalStockBalanceStateLastYear.keySet()); Collections.sort(months); Integer lastMonth = months.get(months.size() - 1); Set<StockState> historicalStockLastMonth = historicalStockBalanceStateLastYear.get(lastMonth); for (StockState currentStockState : historicalStockLastMonth) { balance += currentStockState.getVirtualBalance(); } } return balance; } /** * Returns the total balance along one year in a monthly basis. * * @param year * the balance * @param yearToAnnotationMultimap * year --> annotations multimap * @param selectedBook * book selected for the balance * @param bookSelectionType * type of book * @return */ public static DefaultCategoryDataset getBalance(Integer year, Multimap<Integer, Annotation> yearToAnnotationMultimap, BookSelection bookSelection, Boolean includePurchasedStocks, Optional<String> optionalStockLabel) { Book selectedBook = bookSelection.getSelectedBook(); Double previousYearsTotals = 0.0; for (Integer currentYear : yearToAnnotationMultimap.keySet()) { if (currentYear < year) { for (Annotation currentAnnotation : yearToAnnotationMultimap.get(currentYear)) { previousYearsTotals += currentAnnotation.getSignedAmount(); } } } Set<StocksBook> stockBooks = new HashSet<StocksBook>(); Map<String, Double> totalData = new HashMap<String, Double>(); for (int month = 0; month < 12; month++) { Calendar currentcalendar = GregorianCalendar.getInstance(); currentcalendar.set(Calendar.MONTH, month); currentcalendar.set(Calendar.YEAR, year); currentcalendar.set(Calendar.DAY_OF_MONTH, 1); String mainLabel = getTimeLabel(currentcalendar.getTime()); totalData.put(mainLabel, 0.0); Collection<Annotation> annotations = yearToAnnotationMultimap.get(year); if (annotations != null) { for (Annotation annotation : annotations) { String currentAnnotationLabel = getTimeLabel(annotation.getDate()); if (currentAnnotationLabel.equals(mainLabel)) { if (annotation.getBook() instanceof StocksBook) { stockBooks.add((StocksBook) annotation.getBook()); } totalData.put(mainLabel, totalData.get(mainLabel) + annotation.getSignedAmount()); } } } } DefaultCategoryDataset model = new DefaultCategoryDataset(); List<String> listOfLabels = getListOfMonthTimeLabelsForYear(year); Map<String, Double> labelToToalCumulativeMap = new HashMap<String, Double>(); Double total = 0.0; for (String currentLabel : listOfLabels) { Double currentValue = totalData.get(currentLabel); if (currentValue != null) { total += currentValue; } labelToToalCumulativeMap.put(currentLabel, total + previousYearsTotals); } for (String currentLabel : listOfLabels) { model.addValue(labelToToalCumulativeMap.get(currentLabel), TOTAL_CUMULATIVE, currentLabel); } // add stock information in case it is necessary if ((selectedBook instanceof StocksBook) && includePurchasedStocks) { Table<Integer, Integer, Set<StockState>> historicalStockBalanceStateTable = HistoricalStockBalanceState .getConiniousHistoricalStockBalanceStateTable(bookSelection, year, optionalStockLabel); Collection<Annotation> annotationsForYear = yearToAnnotationMultimap.get(year); if (annotationsForYear == null) { annotationsForYear = Lists.newLinkedList(); } Collection<Annotation> movementAnnotationsForYear = Collections2.filter(annotationsForYear, new Predicate<Annotation>() { @Override public boolean apply(Annotation input) { return input instanceof MovementExpensesAnnotation || input instanceof MovementIncomeAnnotation; } }); movementAnnotationsForYear = Collections2.filter(movementAnnotationsForYear, new Predicate<Annotation>() { @Override public boolean apply(Annotation input) { return input instanceof MovementExpensesAnnotation || input instanceof MovementIncomeAnnotation; } }); final Calendar currentcalendar = GregorianCalendar.getInstance(); Multimap<Integer, Annotation> monthToAnnotationMultimap = Multimaps.index(movementAnnotationsForYear, new Function<Annotation, Integer>() { @Override public Integer apply(Annotation input) { currentcalendar.setTime(input.getDate()); return currentcalendar.get(Calendar.MONTH); } }); Double movementBalance = getAllPreviousMovementCumulative(yearToAnnotationMultimap, year); if (historicalStockBalanceStateTable != null) { Map<Integer, Set<StockState>> historyForYear = historicalStockBalanceStateTable.rowMap().get(year); for (Integer currentMonth = 0; currentMonth <= 11; currentMonth++) { Double balance = 0.0; if (historyForYear != null && historyForYear.get(currentMonth) != null) { for (StockState currentStockState : historyForYear.get(currentMonth)) { balance += currentStockState.getVirtualBalanceForForcedYearAndMonth(year, currentMonth); } } else { balance = getYearBeforeFinalVirtualStockBalance(year, historicalStockBalanceStateTable); } if (monthToAnnotationMultimap.get(currentMonth) != null) { for (Annotation movementAnnotation : monthToAnnotationMultimap.get(currentMonth)) { movementBalance += movementAnnotation.getSignedAmount(); } } model.addValue(balance, TOTAL_CUMULATIVE_STOCKS_PURCHASED, listOfLabels.get(currentMonth)); Double cumulativeBalance = labelToToalCumulativeMap.get(listOfLabels.get(currentMonth)); model.addValue(balance + cumulativeBalance - movementBalance, TOTAL_CUMULATIVE_STOCKS_COMBINED, listOfLabels.get(currentMonth)); } } } return model; } private static Double getAllPreviousMovementCumulative(Multimap<Integer, Annotation> yearToAnnotationMultimap, Integer year) { List<Integer> listOfYears = Lists.newLinkedList(yearToAnnotationMultimap.keys()); if (listOfYears.size() == 0) { return 0.0; } Collections.sort(listOfYears); double allPreviousMovementCumulative = 0.0; for (int currentYearIndex = 0; currentYearIndex < listOfYears.size() && listOfYears.get(currentYearIndex) < year; currentYearIndex++) { for (Annotation annotation : yearToAnnotationMultimap.get(listOfYears.get(currentYearIndex))) { allPreviousMovementCumulative += annotation.getSignedAmount(); } } return allPreviousMovementCumulative; } /** * Generates chart model of a time series in which there are four series -- * Income: the sum of amount of income annotations for a given month in a * year -- Expenses: the sum of amount of expenses annotations for a given * month in a year -- Monthly Total: the *difference* between Income and * Expenses (Monthly Total := Income - Expenses) -- Cumulative: the * cumulative sum over time of 'Monthly Total' * * @return the chart model */ public static DefaultCategoryDataset getIncomeExpensesSimpleOverTime(List<Annotation> annotations, int year, Book selectedBook) { ProperitesChartDataModel properitesChartDataModel = getIncomeExpensesOverTimeChartDataModel(annotations, year); List<String> listOfLabels = getListOfMonthTimeLabelsForYear(year); DefaultCategoryDataset model = new DefaultCategoryDataset(); Map<String, Double> valuesMapIncome = properitesChartDataModel.getChartData().get(INCOME_PROPERTIES); Map<String, Double> valuesMapIncomeOwn = properitesChartDataModel.getChartData().get(INCOME_OWN); Map<String, Double> valuesMapIncomeStocks = properitesChartDataModel.getChartData().get(INCOME_STOCKS); Map<String, Double> valuesMapIncomeMovement = properitesChartDataModel.getChartData().get(INCOME_MOVEMENT); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapIncome.get(currentLabel); Double currentValueOwn = valuesMapIncomeOwn.get(currentLabel); Double currentValueStocks = valuesMapIncomeStocks.get(currentLabel); Double currentValueMovement = valuesMapIncomeMovement.get(currentLabel); model.addValue(currentValueMovement + currentValue + currentValueOwn + currentValueStocks, INCOME, currentLabel); } Map<String, Double> valuesMapExpenses = properitesChartDataModel.getChartData().get(EXPENSES_PROPERITES); Map<String, Double> valuesMapExpensesOwn = properitesChartDataModel.getChartData().get(EXPENSES_OWN); Map<String, Double> valuesMapExpensesStocks = properitesChartDataModel.getChartData().get(EXPENSES_STOCKS); Map<String, Double> valuesMapExpensesMovement = properitesChartDataModel.getChartData() .get(EXPENSES_MOVEMENT); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapExpenses.get(currentLabel); Double currentValueOwn = valuesMapExpensesOwn.get(currentLabel); Double currentValueStocks = valuesMapExpensesStocks.get(currentLabel); Double currentValueMovement = valuesMapExpensesMovement.get(currentLabel); model.addValue(currentValueMovement + currentValue + currentValueOwn + currentValueStocks, EXPENSES, currentLabel); } Map<String, Double> valuesMap = properitesChartDataModel.getChartData().get(TOTAL); for (String currentLabel : listOfLabels) { Double currentValue = valuesMap.get(currentLabel); model.addValue(currentValue, TOTAL, currentLabel); } Double total = 0.0; for (String currentLabel : listOfLabels) { Double currentValue = valuesMap.get(currentLabel); if (currentValue != null) { total += currentValue; } model.addValue(total, TOTAL_CUMULATIVE, currentLabel); } return model; } /** * Generates the image of a grouping bar for each month along a year. Each * monthly group contains two bars (Income and Expenses) for each of the * three types of books type (General, Stocks and Properties) * * @return the chart model */ public static DefaultCategoryDataset getIncomeExpensesOverTime(List<Annotation> annotations, int year, Book selectedBook, BookSelectionType bookSelectionType) { ProperitesChartDataModel properitesChartDataModel = getIncomeExpensesOverTimeChartDataModel(annotations, year); List<String> listOfLabels = getListOfMonthTimeLabelsForYear(year); DefaultCategoryDataset model = new DefaultCategoryDataset(); if (bookSelectionType.getIsAllBooks() || (selectedBook instanceof PropertyBook)) { Map<String, Double> valuesMapIncome = properitesChartDataModel.getChartData().get(INCOME_PROPERTIES); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapIncome.get(currentLabel); model.addValue(currentValue, INCOME_PROPERTIES, currentLabel); } } if (bookSelectionType.getIsAllBooks() || !(selectedBook instanceof PropertyBook)) { Map<String, Double> valuesMapIncomeOwn = properitesChartDataModel.getChartData().get(INCOME_OWN); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapIncomeOwn.get(currentLabel); model.addValue(currentValue, INCOME_OWN, currentLabel); } } if (bookSelectionType.getIsAllBooks() || !(selectedBook instanceof PropertyBook)) { Map<String, Double> valuesMapIncomeStocks = properitesChartDataModel.getChartData().get(INCOME_STOCKS); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapIncomeStocks.get(currentLabel); model.addValue(currentValue, INCOME_STOCKS, currentLabel); } } if (bookSelectionType.getIsAllBooks() || (selectedBook instanceof PropertyBook)) { Map<String, Double> valuesMapExpenses = properitesChartDataModel.getChartData() .get(EXPENSES_PROPERITES); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapExpenses.get(currentLabel); model.addValue(currentValue, EXPENSES_PROPERITES, currentLabel); } } if (bookSelectionType.getIsAllBooks() || !(selectedBook instanceof PropertyBook)) { Map<String, Double> valuesMapExpensesOwn = properitesChartDataModel.getChartData().get(EXPENSES_OWN); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapExpensesOwn.get(currentLabel); model.addValue(currentValue, EXPENSES_OWN, currentLabel); } } if (bookSelectionType.getIsAllBooks() || !(selectedBook instanceof PropertyBook)) { Map<String, Double> valuesMapExpensesStocks = properitesChartDataModel.getChartData() .get(EXPENSES_STOCKS); for (String currentLabel : listOfLabels) { Double currentValue = valuesMapExpensesStocks.get(currentLabel); model.addValue(currentValue, EXPENSES_STOCKS, currentLabel); } } if (!bookSelectionType.getIsAllBooks()) { Map<String, Double> valuesMap = properitesChartDataModel.getChartData().get(TOTAL); for (String currentLabel : listOfLabels) { Double currentValue = valuesMap.get(currentLabel); model.addValue(currentValue, TOTAL, currentLabel); } Double total = 0.0; for (String currentLabel : listOfLabels) { Double currentValue = valuesMap.get(currentLabel); if (currentValue != null) { total += currentValue; } model.addValue(total, TOTAL_CUMULATIVE, currentLabel); } } return model; } /** * @param year * of the list * @return the list of labels that represent a month in a year */ private static List<String> getListOfMonthTimeLabelsForYear(int year) { List<String> listOfLabels = new LinkedList<String>(); for (int month = 0; month < 12; month++) { Calendar currentcalendar = GregorianCalendar.getInstance(); currentcalendar.set(Calendar.MONTH, month); currentcalendar.set(Calendar.YEAR, year); currentcalendar.set(Calendar.DAY_OF_MONTH, 1); String mainLabel = getTimeLabel(currentcalendar.getTime()); listOfLabels.add(mainLabel); } return listOfLabels; } /** * @param annotations * annotations to use * @param year * the year for the annotations * @return The data model of a grouping bar for each month along a year. * Each monthly group contains two bars (Income and Expenses) for * each of the three types of books type (General, Stocks and * Properties) */ private static ProperitesChartDataModel getIncomeExpensesOverTimeChartDataModel(List<Annotation> annotations, int year) { Map<String, Double> incomeData = new HashMap<String, Double>(); Map<String, Double> expensesData = new HashMap<String, Double>(); Map<String, Double> incomeDataStocks = new HashMap<String, Double>(); Map<String, Double> expensesDataStocks = new HashMap<String, Double>(); Map<String, Double> incomeDataOwn = new HashMap<String, Double>(); Map<String, Double> expensesDataOwn = new HashMap<String, Double>(); Map<String, Double> incomeDataMovement = new HashMap<String, Double>(); Map<String, Double> expensesDataMovement = new HashMap<String, Double>(); Map<String, Double> totalData = new HashMap<String, Double>(); for (int month = 0; month < 12; month++) { Calendar currentcalendar = GregorianCalendar.getInstance(); currentcalendar.set(Calendar.MONTH, month); currentcalendar.set(Calendar.YEAR, year); currentcalendar.set(Calendar.DAY_OF_MONTH, 1); String mainLabel = getTimeLabel(currentcalendar.getTime()); incomeDataOwn.put(mainLabel, 0.0); expensesDataOwn.put(mainLabel, 0.0); incomeDataMovement.put(mainLabel, 0.0); expensesDataMovement.put(mainLabel, 0.0); incomeData.put(mainLabel, 0.0); expensesData.put(mainLabel, 0.0); incomeDataStocks.put(mainLabel, 0.0); expensesDataStocks.put(mainLabel, 0.0); totalData.put(mainLabel, 0.0); for (Annotation annotation : annotations) { String currentAnnotationLabel = getTimeLabel(annotation.getDate()); if (currentAnnotationLabel.equals(mainLabel)) { if (annotation instanceof ExpensesAnnotation) { if (annotation instanceof PropertyExpensesAnnotation) { expensesData.put(mainLabel, expensesData.get(mainLabel) + annotation.getSignedAmount()); } else if (annotation instanceof StockExpensesAnnotation) { expensesDataStocks.put(mainLabel, expensesDataStocks.get(mainLabel) + annotation.getSignedAmount()); } else if (annotation instanceof GeneralExpensesAnnotation) { expensesDataOwn.put(mainLabel, expensesDataOwn.get(mainLabel) + annotation.getSignedAmount()); } else if (annotation instanceof MovementExpensesAnnotation) { expensesDataMovement.put(mainLabel, expensesDataMovement.get(mainLabel) + annotation.getSignedAmount()); } totalData.put(mainLabel, totalData.get(mainLabel) + annotation.getSignedAmount()); } else if (annotation instanceof IncomeAnnotation) { if (annotation instanceof PropertyIncomeAnnotation) { incomeData.put(mainLabel, incomeData.get(mainLabel) + annotation.getSignedAmount()); } else if (annotation instanceof StockIncomeAnnotation) { incomeDataStocks.put(mainLabel, incomeDataStocks.get(mainLabel) + annotation.getSignedAmount()); } else if (annotation instanceof GeneralIncomeAnnotation) { incomeDataOwn.put(mainLabel, incomeDataOwn.get(mainLabel) + annotation.getSignedAmount()); } else if (annotation instanceof MovementIncomeAnnotation) { incomeDataMovement.put(mainLabel, incomeDataMovement.get(mainLabel) + annotation.getSignedAmount()); } totalData.put(mainLabel, totalData.get(mainLabel) + annotation.getSignedAmount()); } } } } ProperitesChartDataModel properitesChartDataModel = new ProperitesChartDataModel(); Map<String, Map<String, Double>> chartData = properitesChartDataModel.getChartData(); chartData.put(INCOME_STOCKS, incomeDataStocks); chartData.put(EXPENSES_STOCKS, expensesDataStocks); chartData.put(INCOME_OWN, incomeDataOwn); chartData.put(EXPENSES_OWN, expensesDataOwn); chartData.put(INCOME_MOVEMENT, incomeDataMovement); chartData.put(EXPENSES_MOVEMENT, expensesDataMovement); chartData.put(INCOME_PROPERTIES, incomeData); chartData.put(EXPENSES_PROPERITES, expensesData); chartData.put(TOTAL, totalData); return properitesChartDataModel; } /** * Returns the graph model of a grouping bar for each month along a year. * Each monthly group contains a bar that represent the totals for each of * the selected properties (Incomes - Expenses) The selected property will * be the one from the properties book or all the properties for a client in * case the selection is for all the books * * @return the grouping bar model */ private static ProperitesChartDataModel getTotalsPerBookChartDataModel(List<Annotation> annotations, int year, List<PropertyBook> listOfProperties) { ProperitesChartDataModel properitesChartDataModel = new ProperitesChartDataModel(); Map<String, Map<String, Double>> chartData = properitesChartDataModel.getChartData(); for (Book book : listOfProperties) { Map<String, Double> currentBookData = new HashMap<String, Double>(); chartData.put(book.getName(), currentBookData); for (int month = 0; month < 12; month++) { Calendar currentcalendar = GregorianCalendar.getInstance(); currentcalendar.set(Calendar.MONTH, month); currentcalendar.set(Calendar.YEAR, year); currentcalendar.set(Calendar.DAY_OF_MONTH, 1); String mainLabel = getTimeLabel(currentcalendar.getTime()); currentBookData.put(mainLabel, 0.0); for (Annotation annotation : annotations) { if (annotation.getBook().getName().equals(book.getName())) { String currentAnnotationLabel = getTimeLabel(annotation.getDate()); if (currentAnnotationLabel.equals(mainLabel)) { currentBookData.put(mainLabel, currentBookData.get(mainLabel) + annotation.getSignedAmount()); } } } } } return properitesChartDataModel; } /** * @param date * @return the month time label */ private static String getTimeLabel(Date date) { SimpleDateFormat simpleDateFormat = new SimpleDateFormat("MMM-yyyy"); return simpleDateFormat.format(date); } /** * Generates the chart model of a pie chart that displays the percentage of * expenses of the different books which for a given year are loosing money * (not profitable) * * @return the database model */ public static PieDataset deficitsPieChartDataset(List<Annotation> anotations) { Map<String, Double> incomeForBook = new HashMap<String, Double>(); for (Annotation annotation : anotations) { String name = annotation.getBook().getName(); if (!incomeForBook.containsKey(name)) { incomeForBook.put(name, 0.0); } incomeForBook.put(name, incomeForBook.get(name) - annotation.getSignedAmount()); } List<String> keysToRemove = new LinkedList<String>(); for (String name : incomeForBook.keySet()) { Double value = incomeForBook.get(name); if (value < 0.0) { keysToRemove.add(name); } } for (String addres : keysToRemove) { incomeForBook.remove(addres); } DefaultPieDataset dataset = new DefaultPieDataset(); for (String name : incomeForBook.keySet()) { dataset.setValue(name, incomeForBook.get(name)); } return dataset; } /** * Generates the a chart model of a pie chart that displays the percentage * of income of the different books which for a given year are profitable * * @return the char model */ public static PieDataset incomesPieChartDataset(List<Annotation> anotations) { Map<String, Double> incomeForBook = new HashMap<String, Double>(); for (Annotation annotation : anotations) { String name = annotation.getBook().getName(); if (!incomeForBook.containsKey(name)) { incomeForBook.put(name, 0.0); } incomeForBook.put(name, incomeForBook.get(name) + annotation.getSignedAmount()); } List<String> keysToRemove = new LinkedList<String>(); for (String name : incomeForBook.keySet()) { Double value = incomeForBook.get(name); if (value < 0.0) { keysToRemove.add(name); } } for (String addres : keysToRemove) { incomeForBook.remove(addres); } DefaultPieDataset dataset = new DefaultPieDataset(); for (String name : incomeForBook.keySet()) { dataset.setValue(name, incomeForBook.get(name)); } return dataset; } /** * Generates a chart model of a chart with the performance of the sold * stocks. It computes the amount of money earned or lost given the price * per stock of the sold stocks. * * Note: The chart has into account that the stocks could have been bought * at different points in time and that the sold stocks can span different * different 'stock purchases' with different price per stock * * @return the chart model */ public static CategoryDataset getStockConceptsPerformance( Map<String, StockConceptPerformance> stocksConceptToProfitLimitedToNumberOfSoldSlocks) { DefaultCategoryDataset model = new DefaultCategoryDataset(); for (String concept : stocksConceptToProfitLimitedToNumberOfSoldSlocks.keySet()) { StockConceptPerformance stockConceptPerformance = stocksConceptToProfitLimitedToNumberOfSoldSlocks .get(concept); model.addValue(stockConceptPerformance.getProfit(), concept, stockConceptPerformance); } return model; } }