spdxedit.license.LicenseEditControl.java Source code

Java tutorial

Introduction

Here is the source code for spdxedit.license.LicenseEditControl.java

Source

/*
SPDX-License-Identifier: Apache-2.0
 */
package spdxedit.license;

import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader;
import javafx.scene.control.*;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.Pane;
import javafx.util.StringConverter;
import org.apache.commons.lang3.StringUtils;
import org.spdx.rdfparser.InvalidSPDXAnalysisException;
import org.spdx.rdfparser.SpdxDocumentContainer;
import org.spdx.rdfparser.license.*;
import org.spdx.rdfparser.model.SpdxDocument;
import org.spdx.rdfparser.model.SpdxFile;

import java.io.IOException;
import java.net.URL;
import java.util.Arrays;
import java.util.Objects;
import java.util.ResourceBundle;
import java.util.concurrent.Callable;
import java.util.function.Consumer;
import java.util.stream.Collectors;

public class LicenseEditControl {

    private SpdxDocumentContainer documentContainer;

    private SpdxFile file;

    private AnyLicenseInfo initialValue = new SpdxNoAssertionLicense();

    private boolean showExtractLicenseButton;

    @FXML
    private ResourceBundle resources;

    @FXML
    private URL location;

    @FXML
    private RadioButton rdoNone;

    @FXML
    private RadioButton rdoNoAssert;

    @FXML
    private RadioButton rdoStandard;

    @FXML
    private ChoiceBox<String> chcListedLicense;

    @FXML
    private ChoiceBox<ExtractedLicenseInfo> chcExtractedLicenses;

    @FXML
    private RadioButton rdoExtracted;

    @FXML
    private Button btnNewFromFile;

    private Consumer<AnyLicenseInfo> onLicenseChange;

    @FXML
    void handleBtnNewFromFileClick(MouseEvent event) {
        FileLicenseEditor.extractLicenseFromFile(file, documentContainer);
        refreshExtractedLicenses();
    }

    /**
     * Creates a new control without an exstract license button.
     * @param documentContainer
     */
    public LicenseEditControl(SpdxDocumentContainer documentContainer) {
        this(documentContainer, null, false);
    }

    /**
     *
     * @param documentContainer
     * @param file File from which to extract the license if Extract License button is clicked.
     * @param showExtractLicenseButton
     */
    public LicenseEditControl(SpdxDocumentContainer documentContainer, SpdxFile file,
            boolean showExtractLicenseButton) {
        this.showExtractLicenseButton = showExtractLicenseButton;
        this.documentContainer = documentContainer;
        this.file = file;
    }

    @FXML
    void initialize() {
        assert rdoNone != null : "fx:id=\"rdoNone\" was not injected: check your FXML file 'LicenseEditControl.fxml'.";
        assert rdoNoAssert != null : "fx:id=\"rdoNoAssert\" was not injected: check your FXML file 'LicenseEditControl.fxml'.";
        assert rdoStandard != null : "fx:id=\"rdoStandard\" was not injected: check your FXML file 'LicenseEditControl.fxml'.";
        assert chcListedLicense != null : "fx:id=\"chcListedLicense\" was not injected: check your FXML file 'LicenseEditControl.fxml'.";
        assert chcExtractedLicenses != null : "fx:id=\"chcExtractedLicenses\" was not injected: check your FXML file 'LicenseEditControl.fxml'.";
        assert rdoExtracted != null : "fx:id=\"rdoExtracted\" was not injected: check your FXML file 'LicenseEditControl.fxml'.";
        assert btnNewFromFile != null : "fx:id=\"btnNewFromFile\" was not injected: check your FXML file 'LicenseEditControl.fxml'.";

        //Make radio buttons mutually exclusive

        ToggleGroup licenseTypeGroup = new ToggleGroup();
        rdoExtracted.setToggleGroup(licenseTypeGroup);
        rdoStandard.setToggleGroup(licenseTypeGroup);
        rdoNone.setToggleGroup(licenseTypeGroup);
        rdoNoAssert.setToggleGroup(licenseTypeGroup);

        //Choice boxes should disable when their respective radio buttons are untoggled.
        rdoStandard.selectedProperty()
                .addListener((observable, oldValue, newValue) -> chcListedLicense.setDisable(!newValue));
        rdoExtracted.selectedProperty()
                .addListener((observable, oldValue, newValue) -> chcExtractedLicenses.setDisable(!newValue));

        chcListedLicense.getItems()
                .addAll(Arrays.stream(ListedLicenses.getListedLicenses().getSpdxListedLicenseIds()).sorted()
                        .collect(Collectors.toList()));
        chcExtractedLicenses.setConverter(new StringConverter<ExtractedLicenseInfo>() {
            @Override
            public String toString(ExtractedLicenseInfo object) {
                return object.getName();
            }

            @Override
            public ExtractedLicenseInfo fromString(String string) {
                return Arrays.stream(documentContainer.getExtractedLicenseInfos())
                        .filter(license -> StringUtils.equals(license.getName(), string)).findAny().get();
            }
        });

        btnNewFromFile.setVisible(showExtractLicenseButton);

        //Apply the initial value
        if (this.initialValue instanceof SpdxListedLicense) {
            chcListedLicense.setValue(((SpdxListedLicense) initialValue).getLicenseId());
            chcListedLicense.setDisable(false);
            rdoStandard.selectedProperty().setValue(true);
        } else if (initialValue instanceof ExtractedLicenseInfo) {
            refreshExtractedLicenses();
            chcExtractedLicenses.setValue((ExtractedLicenseInfo) initialValue);
            chcExtractedLicenses.setDisable(false);
            rdoExtracted.selectedProperty().setValue(true);
        } else if (initialValue instanceof SpdxNoAssertionLicense) {
            rdoNoAssert.selectedProperty().setValue(true);
        } else if (initialValue instanceof SpdxNoneLicense) {
            rdoNone.selectedProperty().setValue(true);
        } else {
            new Alert(Alert.AlertType.ERROR,
                    "Unsupported license type: " + initialValue.getClass().getSimpleName() + ".", ButtonType.OK);
        }

        //Listen for change events

        licenseTypeGroup.selectedToggleProperty().addListener((observable1, oldValue1, newValue1) -> {
            hanldLicenseChangeEvent();
        });
        chcExtractedLicenses.valueProperty().addListener((observable, oldValue, newValue) -> {
            hanldLicenseChangeEvent();
        });
        chcListedLicense.valueProperty().addListener((observable, oldValue, newValue) -> {
            hanldLicenseChangeEvent();
        });
    }

    private void refreshExtractedLicenses() {
        chcExtractedLicenses.getItems().clear();
        chcExtractedLicenses.getItems()
                .addAll(Arrays.stream(documentContainer.getExtractedLicenseInfos()).collect(Collectors.toList()));
    }

    /**
     * Sets the initial value of the control. Has no impact if called after the UI is initialized.
     * Must not be null.
     *
     * @param value
     */
    public void setInitialValue(AnyLicenseInfo value) {
        this.initialValue = Objects.requireNonNull(value);
    }

    public AnyLicenseInfo getValue() {
        AnyLicenseInfo result = null;
        if (rdoNoAssert.isSelected()) {
            result = new SpdxNoAssertionLicense();
        } else if (rdoNone.isSelected()) {
            result = new SpdxNoneLicense();
        } else if (rdoStandard.isSelected()) {
            try {
                result = ListedLicenses.getListedLicenses().getListedLicenseById(chcListedLicense.getValue());
            } catch (InvalidSPDXAnalysisException e) {
                throw new RuntimeException(e);
            }
        } else if (rdoExtracted.isSelected()) {
            result = chcExtractedLicenses.getValue();
        }
        if (result == null) {
            new Alert(Alert.AlertType.ERROR, "Unable to extract selected license", ButtonType.OK);
        }
        return result;
    }

    public Pane getUi() {
        try {
            FXMLLoader loader = new FXMLLoader(LicenseEditControl.class.getResource("/LicenseEdit.fxml"));
            loader.setController(this);
            Pane pane = loader.load();
            return pane;
        } catch (IOException ioe) {
            throw new RuntimeException("Unable to load scene for License editor dialog");
        }
    }

    public void setOnLicenseChange(Consumer<AnyLicenseInfo> onLicenseChange) {
        this.onLicenseChange = onLicenseChange;
    }

    /**
     * Catchall handler for all license change events.
     */
    private void hanldLicenseChangeEvent() {
        if (this.onLicenseChange != null) {
            this.onLicenseChange.accept(getValue());
        }
    }

}