Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
108 changes: 108 additions & 0 deletions src/main/java/de/doubleslash/keeptime/controller/report/Report.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
package de.doubleslash.keeptime.controller.report;

import de.doubleslash.keeptime.common.DateFormatter;
import de.doubleslash.keeptime.controller.Controller;
import de.doubleslash.keeptime.model.Model;
import de.doubleslash.keeptime.model.Project;
import de.doubleslash.keeptime.model.Work;

import java.time.LocalDate;
import java.util.*;
import java.util.stream.Collectors;

public class Report {
private final LocalDate date;
private final Model model;
private final Controller controller;
private List<Work> workItems;
private long workItemsSeconds;
private SortedSet<Project> workedProjectsSet;
private long presentTime;
private long workTime;
private Map<Long, Long> projectWorkSecondsMap;

public Report(LocalDate date, Model model, Controller controller) {
this.date = date;
this.model = model;
this.controller = controller;

fetchWorkItems();

fetchProjects();

calculateSeconds();

}

public LocalDate getDate() {
return date;
}

public String getDateString() {
return DateFormatter.toDayDateString(this.date);
}

public List<Work> getWorkItems() {
return workItems;
}

public long getWorkItemsSeconds() {
return workItemsSeconds;
}

public SortedSet<Project> getWorkedProjectsSet() {
return workedProjectsSet;
}

public String getPresentTimeString() {
return DateFormatter.secondsToHHMMSS(this.presentTime);
}

public String getWorkTimeString() {
return DateFormatter.secondsToHHMMSS(this.workTime);
}

public Map<Long, Long> getProjectWorkSecondsMap() {
return this.projectWorkSecondsMap;
}

private void fetchWorkItems() {
this.workItems = model.getWorkRepository().findByStartDateOrderByStartTimeAsc(date);

if (date.equals(LocalDate.now())) {
Work activeWorkItem = model.activeWorkItem.get();
if (activeWorkItem != null && !this.workItems.contains(activeWorkItem)) {
this.workItems.add(activeWorkItem);
}
}
}

private void fetchProjects() {
this.workedProjectsSet = workItems.stream()
.map(Work::getProject)
.collect(Collectors.toCollection(
() -> new TreeSet<>(Comparator.comparing(Project::getIndex))));
}

private void calculateSeconds() {
this.workItemsSeconds = this.controller.calcSeconds(this.workItems);

this.projectWorkSecondsMap = new HashMap<>();

for (final Project project : workedProjectsSet) {
final List<Work> onlyCurrentProjectWork = workItems.stream()
.filter(w -> w.getProject() == project)
.collect(Collectors.toList());

final long projectWorkSeconds = this.controller.calcSeconds(onlyCurrentProjectWork);

projectWorkSecondsMap.put(project.getId(), projectWorkSeconds);

presentTime += projectWorkSeconds;
if (project.isWork()) {
workTime += projectWorkSeconds;
}
}
}

}
113 changes: 43 additions & 70 deletions src/main/java/de/doubleslash/keeptime/view/ReportController.java
Original file line number Diff line number Diff line change
Expand Up @@ -16,20 +16,11 @@

package de.doubleslash.keeptime.view;

import java.io.IOException;
import java.time.LocalDate;
import java.util.*;
import java.util.stream.Collectors;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

import de.doubleslash.keeptime.common.DateFormatter;
import de.doubleslash.keeptime.common.Resources;
import de.doubleslash.keeptime.common.Resources.RESOURCE;
import de.doubleslash.keeptime.common.SvgNodeProvider;
import de.doubleslash.keeptime.controller.Controller;
import de.doubleslash.keeptime.controller.report.Report;
import de.doubleslash.keeptime.exceptions.FXMLLoaderException;
import de.doubleslash.keeptime.model.Model;
import de.doubleslash.keeptime.model.Project;
Expand Down Expand Up @@ -57,6 +48,14 @@
import javafx.scene.shape.Circle;
import javafx.stage.Stage;
import javafx.util.Callback;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

import java.io.IOException;
import java.time.LocalDate;
import java.util.List;
import java.util.Optional;

@Component
public class ReportController {
Expand All @@ -70,43 +69,29 @@ public class ReportController {
private static final String FX_BACKGROUND_COLOR_WORKED = "-fx-background-color: #00a5e1;";

private static final String EDIT_WORK_DIALOG_TITLE = "Edit work";

private static final Logger LOG = LoggerFactory.getLogger(ReportController.class);
private final Model model;
private final Controller controller;
private final TreeItem<TableRow> rootItem = new TreeItem<>();
@FXML
private BorderPane topBorderPane;

@FXML
private Label currentDayLabel;
@FXML
private Label currentDayWorkTimeLabel;
@FXML
private Label currentDayTimeLabel;

@FXML
private TreeTableView<TableRow> workTableTreeView;

@FXML
private AnchorPane reportRoot;

@FXML
private Canvas colorTimeLineCanvas;

@FXML
private Button expandCollapseButton;

private static final Logger LOG = LoggerFactory.getLogger(ReportController.class);

private final Model model;

private final Controller controller;

private Stage stage;

private ColorTimeLine colorTimeLine;

private LocalDate currentReportDate;

private final TreeItem<TableRow> rootItem = new TreeItem<>();

private boolean expanded = true;

public ReportController(final Model model, final Controller controller) {
Expand All @@ -121,7 +106,7 @@ private void initialize() {

colorTimeLine = new ColorTimeLine(colorTimeLineCanvas);

expandCollapseButton.setOnMouseClicked(event ->toggleCollapseExpandReport());
expandCollapseButton.setOnMouseClicked(event -> toggleCollapseExpandReport());
initTableView();
}

Expand Down Expand Up @@ -211,74 +196,62 @@ protected void updateItem(TableRow workItem, boolean empty) {
rootItem.setExpanded(true);
}

private void toggleCollapseExpandReport(){
private void toggleCollapseExpandReport() {

if(expanded){
if (expanded) {
expandAll(false);
expandCollapseButton.setText("Expand");

}else {
} else {
expandAll(true);
expandCollapseButton.setText("Collapse");
}
expanded = !expanded;
}

private void expandAll(boolean expand){
for (int i=0; i<rootItem.getChildren().size(); i++){
private void expandAll(boolean expand) {
for (int i = 0; i < rootItem.getChildren().size(); i++) {
rootItem.getChildren().get(i).setExpanded(expand);
}
}

private void updateReport(final LocalDate dateToShow) {
Report report = new Report(dateToShow, model, controller);

this.currentReportDate = dateToShow;
rootItem.getChildren().clear();
reportRoot.requestFocus();

this.currentDayLabel.setText(DateFormatter.toDayDateString(this.currentReportDate));
final List<Work> currentWorkItems = model.getWorkRepository()
.findByStartDateOrderByStartTimeAsc(this.currentReportDate);

colorTimeLine.update(currentWorkItems, controller.calcSeconds(currentWorkItems));

final SortedSet<Project> workedProjectsSet = currentWorkItems.stream()
.map(Work::getProject)
.collect(Collectors.toCollection(() -> new TreeSet<>(
Comparator.comparing(Project::getIndex))));

long currentWorkSeconds = 0;
long currentSeconds = 0;
this.currentDayLabel.setText(report.getDateString());

for (final Project project : workedProjectsSet) {
final List<Work> onlyCurrentProjectWork = currentWorkItems.stream()
.filter(w -> w.getProject() == project)
.collect(Collectors.toList());
colorTimeLine.update(report.getWorkItems(), report.getWorkItemsSeconds());

final long projectWorkSeconds = controller.calcSeconds(onlyCurrentProjectWork);

currentSeconds += projectWorkSeconds;
if (project.isWork()) {
currentWorkSeconds += projectWorkSeconds;
}
for (Project project : report.getWorkedProjectsSet()) {
final List<Work> projectWorks = report.getWorkItems()
.stream()
.filter(w -> w.getProject().getId() == project.getId())
.toList();

final HBox projectButtonBox = new HBox();
projectButtonBox.getChildren().add(createCopyProjectButton(onlyCurrentProjectWork));

projectButtonBox.getChildren().add(createCopyProjectButton(projectWorks));
final TreeItem<TableRow> projectRow = new TreeItem<>(
new ProjectTableRow(project, projectWorkSeconds, projectButtonBox));
new ProjectTableRow(project, report.getProjectWorkSecondsMap().get(project.getId()), projectButtonBox));

for (final Work w : onlyCurrentProjectWork) {
for (final Work work : projectWorks) {
final HBox workButtonBox = new HBox(5.0);
if(w.getId()==model.activeWorkItem.get().getId()){

if (work.getId() == model.activeWorkItem.get().getId() || work.getId() == 0) {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

reminder for me: I do not like having this check still in the view-controller. Idea was that view just stupidly can show what the "view-model" presents it. no special logic needed.
this is why we did not merge it yet - as we now have logic in 2 places (Report.java and this class)

Label label = new Label("Active Work");
label.setTooltip(new Tooltip("The active work item cannot be edited as it is currently active. To edit it you need to switch to another work first."));
label.setTooltip(new Tooltip(
"The active work item cannot be edited as it is currently active. To edit it you need to switch to another work first."));
label.setStyle("-fx-font-weight: bold");
workButtonBox.getChildren().add(label);
}else {
workButtonBox.getChildren().add(createCopyWorkButton(w));
workButtonBox.getChildren().add(createEditWorkButton(w));
workButtonBox.getChildren().add(createDeleteWorkButton(w));
} else {
workButtonBox.getChildren().add(createCopyWorkButton(work));
workButtonBox.getChildren().add(createEditWorkButton(work));
workButtonBox.getChildren().add(createDeleteWorkButton(work));
}
final TreeItem<TableRow> workRow = new TreeItem<>(new WorkTableRow(w, workButtonBox));
final TreeItem<TableRow> workRow = new TreeItem<>(new WorkTableRow(work, workButtonBox));
projectRow.getChildren().add(workRow);
}

Expand All @@ -287,8 +260,8 @@ private void updateReport(final LocalDate dateToShow) {

}

this.currentDayTimeLabel.setText(DateFormatter.secondsToHHMMSS(currentSeconds));
this.currentDayWorkTimeLabel.setText(DateFormatter.secondsToHHMMSS(currentWorkSeconds));
this.currentDayTimeLabel.setText(report.getPresentTimeString());
this.currentDayWorkTimeLabel.setText(report.getWorkTimeString());

loadCalenderWidget();

Expand Down
Loading