commit 6a4c1ace4ff6beb063b8e211e3c597125934c09d Author: Andreas Billmann Date: Mon Mar 23 21:50:58 2015 +0100 initial commit of version 2 diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..fd2d5e0 --- /dev/null +++ b/.gitignore @@ -0,0 +1,76 @@ +# Created by .ignore support plugin (hsz.mobi) +### Java template +*.class + +# Mobile Tools for Java (J2ME) +.mtj.tmp/ + +# Package Files # +*.jar +*.war +*.ear + +# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml +hs_err_pid* + + +### Gradle template +.gradle +build/ + +# Ignore Gradle GUI config +gradle-app.setting + +# Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored) +!gradle-wrapper.jar + + +### JetBrains template +# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm + +*.iml + +## Directory-based project format: +.idea/ +# if you remove the above rule, at least ignore the following: + +# User-specific stuff: +# .idea/workspace.xml +# .idea/tasks.xml +# .idea/dictionaries + +# Sensitive or high-churn files: +# .idea/dataSources.ids +# .idea/dataSources.xml +# .idea/sqlDataSources.xml +# .idea/dynamic.xml +# .idea/uiDesigner.xml + +# Gradle: +# .idea/gradle.xml +# .idea/libraries + +# Mongo Explorer plugin: +# .idea/mongoSettings.xml + +## File-based project format: +*.ipr +*.iws + +## Plugin-specific files: + +# IntelliJ +out/ + +# mpeltonen/sbt-idea plugin +.idea_modules/ + +# JIRA plugin +atlassian-ide-plugin.xml + +# Crashlytics plugin (for Android Studio and IntelliJ) +com_crashlytics_export_strings.xml +crashlytics.properties +crashlytics-build.properties + + diff --git a/README.md b/README.md new file mode 100644 index 0000000..a1045a4 --- /dev/null +++ b/README.md @@ -0,0 +1,17 @@ +GeoFroggerFX +============ +GeoFroggerFX is a JavaFX desktop application to manage geocaching gpx files. +Webpage of the project: [http://www.geofroggerfx.de](http://www.geofroggerfx.de) + +This is the second try after a complete rewrite. + +Requirements +------------ +- JDK8 + +Building and run with Gradle +---------------------------- +* Set your environment variable JAVA_HOME to the directory that contains the JDK1.8 +* gradlew run + + diff --git a/build.gradle b/build.gradle new file mode 100644 index 0000000..b5512b9 --- /dev/null +++ b/build.gradle @@ -0,0 +1,26 @@ +apply plugin: 'java' +apply plugin: 'groovy' +apply plugin:'application' +apply plugin: 'idea' + +sourceCompatibility = 1.8 +version = '1.0' +mainClassName = 'de.geofroggerfx.ui.GeoFroggerFX' + +repositories { + mavenCentral() +} + +dependencies { + testCompile group: 'junit', name: 'junit', version: '4.11' + compile group: 'org.codehaus.groovy', name: 'groovy-all', version: '2.4.0' + compile group: 'org.springframework', name:'spring-context', version: '4.1.5.RELEASE' + compile group: 'org.springframework', name:'spring-jdbc', version: '4.1.5.RELEASE' + compile group: 'org.codehaus.woodstox', name: 'woodstox-core-asl', version: '4.4.1' + compile group: 'org.codehaus.woodstox', name: 'stax2-api', version: '4.0.0' + compile group: 'com.h2database', name: 'h2', version: '1.4.186' + compile group: 'de.jensd', name: 'fontawesomefx', version: '8.2' + compile group: 'org.controlsfx', name: 'controlsfx', version: '8.20.8' + compile group: 'com.lynden', name: 'GMapsFX', version: '1.1.1' +} + diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar new file mode 100644 index 0000000..3d0dee6 Binary files /dev/null and b/gradle/wrapper/gradle-wrapper.jar differ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties new file mode 100644 index 0000000..d4e1165 --- /dev/null +++ b/gradle/wrapper/gradle-wrapper.properties @@ -0,0 +1,6 @@ +#Mon Mar 09 19:47:19 CET 2015 +distributionBase=GRADLE_USER_HOME +distributionPath=wrapper/dists +zipStoreBase=GRADLE_USER_HOME +zipStorePath=wrapper/dists +distributionUrl=https\://services.gradle.org/distributions/gradle-2.1-all.zip diff --git a/gradlew b/gradlew new file mode 100644 index 0000000..91a7e26 --- /dev/null +++ b/gradlew @@ -0,0 +1,164 @@ +#!/usr/bin/env bash + +############################################################################## +## +## Gradle start up script for UN*X +## +############################################################################## + +# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +DEFAULT_JVM_OPTS="" + +APP_NAME="Gradle" +APP_BASE_NAME=`basename "$0"` + +# Use the maximum available, or set MAX_FD != -1 to use that value. +MAX_FD="maximum" + +warn ( ) { + echo "$*" +} + +die ( ) { + echo + echo "$*" + echo + exit 1 +} + +# OS specific support (must be 'true' or 'false'). +cygwin=false +msys=false +darwin=false +case "`uname`" in + CYGWIN* ) + cygwin=true + ;; + Darwin* ) + darwin=true + ;; + MINGW* ) + msys=true + ;; +esac + +# For Cygwin, ensure paths are in UNIX format before anything is touched. +if $cygwin ; then + [ -n "$JAVA_HOME" ] && JAVA_HOME=`cygpath --unix "$JAVA_HOME"` +fi + +# Attempt to set APP_HOME +# Resolve links: $0 may be a link +PRG="$0" +# Need this for relative symlinks. +while [ -h "$PRG" ] ; do + ls=`ls -ld "$PRG"` + link=`expr "$ls" : '.*-> \(.*\)$'` + if expr "$link" : '/.*' > /dev/null; then + PRG="$link" + else + PRG=`dirname "$PRG"`"/$link" + fi +done +SAVED="`pwd`" +cd "`dirname \"$PRG\"`/" >&- +APP_HOME="`pwd -P`" +cd "$SAVED" >&- + +CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar + +# Determine the Java command to use to start the JVM. +if [ -n "$JAVA_HOME" ] ; then + if [ -x "$JAVA_HOME/jre/sh/java" ] ; then + # IBM's JDK on AIX uses strange locations for the executables + JAVACMD="$JAVA_HOME/jre/sh/java" + else + JAVACMD="$JAVA_HOME/bin/java" + fi + if [ ! -x "$JAVACMD" ] ; then + die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." + fi +else + JAVACMD="java" + which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." +fi + +# Increase the maximum file descriptors if we can. +if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then + MAX_FD_LIMIT=`ulimit -H -n` + if [ $? -eq 0 ] ; then + if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then + MAX_FD="$MAX_FD_LIMIT" + fi + ulimit -n $MAX_FD + if [ $? -ne 0 ] ; then + warn "Could not set maximum file descriptor limit: $MAX_FD" + fi + else + warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" + fi +fi + +# For Darwin, add options to specify how the application appears in the dock +if $darwin; then + GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" +fi + +# For Cygwin, switch paths to Windows format before running java +if $cygwin ; then + APP_HOME=`cygpath --path --mixed "$APP_HOME"` + CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` + + # We build the pattern for arguments to be converted via cygpath + ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` + SEP="" + for dir in $ROOTDIRSRAW ; do + ROOTDIRS="$ROOTDIRS$SEP$dir" + SEP="|" + done + OURCYGPATTERN="(^($ROOTDIRS))" + # Add a user-defined pattern to the cygpath arguments + if [ "$GRADLE_CYGPATTERN" != "" ] ; then + OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" + fi + # Now convert the arguments - kludge to limit ourselves to /bin/sh + i=0 + for arg in "$@" ; do + CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` + CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option + + if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition + eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` + else + eval `echo args$i`="\"$arg\"" + fi + i=$((i+1)) + done + case $i in + (0) set -- ;; + (1) set -- "$args0" ;; + (2) set -- "$args0" "$args1" ;; + (3) set -- "$args0" "$args1" "$args2" ;; + (4) set -- "$args0" "$args1" "$args2" "$args3" ;; + (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; + (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; + (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; + (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; + (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; + esac +fi + +# Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules +function splitJvmOpts() { + JVM_OPTS=("$@") +} +eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS +JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME" + +exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@" diff --git a/gradlew.bat b/gradlew.bat new file mode 100644 index 0000000..8a0b282 --- /dev/null +++ b/gradlew.bat @@ -0,0 +1,90 @@ +@if "%DEBUG%" == "" @echo off +@rem ########################################################################## +@rem +@rem Gradle startup script for Windows +@rem +@rem ########################################################################## + +@rem Set local scope for the variables with windows NT shell +if "%OS%"=="Windows_NT" setlocal + +@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +set DEFAULT_JVM_OPTS= + +set DIRNAME=%~dp0 +if "%DIRNAME%" == "" set DIRNAME=. +set APP_BASE_NAME=%~n0 +set APP_HOME=%DIRNAME% + +@rem Find java.exe +if defined JAVA_HOME goto findJavaFromJavaHome + +set JAVA_EXE=java.exe +%JAVA_EXE% -version >NUL 2>&1 +if "%ERRORLEVEL%" == "0" goto init + +echo. +echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:findJavaFromJavaHome +set JAVA_HOME=%JAVA_HOME:"=% +set JAVA_EXE=%JAVA_HOME%/bin/java.exe + +if exist "%JAVA_EXE%" goto init + +echo. +echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:init +@rem Get command-line arguments, handling Windowz variants + +if not "%OS%" == "Windows_NT" goto win9xME_args +if "%@eval[2+2]" == "4" goto 4NT_args + +:win9xME_args +@rem Slurp the command line arguments. +set CMD_LINE_ARGS= +set _SKIP=2 + +:win9xME_args_slurp +if "x%~1" == "x" goto execute + +set CMD_LINE_ARGS=%* +goto execute + +:4NT_args +@rem Get arguments from the 4NT Shell from JP Software +set CMD_LINE_ARGS=%$ + +:execute +@rem Setup the command line + +set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar + +@rem Execute Gradle +"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS% + +:end +@rem End local scope for the variables with windows NT shell +if "%ERRORLEVEL%"=="0" goto mainEnd + +:fail +rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of +rem the _cmd.exe /c_ return code! +if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 +exit /b 1 + +:mainEnd +if "%OS%"=="Windows_NT" endlocal + +:omega diff --git a/license.txt b/license.txt new file mode 100644 index 0000000..e615d2e --- /dev/null +++ b/license.txt @@ -0,0 +1,25 @@ +/* + * Copyright (c) 2013-2015 Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ \ No newline at end of file diff --git a/plugins/BasicListStatisticsPlugin.groovy b/plugins/BasicListStatisticsPlugin.groovy new file mode 100644 index 0000000..546e27e --- /dev/null +++ b/plugins/BasicListStatisticsPlugin.groovy @@ -0,0 +1,97 @@ +import de.geofroggerfx.plugins.Plugin +import javafx.collections.FXCollections +import javafx.scene.chart.PieChart +import javafx.scene.control.ButtonType +import javafx.scene.control.Dialog +import javafx.scene.control.ScrollPane +import javafx.scene.layout.VBox + +import static javafx.scene.chart.PieChart.Data + +class BasicListStatisticsPlugin implements Plugin { + + private difficultyTerrainValues = ['1', '1.5', '2', '2.5', '3', '3.5', '4', '4.5', '5'] + + final String name = "Basic List Statistic" + final String version = "0.0.2" + + @Override + void run(final Map context) { + showDialog(createContent(context.cacheService)) + } + + /** + * creates the statistic charts to show + * @param sessionContext context with the cache list in it + * @return + */ + private javafx.scene.Node createContent(cacheService) { + + // get the cache list from service + def cacheList = cacheService.getAllCaches() + + // create a vbox as layout container + VBox contenPane = new VBox() + + // groovy maps for selecting the statistic numbers + def typeStats = [:] + def difficultyStats = [:] + def terrainStats = [:] + + // iterate over all the caches and count the data + for (def cache in cacheList) { + incrementStats(typeStats, cache.type) + incrementStats(difficultyStats, cache.difficulty) + incrementStats(terrainStats, cache.terrain) + } + + // create javafx chart + def typeData = FXCollections.observableArrayList() + typeStats.each() { key, value -> typeData.add(new Data(key.toString() + ' (' + value + ')', value as double)) } + def typeChart = new PieChart(typeData); + typeChart.setTitle("Spreading of cache types in list."); + + // create javafx chart + def difficultyData = FXCollections.observableArrayList() + difficultyTerrainValues.each { + def value = difficultyStats[it] + if (value) difficultyData.add(new Data(it + ' (' + value + ')', value)) + } + def difficultyChart = new PieChart(difficultyData); + difficultyChart.setTitle("Spreading of difficulties in list."); + + // create javafx chart + def terrainData = FXCollections.observableArrayList() + difficultyTerrainValues.each { + def value = terrainStats[it] + if (value) terrainData.add(new Data(it + ' (' + value + ')', value)) + } + def terrainChart = new PieChart(terrainData); + terrainChart.setTitle("Spreading of terrain in list."); + + // add charts to layout container + contenPane.children.addAll(typeChart, difficultyChart, terrainChart) + + // return the layout container + def scrollPane = new ScrollPane(contenPane) + scrollPane.minWidth = 600 + scrollPane.minHeight = 450 + scrollPane + } + + private void incrementStats(map, key) { + map[key] = map[key] ? map[key] + 1 : 1 + } + + private void showDialog(content) { + Dialog dialog = new Dialog() + dialog.resizableProperty().set(true) + dialog.getDialogPane().getButtonTypes().addAll(ButtonType.CLOSE); + dialog.setTitle(name + " (" + version + ")") + dialog.setHeaderText("This example plugin shows some stats based on the current list.\nThese statistics are global statistics over all caches in list\nand not personalized statistics over own founds.") + dialog.getDialogPane().setContent(content) + dialog.setWidth(800) + dialog.setHeight(600) + dialog.show() + } +} \ No newline at end of file diff --git a/plugins/OwnStatisticsPlugin.groovy b/plugins/OwnStatisticsPlugin.groovy new file mode 100644 index 0000000..762e8ec --- /dev/null +++ b/plugins/OwnStatisticsPlugin.groovy @@ -0,0 +1,139 @@ +import de.geofroggerfx.plugins.Plugin +import javafx.collections.FXCollections +import javafx.concurrent.Service +import javafx.concurrent.Task +import javafx.concurrent.WorkerStateEvent +import javafx.event.EventHandler +import javafx.scene.chart.PieChart +import javafx.scene.control.ButtonType +import javafx.scene.control.Dialog +import javafx.scene.control.ScrollPane +import javafx.scene.layout.Priority +import javafx.scene.layout.VBox + +import static javafx.scene.chart.PieChart.Data + +class OwnStatisticsPlugin implements Plugin { + + private difficultyTerrainValues = ['1', '1.5', '2', '2.5', '3', '3.5', '4', '4.5', '5'] + + final String name = "Own Statistic" + final String version = "0.0.1" + final CalculateService service = new CalculateService(); + + OwnStatisticsPlugin() { + service.onSucceeded = { + showDialog(createContent(it.source.value)) + } as EventHandler; + } + + @Override + void run(final Map context) { + calculateStats(context.cacheService) + } + +/** + * creates the statistic charts to show + * @param sessionContext context with the cache list in it + * @return + */ + private void calculateStats(cacheService) { + // get the cache list from service + def cacheList = cacheService.getAllCaches() + service.cacheList = cacheList; + service.restart(); + } + + /** + * creates the statistic charts to show + * @param sessionContext context with the cache list in it + * @return + */ + private javafx.scene.Node createContent(result) { + + // create a vbox as layout container + VBox contenPane = new VBox() + contenPane.prefWidth = 600 + VBox.setVgrow(contenPane, Priority.ALWAYS); + + // create javafx chart + def typeData = FXCollections.observableArrayList() + result.typeStats.each() { key, value -> typeData.add(new Data(key.toString() + ' (' + value + ')', value as double)) } + def typeChart = new PieChart(typeData); + typeChart.setTitle("Spreading of cache types found (${result.foundCount})."); + + // create javafx chart + def difficultyData = FXCollections.observableArrayList() + difficultyTerrainValues.each { + def value = result.difficultyStats[it] + if (value) difficultyData.add(new Data(it + ' (' + value + ')', value)) + } + def difficultyChart = new PieChart(difficultyData); + difficultyChart.setTitle("Spreading of difficulties found (${result.foundCount})."); + + // create javafx chart + def terrainData = FXCollections.observableArrayList() + difficultyTerrainValues.each { + def value = result.terrainStats[it] + if (value) terrainData.add(new Data(it + ' (' + value + ')', value)) + } + def terrainChart = new PieChart(terrainData); + terrainChart.setTitle("Spreading of terrain found (${result.foundCount})."); + + // add charts to layout container + contenPane.children.addAll(typeChart, difficultyChart, terrainChart) + + // return the layout container + def scrollPane = new ScrollPane(contenPane) + scrollPane.minWidth = 640 + scrollPane.minHeight = 450 + scrollPane + } + + private void showDialog(content) { + Dialog dialog = new Dialog() + dialog.resizableProperty().set(true) + dialog.getDialogPane().getButtonTypes().addAll(ButtonType.CLOSE); + dialog.setTitle(name + " (" + version + ")") + dialog.setHeaderText("This example plugin shows some stats based on the current list.\nThese statistics are found statistics, based on all found caches in the list.") + dialog.getDialogPane().setContent(content) + dialog.setWidth(800) + dialog.setHeight(600) + dialog.show() + } +} + +class CalculateService extends Service { + + def cacheList + + @Override + protected Task createTask() { + return new Task() { + @Override + protected LinkedHashMap call() throws Exception { + + def typeStats = [:] + def difficultyStats = [:] + def terrainStats = [:] + + def foundCount = 0 + + for (def cache in cacheList) { + if (cache.found) { + foundCount++ + incrementStats(typeStats, cache.type) + incrementStats(difficultyStats, cache.difficulty) + incrementStats(terrainStats, cache.terrain) + } + } + ['foundCount': foundCount, 'typeStats': typeStats, 'difficultyStats': difficultyStats, 'terrainStats': terrainStats] + } + }; + } + + private void incrementStats(map, key) { + map[key] = map[key] ? map[key] + 1 : 1 + } + +} \ No newline at end of file diff --git a/settings.gradle b/settings.gradle new file mode 100644 index 0000000..874c222 --- /dev/null +++ b/settings.gradle @@ -0,0 +1,2 @@ +rootProject.name = 'GeoFroggerFX2' + diff --git a/src/main/java/de/geofroggerfx/application/ProgressEvent.java b/src/main/java/de/geofroggerfx/application/ProgressEvent.java new file mode 100644 index 0000000..e7a84a6 --- /dev/null +++ b/src/main/java/de/geofroggerfx/application/ProgressEvent.java @@ -0,0 +1,69 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.application; + +/** + * @author Andreas + */ +public class ProgressEvent { + + public enum State {INITIALIZED, STARTED, RUNNING, FINISHED} + + ; + public static final double INDETERMINATE_PROGRESS = -1.0; + + private final String module; + private final State state; + private final String message; + private final Double progress; + + public ProgressEvent(String module, State state, String message) { + this(module, state, message, INDETERMINATE_PROGRESS); + } + + public ProgressEvent(String module, State state, String message, Double progress) { + this.module = module; + this.state = state; + this.message = message; + this.progress = progress; + } + + public String getModule() { + return module; + } + + public State getState() { + return state; + } + + public String getMessage() { + return message; + } + + public Double getProgress() { + return progress; + } +} diff --git a/src/main/java/de/geofroggerfx/application/ProgressListener.java b/src/main/java/de/geofroggerfx/application/ProgressListener.java new file mode 100644 index 0000000..f9d658a --- /dev/null +++ b/src/main/java/de/geofroggerfx/application/ProgressListener.java @@ -0,0 +1,33 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.application; + +/** + * @author Andreas + */ +public interface ProgressListener { + void progress(ProgressEvent event); +} diff --git a/src/main/java/de/geofroggerfx/application/SessionContext.java b/src/main/java/de/geofroggerfx/application/SessionContext.java new file mode 100644 index 0000000..395230a --- /dev/null +++ b/src/main/java/de/geofroggerfx/application/SessionContext.java @@ -0,0 +1,88 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.application; + +import org.springframework.stereotype.Component; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; + +/** + * @author Andreas + */ +@Component +public class SessionContext { + + public static final String CACHE_ENTRY_LIST = "CACHE_ENTRY_LIST"; + public static final String CURRENT_CACHE = "CURRENT_CACHE"; + + private final Map map = new ConcurrentHashMap<>(); + private final Map> sessionListeners = new HashMap<>(); + + public void setData(String key, Object value) { + if (value == null && map.containsKey(key)) { + map.remove(key); + } else if (value != null) { + map.put(key, value); + } + fireSessionEvent(key); + } + + public Object getData(String key) { + if (map.containsKey(key)) { + return map.get(key); + } else { + return null; + } + } + + public void addListener(String key, SessionContextListener sessionListener) { + + List listenerList; + if (sessionListeners.containsKey(key)) { + listenerList = sessionListeners.get(key); + } else { + listenerList = new ArrayList<>(); + sessionListeners.put(key, listenerList); + } + + if (!listenerList.contains(sessionListener)) { + listenerList.add(sessionListener); + } + } + + private void fireSessionEvent(String key) { + if (sessionListeners.containsKey(key)) { + sessionListeners. + get(key). + stream(). + forEach(SessionContextListener::sessionContextChanged); + } + } +} diff --git a/src/main/java/de/geofroggerfx/application/SessionContextListener.java b/src/main/java/de/geofroggerfx/application/SessionContextListener.java new file mode 100644 index 0000000..d071c60 --- /dev/null +++ b/src/main/java/de/geofroggerfx/application/SessionContextListener.java @@ -0,0 +1,33 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.application; + +/** + * @author Andreas + */ +public interface SessionContextListener { + void sessionContextChanged(); +} diff --git a/src/main/java/de/geofroggerfx/dao/CacheDAO.java b/src/main/java/de/geofroggerfx/dao/CacheDAO.java new file mode 100644 index 0000000..43e35f8 --- /dev/null +++ b/src/main/java/de/geofroggerfx/dao/CacheDAO.java @@ -0,0 +1,45 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.dao; + +import de.geofroggerfx.model.Cache; +import de.geofroggerfx.model.CacheListEntry; + +import java.util.List; + +/** + * Created by Andreas on 11.03.2015. + */ +public interface CacheDAO { + + void save(List listOfCaches); + void update(Cache cache); + List getAllCachEntriesSortBy(String name, String asc); + + Cache getCacheForId(long id); + + List getAllCaches(); +} diff --git a/src/main/java/de/geofroggerfx/dao/jdbc/DataConfig.java b/src/main/java/de/geofroggerfx/dao/jdbc/DataConfig.java new file mode 100644 index 0000000..9fd26aa --- /dev/null +++ b/src/main/java/de/geofroggerfx/dao/jdbc/DataConfig.java @@ -0,0 +1,61 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.dao.jdbc; + +import org.h2.jdbcx.JdbcDataSource; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.context.annotation.PropertySource; +import org.springframework.core.env.Environment; +import org.springframework.jdbc.datasource.DataSourceTransactionManager; +import org.springframework.transaction.PlatformTransactionManager; + +import javax.sql.DataSource; + +/** + * Created by Andreas on 11.03.2015. + */ +@Configuration +@PropertySource("classpath:/de/geofroggerfx/dao/jdbc/database.properties") +public class DataConfig { + @Autowired + private Environment env; + + @Bean + public DataSource dataSource(){ + JdbcDataSource dataSource = new JdbcDataSource(); + dataSource.setURL(env.getProperty("jdbc.url")); + dataSource.setUser(env.getProperty("jdbc.username")); + dataSource.setPassword(env.getProperty("jdbc.password")); + return dataSource; + } + + @Bean + public PlatformTransactionManager transactionManager(){ + return new DataSourceTransactionManager(dataSource()); + } +} diff --git a/src/main/java/de/geofroggerfx/dao/jdbc/JDBCUtils.java b/src/main/java/de/geofroggerfx/dao/jdbc/JDBCUtils.java new file mode 100644 index 0000000..a83b46f --- /dev/null +++ b/src/main/java/de/geofroggerfx/dao/jdbc/JDBCUtils.java @@ -0,0 +1,117 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.dao.jdbc; + +/** + * Created by Andreas on 11.03.2015. + */ +public class JDBCUtils { + + public static String generateSelectSQL(String table, String... columns) { + + assert columns != null && columns.length > 0 : "columns must not be null or empty"; + + StringBuffer sql = new StringBuffer(); + sql.append("SELECT "); + + for (int columnCounter = 0; columnCounter < columns.length-1; columnCounter++) { + addCommaToValue(sql, columns[columnCounter]); + } + sql.append(columns[columns.length-1]); + sql.append(" FROM ").append(table); + return sql.toString(); + } + + public static String generateUpdateSQL(String table, String... columns) { + + assert columns != null && columns.length > 0 : "columns must not be null or empty"; + + StringBuffer sql = new StringBuffer(); + sql.append("UPDATE ").append(table).append(" SET "); + + for (int columnCounter = 0; columnCounter < columns.length-1; columnCounter++) { + addCommaToValue(sql, columns[columnCounter]+"=? "); + } + sql.append(columns[columns.length-1]+"=? "); + sql.append(" WHERE ID = ?"); + return sql.toString(); + } + + public static String generateInsertSQL(String table, String... columns) { + + assert columns != null && columns.length > 0 : "columns must not be null or empty"; + + StringBuffer sql = new StringBuffer(); + sql.append("INSERT INTO ").append(table).append("("); + + for (int columnCounter = 0; columnCounter < columns.length-1; columnCounter++) { + addCommaToValue(sql, columns[columnCounter]); + } + sql.append(columns[columns.length-1]); + + sql.append(") "); + sql.append("values("); + + for (int columnCounter = 0; columnCounter < columns.length-1; columnCounter++) { + addCommaToValue(sql, "?"); + } + sql.append("?"); + sql.append(") "); + + return sql.toString(); + } + + public static String generateInsertSQL(String table, String[] columns, Object[] values) { + + assert columns != null && columns.length > 0 : "columns must not be null or empty"; + + StringBuffer sql = new StringBuffer(); + sql.append("INSERT INTO ").append(table).append("("); + + for (int columnCounter = 0; columnCounter < columns.length-1; columnCounter++) { + addCommaToValue(sql, columns[columnCounter]); + } + sql.append(columns[columns.length-1]); + + sql.append(") "); + sql.append("values("); + + for (int valuesCounter = 0; valuesCounter < values.length-1; valuesCounter++) { + addCommaToValue(sql, "'"+values[valuesCounter]+"'"); + } + sql.append("'"+values[values.length-1]+"'"); + sql.append(") "); + + return sql.toString(); + } + + + public static void addCommaToValue(StringBuffer sql, String value) { + sql.append(value); + sql.append(","); + } + +} diff --git a/src/main/java/de/geofroggerfx/dao/jdbc/JdbcCacheDAO.java b/src/main/java/de/geofroggerfx/dao/jdbc/JdbcCacheDAO.java new file mode 100644 index 0000000..ddc785b --- /dev/null +++ b/src/main/java/de/geofroggerfx/dao/jdbc/JdbcCacheDAO.java @@ -0,0 +1,327 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.dao.jdbc; + +import de.geofroggerfx.dao.CacheDAO; +import de.geofroggerfx.model.Cache; +import de.geofroggerfx.model.CacheListEntry; +import de.geofroggerfx.model.Waypoint; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.jdbc.core.JdbcTemplate; +import org.springframework.stereotype.Repository; + +import java.sql.ResultSet; +import java.sql.SQLException; +import java.util.Arrays; +import java.util.List; +import java.util.logging.Level; +import java.util.logging.Logger; +import java.util.stream.Collectors; + +import static de.geofroggerfx.dao.jdbc.JDBCUtils.*; +import static de.geofroggerfx.model.Container.groundspeakStringToContainer; +import static de.geofroggerfx.model.Type.groundspeakStringToType; + +/** + * Created by Andreas on 11.03.2015. + */ +@Repository +public class JdbcCacheDAO implements CacheDAO { + + private static final Logger LOGGER = Logger.getLogger("JdbcCacheDAO"); + private static final String CACHE_TABLE = "cache"; + private static final String WAYPOINT_TABLE = "waypoint"; + + + private String[] columnListCache = new String[] { + "id", + "name", + "placed_by", + "available", + "archived", + "found", + "difficulty", + "terrain", + "country", + "state", + "short_description", + "short_description_html", + "long_description", + "long_description_html", + "encoded_hints", + "container", + "type", + "user_id"}; + + private String[] columnListWaypoint = new String[] { + "name", + "cache_id", + "latitude", + "longitude", + "time", + "description", + "url", + "urlName", + "symbol", + "type"}; + + + private JdbcTemplate jdbcTemplate; + + @Autowired + public void setDataConfig(DataConfig dataConfig) { + this.jdbcTemplate = new JdbcTemplate(dataConfig.dataSource()); + } + + @Override + public void save(List listOfCaches) { + deleteExistingCaches(listOfCaches); + batchInsertCaches(listOfCaches); + batchInsertWaypoints(listOfCaches); + } + + @Override + public void update(Cache cache) { + String updateSQL = generateUpdateSQL(CACHE_TABLE, columnListCache); + jdbcTemplate.update(updateSQL, valuesFromCache(cache, cache.getId())); + updateSQL = generateUpdateSQL(WAYPOINT_TABLE, columnListWaypoint); + jdbcTemplate.update(updateSQL, valuesFromWaypoint(cache, cache.getMainWayPoint().getName())); + } + + @Override + public List getAllCachEntriesSortBy(String name, String asc) { + return this.jdbcTemplate.query( + "SELECT c.id, c.name AS name, c.name AS code, c.difficulty, c.terrain, c.type FROM "+CACHE_TABLE+" c ORDER BY "+name+" "+asc, + (rs, rowNum) -> { + return new CacheListEntry( + rs.getLong("id"), + rs.getString("name"), + rs.getString("code"), + rs.getString("difficulty"), + rs.getString("terrain"), + groundspeakStringToType(rs.getString("type"))); + }); + } + + @Override + public Cache getCacheForId(long id) { + return this.jdbcTemplate.queryForObject( + generateSelectSQL(CACHE_TABLE, columnListCache) + " WHERE id=?", + new Object[]{id}, + (rs, rowNum) -> { + Cache cache = getCacheFromResultSet(rs); + Waypoint waypoint = getWaypointForCacheId(cache.getId()); + cache.setMainWayPoint(waypoint); + waypoint.setCache(cache); + return cache; + }); + } + + @Override + public List getAllCaches() { + return this.jdbcTemplate.query( + generateSelectSQL(CACHE_TABLE, columnListCache), + (rs, rowNum) -> { + return getCacheFromResultSet(rs); + }); + + } + + private void batchInsertCaches(List listOfCaches) { + LOGGER.info("try to save " + listOfCaches.size() + " caches"); + long startInsert = System.currentTimeMillis(); + + List batch = listOfCaches.parallelStream().map(this::valuesFromCache).collect(Collectors.toList()); + + try { + String insertSQL = generateInsertSQL(CACHE_TABLE, columnListCache); + int[] updateCounts = jdbcTemplate.batchUpdate( + insertSQL, + batch); + int updatedRows = 0; + for (int count:updateCounts) { + updatedRows += count; + } + LOGGER.info("batch inserted "+updatedRows+" caches"); + } catch (Throwable e) { + LOGGER.log(Level.SEVERE, e.getMessage(), e); + } + + long endInsert = System.currentTimeMillis(); + LOGGER.info("try to save " + listOfCaches.size() + " caches -> done in " + (endInsert - startInsert) + " ms"); + } + + private void deleteExistingCaches(List listOfCaches) { + LOGGER.info("try to delete existing caches"); + long startDelete = System.currentTimeMillis(); + StringBuffer sb = new StringBuffer(); + for (int current = 0; current < listOfCaches.size()-1; current++) { + addCommaToValue(sb, Long.toString(listOfCaches.get(current).getId())); + } + sb.append(listOfCaches.get(listOfCaches.size()-1).getId()); + + try { + int result = jdbcTemplate.update("DELETE FROM "+CACHE_TABLE+" WHERE id IN ("+sb.toString()+")"); + LOGGER.info("deleted "+result+" caches"); + } catch (Throwable e) { + LOGGER.log(Level.SEVERE, e.getMessage(), e); + } + long endDelete = System.currentTimeMillis(); + LOGGER.info("try to delete existing caches -> done in " + (endDelete - startDelete) + " ms"); + } + + + private void batchInsertWaypoints(List listOfCaches) { + LOGGER.info("try to save "+listOfCaches.size()+" waypoints"); + long startInsert = System.currentTimeMillis(); + + List batch = listOfCaches.parallelStream().map(this::valuesFromWaypoint).collect(Collectors.toList()); + + try { + String insertSQL = generateInsertSQL(WAYPOINT_TABLE, columnListWaypoint); + int[] updateCounts = jdbcTemplate.batchUpdate( + insertSQL, + batch); + int updatedRows = 0; + for (int count:updateCounts) { + updatedRows += count; + } + LOGGER.info("batch inserted "+updatedRows+" waypoints"); + } catch (Throwable e) { + LOGGER.log(Level.SEVERE, e.getMessage(), e); + } + + long endInsert = System.currentTimeMillis(); + LOGGER.info("try to save "+listOfCaches.size()+" waypoints -> done in "+(endInsert-startInsert)+" ms"); + } + + private Waypoint getWaypointForCacheId(long cacheId) { + return this.jdbcTemplate.queryForObject( + generateSelectSQL(WAYPOINT_TABLE, columnListWaypoint) + " WHERE cache_id=?", + new Object[]{cacheId}, + (rs, rowNum) -> { + return getWaypointFromResultSet(rs); + }); + + } + + + private Cache getCacheFromResultSet(ResultSet rs) throws SQLException { + Cache cache = new Cache(); + cache.setId(rs.getLong("id")); + cache.setName(rs.getString("name")); + cache.setDifficulty(rs.getString("difficulty")); + cache.setTerrain(rs.getString("terrain")); + cache.setPlacedBy(rs.getString("placed_by")); + cache.setAvailable(rs.getBoolean("available")); + cache.setArchived(rs.getBoolean("archived")); + cache.setFound(rs.getBoolean("found")); + cache.setCountry(rs.getString("country")); + cache.setState(rs.getString("state")); + cache.setShortDescription(rs.getString("short_description")); + cache.setLongDescription(rs.getString("long_description")); + cache.setEncodedHints(rs.getString("encoded_hints")); + cache.setShortDescriptionHtml(rs.getBoolean("short_description_html")); + cache.setLongDescriptionHtml(rs.getBoolean("long_description_html")); + cache.setContainer(groundspeakStringToContainer(rs.getString("container"))); + cache.setType(groundspeakStringToType(rs.getString("type"))); + cache.setOwner(null); + return cache; + } + + private Object[] valuesFromCache(Cache cache) { + return new Object[]{ + cache.getId(), + cache.getName(), + cache.getPlacedBy(), + cache.getAvailable(), + cache.getArchived(), + cache.getFound(), + cache.getDifficulty(), + cache.getTerrain(), + cache.getCountry(), + cache.getState(), + cache.getShortDescription(), + cache.getShortDescriptionHtml(), + cache.getLongDescription(), + cache.getLongDescriptionHtml(), + cache.getEncodedHints(), + cache.getContainer().toGroundspeakString(), + cache.getType().toGroundspeakString(), + cache.getOwner() != null ? cache.getOwner().getId() : null }; + } + + private Waypoint getWaypointFromResultSet(ResultSet rs) throws SQLException { + Waypoint waypoint = new Waypoint(); + waypoint.setName(rs.getString("name")); + waypoint.setLatitude(rs.getDouble("latitude")); + waypoint.setLongitude(rs.getDouble("longitude")); + waypoint.setTime(rs.getTimestamp("time")); + waypoint.setDescription(rs.getString("description")); + waypoint.setUrl(rs.getString("url")); + waypoint.setUrlName(rs.getString("urlName")); + waypoint.setSymbol(rs.getString("symbol")); +// waypoint.setType(WaypointType.rs.getString("description")); + return waypoint; + } + + private Object[] valuesFromWaypoint(Cache cache) { + return new Object[]{ + cache.getMainWayPoint().getName(), + cache.getId(), + cache.getMainWayPoint().getLatitude(), + cache.getMainWayPoint().getLongitude(), + cache.getMainWayPoint().getTime(), + cache.getMainWayPoint().getDescription(), + cache.getMainWayPoint().getUrl(), + cache.getMainWayPoint().getUrlName(), + cache.getMainWayPoint().getSymbol(), + null + }; + /* + "name", + "cache_id", + "latitude", + "longitude", + "time", + "description", + "url", + "urlName", + "symbol", + "type" + */ + } + + + private Object[] valuesFromCache(Cache cache, long id) { + return Arrays.asList(valuesFromCache(cache), id).toArray(); + } + + private Object[] valuesFromWaypoint(Cache cache, String name) { + return Arrays.asList(valuesFromWaypoint(cache), name).toArray(); + } + +} diff --git a/src/main/java/de/geofroggerfx/gpx/GPXReader.java b/src/main/java/de/geofroggerfx/gpx/GPXReader.java new file mode 100644 index 0000000..85fed04 --- /dev/null +++ b/src/main/java/de/geofroggerfx/gpx/GPXReader.java @@ -0,0 +1,43 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.gpx; + +import de.geofroggerfx.application.ProgressListener; +import de.geofroggerfx.model.Cache; + +import java.io.File; +import java.io.IOException; +import java.util.List; + +/** + * TODO: describe the class + * + * @author Andreas Billmann + */ +public interface GPXReader { + List load(File fileName) throws IOException; + void addListener(ProgressListener listener); +} diff --git a/src/main/java/de/geofroggerfx/gpx/GroundspeakGPXReader.java b/src/main/java/de/geofroggerfx/gpx/GroundspeakGPXReader.java new file mode 100644 index 0000000..b589449 --- /dev/null +++ b/src/main/java/de/geofroggerfx/gpx/GroundspeakGPXReader.java @@ -0,0 +1,267 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.gpx; + +import de.geofroggerfx.application.ProgressEvent; +import de.geofroggerfx.application.ProgressListener; +import de.geofroggerfx.model.*; +import org.springframework.stereotype.Service; + +import javax.xml.stream.XMLInputFactory; +import javax.xml.stream.XMLStreamConstants; +import javax.xml.stream.XMLStreamReader; +import java.io.File; +import java.io.FileInputStream; +import java.io.IOException; +import java.text.SimpleDateFormat; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.logging.Logger; + +/** + * @author Andreas Billmann + */ +@Service +public class GroundspeakGPXReader implements GPXReader { + + private static final Logger LOGGER = Logger.getLogger(GroundspeakGPXReader.class.getName()); + + public static final String LAT = "lat"; + public static final String LON = "lon"; + public static final String TIME = "time"; + public static final String NAME = "name"; + public static final String DESC = "desc"; + public static final String WPT = "wpt"; + public static final String URL = "url"; + public static final String URLNAME = "urlname"; + public static final String SYM = "sym"; + public static final String TYPE = "type"; + public static final String CACHE = "cache"; + public static final String GROUNDSPEAK = "groundspeak"; + public static final String ID = "id"; + public static final String AVAILABLE = "available"; + public static final String ARCHIVED = "archived"; + public static final String PLACED_BY = "placed_by"; + public static final String OWNER = "owner"; + public static final String CONTAINER = "container"; + public static final String ATTRIBUTES = "attributes"; + public static final String ATTRIBUTE = "attribute"; + public static final String INC = "inc"; + public static final String DIFFICULTY = "difficulty"; + public static final String TERRAIN = "terrain"; + public static final String COUNTRY = "country"; + public static final String STATE = "state"; + public static final String SHORT_DESCRIPTION = "short_description"; + public static final String HTML = "html"; + public static final String LONG_DESCRIPTION = "long_description"; + public static final String ENCODED_HINTS = "encoded_hints"; + public static final String LOGS = "logs"; + public static final String LOG = "log"; + public static final String DATE = "date"; + public static final String FINDER = "finder"; + public static final String ENCODED = "encoded"; + public static final String TRAVELBUGS = "travelbugs"; + public static final String TRAVELBUG = "travelbug"; + public static final String TEXT = "text"; + public static final String REF = "ref"; + + // 2011-12-03T10:15:30+01:00 + private final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'"); + + private final List listeners = new ArrayList<>(); + + private final Map userCache = new HashMap<>(); + + + @Override + public void addListener(ProgressListener listener) { + if (!listeners.contains(listener)) { + listeners.add(listener); + } + } + + @Override + public List load(File file) throws IOException { + fireEvent(new ProgressEvent("GPX Reader", + ProgressEvent.State.STARTED, + "Load File " + file.getName() + " started.")); + List modelList = new ArrayList<>(); + + long start = System.currentTimeMillis(); + XMLInputFactory factory = XMLInputFactory.newInstance(); + try (FileInputStream fis = new FileInputStream(file)) { + XMLStreamReader reader = factory.createXMLStreamReader(fis); + + Waypoint waypoint = null; + Cache cache = null; + String currentLevel = null; + String startTag; + StringBuffer tagContent = new StringBuffer(); + + while(reader.hasNext()) { + int event = reader.next(); + + switch (event) { + case XMLStreamConstants.START_ELEMENT: + + tagContent = new StringBuffer(); + startTag = reader.getLocalName(); + switch (startTag) { + case WPT: + currentLevel = WPT; + waypoint = new Waypoint(); + waypoint.setLatitude(Double.parseDouble(reader.getAttributeValue(0))); + waypoint.setLongitude(Double.parseDouble(reader.getAttributeValue(1))); + break; + case CACHE: + currentLevel = CACHE; + cache = new Cache(); + cache.setMainWayPoint(waypoint); + waypoint.setCache(cache); + cache.setId(Long.parseLong(reader.getAttributeValue(0))); + cache.setAvailable(Boolean.parseBoolean(reader.getAttributeValue(1))); + cache.setArchived(Boolean.parseBoolean(reader.getAttributeValue(2))); + modelList.add(cache); + break; + case LOG: + currentLevel = LOG; + break; + case ATTRIBUTE: + cache.getAttributes().add( + Attribute.groundspeakAttributeToAttribute( + Long.parseLong(reader.getAttributeValue(0)), + Boolean.parseBoolean(reader.getAttributeValue(1)))); + break; + case SHORT_DESCRIPTION: + cache.setShortDescriptionHtml(Boolean.parseBoolean(reader.getAttributeValue(0))); + break; + case LONG_DESCRIPTION: + cache.setLongDescriptionHtml(Boolean.parseBoolean(reader.getAttributeValue(0))); + break; + } + + break; + + case XMLStreamConstants.CHARACTERS: + tagContent.append(reader.getText().trim()); + break; + + case XMLStreamConstants.END_ELEMENT: + switch (reader.getLocalName()) { + case WPT: + currentLevel = null; + break; + case CACHE: + cache = null; + currentLevel = WPT; + break; + case LOG: + currentLevel = CACHE; + break; + case NAME: + if (WPT.equals(currentLevel)) { + waypoint.setName(tagContent.toString()); + } else if (CACHE.equals(currentLevel)) { + cache.setName(tagContent.toString()); + } + break; + case DESC: + if (WPT.equals(currentLevel)) { + waypoint.setDescription(tagContent.toString()); + } + break; + case URL: + waypoint.setUrl(tagContent.toString()); + break; + case URLNAME: + waypoint.setUrlName(tagContent.toString()); + break; + case SYM: + waypoint.setSymbol(tagContent.toString()); + break; + case TYPE: + if (CACHE.equals(currentLevel)) { + cache.setType(Type.groundspeakStringToType(tagContent.toString())); + } + break; + case PLACED_BY: + cache.setPlacedBy(tagContent.toString()); + break; + case OWNER: + break; + case CONTAINER: + cache.setContainer(Container.groundspeakStringToContainer(tagContent.toString())); + break; + case ATTRIBUTES: + // do nothing + break; + case DIFFICULTY: + cache.setDifficulty(tagContent.toString()); + break; + case TERRAIN: + cache.setTerrain(tagContent.toString()); + break; + case COUNTRY: + cache.setCountry(tagContent.toString()); + break; + case STATE: + cache.setState(tagContent.toString()); + break; + case SHORT_DESCRIPTION: + cache.setShortDescription(tagContent.toString()); + break; + case LONG_DESCRIPTION: + cache.setLongDescription(tagContent.toString()); + break; + case ENCODED_HINTS: + cache.setEncodedHints(tagContent.toString()); + break; + } + break; + } + } + } catch (Throwable e) { + e.printStackTrace(); + throw new IOException(e.getMessage(), e); + } + + long end = System.currentTimeMillis(); + LOGGER.info(modelList.size()+" Caches geladen in "+(end-start)+"ms"); + + fireEvent(new ProgressEvent("GPX Reader", + ProgressEvent.State.FINISHED, + "Load File " + file.getName() + " finished.")); + return modelList; + } + + private void fireEvent(ProgressEvent event) { + listeners.stream().forEach((l) -> { + l.progress(event); + }); + } +} diff --git a/src/main/java/de/geofroggerfx/model/Attribute.java b/src/main/java/de/geofroggerfx/model/Attribute.java new file mode 100644 index 0000000..0a6f17d --- /dev/null +++ b/src/main/java/de/geofroggerfx/model/Attribute.java @@ -0,0 +1,337 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.model; + +import java.util.ArrayList; +import java.util.List; + +/** + * @author Andreas Billmann + */ +public enum Attribute { + + // id:1 text:Dogs + DOGS_TRUE(1), + DOGS_FALSE(-1), + + // id:2 text:Access or parking fee + ACCESS_OR_PARKING_FEE_TRUE(2), + ACCESS_OR_PARKING_FEE_FALSE(-2), + + // id:3 text:Climbing gear + CLIMBING_GEAR_TRUE(3), + CLIMBING_GEAR_FALSE(-3), + + // id:4 text:Boat + BOAT_TRUE(4), + BOAT_FALSE(-4), + + // id:5 text:Scuba gear + SCUBA_GEAR_TRUE(5), + SCUBA_GEAR_FALSE(-5), + + // id:6 text:Recommended for kids + RECOMMENDED_FOR_KIDS_TRUE(6), + RECOMMENDED_FOR_KIDS_FALSE(-6), + + // id:7 text:Takes less than an hour + TAKES_LESS_THAN_AN_HOUR_TRUE(7), + TAKES_LESS_THAN_AN_HOUR_FALSE(-7), + + // id:8 text:Scenic view + SCENIC_VIEW_TRUE(8), + SCENIC_VIEW_FALSE(-8), + + // id:9 text:Significant Hike + SIGNIFICANT_HIKE_TRUE(9), + SIGNIFICANT_HIKE_FALSE(-9), + + // id:10 text:Difficult climbing + DIFFICULT_CLIMBING_TRUE(10), + DIFFICULT_CLIMBING_FALSE(-10), + + // id:11 text:May require wading + MAY_REQUIRE_WADING_TRUE(11), + MAY_REQUIRE_WADING_FALSE(-11), + + // id:12 text:May require swimming + MAY_REQUIRE_SWIMMING_TRUE(12), + MAY_REQUIRE_SWIMMING_FALSE(-12), + + // id:13 text:Available at all times + AVAILABLE_AT_ALL_TIMES_TRUE(13), + AVAILABLE_AT_ALL_TIMES_FALSE(-13), + + // id:14 text:Recommended at night + RECOMMENDED_AT_NIGHT_TRUE(14), + RECOMMENDED_AT_NIGHT_FALSE(-14), + + // id:15 text:Available during winter + AVAILABLE_DURING_WINTER_TRUE(15), + AVAILABLE_DURING_WINTER_FALSE(-15), + + // id:17 text:Poison plants + POISON_PLANTS_TRUE(17), + POISON_PLANTS_FALSE(-17), + + // id:18 text:Dangerous Animals + DANGEROUS_ANIMALS_TRUE(18), + DANGEROUS_ANIMALS_FALSE(-18), + + // id:19 text:Ticks + TICKS_TRUE(19), + TICKS_FALSE(-19), + + // id:20 text:Abandoned mines + ABANDONED_MINES_TRUE(20), + ABANDONED_MINES_FALSE(-20), + + // id:21 text:Cliff / falling rocks + CLIFF_FALLING_ROCKS_TRUE(21), + CLIFF_FALLING_ROCKS_FALSE(-21), + + // id:22 text:Hunting + HUNTING_TRUE(22), + HUNTING_FALSE(-22), + + // id:23 text:Dangerous area + DANGEROUS_AREA_TRUE(23), + DANGEROUS_AREA_FALSE(-23), + + // id:24 text:Wheelchair accessible + WHEELCHAIR_ACCESSIBLE_TRUE(24), + WHEELCHAIR_ACCESSIBLE_FALSE(-24), + + // id:25 text:Parking available + PARKING_AVAILABLE_TRUE(25), + PARKING_AVAILABLE_FALSE(-25), + + // id:26 text:Public transportation + PUBLIC_TRANSPORTATION_TRUE(26), + PUBLIC_TRANSPORTATION_FALSE(-26), + + // id:27 text:Drinking water nearby + DRINKING_WATER_NEARBY_TRUE(27), + DRINKING_WATER_NEARBY_FALSE(-27), + + // id:28 text:Public restrooms nearby + PUBLIC_RESTROOMS_NEARBY_TRUE(28), + PUBLIC_RESTROOMS_NEARBY_FALSE(-28), + + // id:29 text:Telephone nearby + TELEPHONE_NEARBY_TRUE(29), + TELEPHONE_NEARBY_FALSE(-29), + + // id:30 text:Picnic tables nearby + PICNIC_TABLES_NEARBY_TRUE(30), + PICNIC_TABLES_NEARBY_FALSE(-30), + + // id:31 text:Camping available + CAMPING_AVAILABLE_TRUE(31), + CAMPING_AVAILABLE_FALSE(-31), + + // id:32 text:Bicycles + BICYCLES_TRUE(32), + BICYCLES_FALSE(-32), + + // id:33 text:Motorcycles + MOTORCYCLES_TRUE(33), + MOTORCYCLES_FALSE(-33), + + // id:34 text:Quads + QUADS_TRUE(34), + QUADS_FALSE(-34), + + // id:35 text:Off-road vehicles + OFF_ROAD_VEHICLES_TRUE(35), + OFF_ROAD_VEHICLES_FALSE(-35), + + // id:36 text:Snowmobiles + SNOWMOBILES_TRUE(36), + SNOWMOBILES_FALSE(-36), + + // id:37 text:Horses + HORSES_TRUE(37), + HORSES_FALSE(-37), + + // id:38 text:Campfires + CAMPFIRES_TRUE(38), + CAMPFIRES_FALSE(-38), + + // id:39 text:Thorns + THORNS_TRUE(39), + THORNS_FALSE(-39), + + // id:40 text:Stealth required + STEALTH_REQUIRED_TRUE(40), + STEALTH_REQUIRED_FALSE(-40), + + // id:41 text:Stroller accessible + STROLLER_ACCESSIBLE_TRUE(41), + STROLLER_ACCESSIBLE_FALSE(-41), + + // id:43 text:Watch for livestock + WATCH_FOR_LIVESTOCK_TRUE(43), + WATCH_FOR_LIVESTOCK_FALSE(-43), + + // id:42 text:Needs maintenance + NEEDS_MAINTENANCE_TRUE(42), + NEEDS_MAINTENANCE_FALSE(-42), + + // id:44 text:Flashlight required + FLASHLIGHT_REQUIRED_TRUE(44), + FLASHLIGHT_REQUIRED_FALSE(-44), + + // id:45 text:Lost and Found Tour + LOST_AND_FOUND_TOUR_TRUE(45), + LOST_AND_FOUND_TOUR_FALSE(-45), + + // id:46 text:Truck Driver/RV + TRUCK_DRIVER_RV_TRUE(46), + TRUCK_DRIVER_RV_FALSE(-46), + + // id:47 text:Field Puzzle + FIELD_PUZZLE_TRUE(47), + FIELD_PUZZLE_FALSE(-47), + + // id:48 text:UV Light Required + UV_LIGHT_REQUIRED_TRUE(48), + UV_LIGHT_REQUIRED_FALSE(-48), + + // id:49 text:Snowshoes + SNOWSHOES_TRUE(49), + SNOWSHOES_FALSE(-49), + + // id:50 text:Cross Country Skis + CROSS_COUNTRY_SKIS_TRUE(50), + CROSS_COUNTRY_SKIS_FALSE(-50), + + // id:51 text:Special Tool Required + SPECIAL_TOOL_REQUIRED_TRUE(51), + SPECIAL_TOOL_REQUIRED_FALSE(-51), + + // id:52 text:Night Cache + NIGHT_CACHE_TRUE(52), + NIGHT_CACHE_FALSE(-52), + + // id:53 text:Park and Grab + PARK_AND_GRAB_TRUE(53), + PARK_AND_GRAB_FALSE(-53), + + // id:54 text:Abandoned Structure + ABANDONED_STRUCTURE_TRUE(54), + ABANDONED_STRUCTURE_FALSE(-54), + + // id:55 text:Short hike (less than 1km) + SHORT_HIKE_LESS_THAN_1KM_TRUE(55), + SHORT_HIKE_LESS_THAN_1KM_FALSE(-55), + + // id:56 text:Medium hike (1km-10km) + MEDIUM_HIKE_1KM_10KM_TRUE(56), + MEDIUM_HIKE_1KM_10KM_FALSE(-56), + + // id:57 text:Long Hike (+10km) + LONG_HIKE_10KM_TRUE(57), + LONG_HIKE_10KM_FALSE(-57), + + // id:58 text:Fuel Nearby + FUEL_NEARBY_TRUE(58), + FUEL_NEARBY_FALSE(-58), + + // id:59 text:Food Nearby + FOOD_NEARBY_TRUE(59), + FOOD_NEARBY_FALSE(-59), + + // id:60 text:Wireless Beacon + WIRELESS_BEACON_TRUE(60), + WIRELESS_BEACON_FALSE(-60), + + // id:61 text:Partnership cache + PARTNERSHIP_CACHE_TRUE(61), + PARTNERSHIP_CACHE_FALSE(-61), + + // id:62 text:Seasonal Access + SEASONAL_ACCESS_TRUE(62), + SEASONAL_ACCESS_FALSE(-62), + + // id:63 text:Tourist Friendly + TOURIST_FRIENDLY_TRUE(63), + TOURIST_FRIENDLY_FALSE(-63), + + // id:64 text:Tree Climbing + TREE_CLIMBING_TRUE(64), + TREE_CLIMBING_FALSE(-64), + + // id:65 text:Front Yard (Private Residence) + FRONT_YARD_PRIVATE_RESIDENCE_TRUE(65), + FRONT_YARD_PRIVATE_RESIDENCE_FALSE(-65), + + // id:66 text:Teamwork Required + TEAMWORK_REQUIRED_TRUE(66), + TEAMWORK_REQUIRED_FALSE(-66), + + // id:67 text:geotour + GEOTOUR_TRUE(67), + GEOTOUR_FALSE(-67); + + + private final static List attributes = new ArrayList<>(); + + private int id; + + private Attribute(int id) { + this.id = id; + } + + public int getId() { + return id; + } + + public void setId(int id) { + this.id = id; + } + + public static Attribute groundspeakAttributeToAttribute(Long id, boolean inc) { + + int idToCompare = id.intValue(); + + if (!inc) { + idToCompare = -idToCompare; + } + + for (Attribute t : Attribute.values()) { + if (t.getId() == idToCompare) { + return t; + } + } + + if (!attributes.contains(id)) { + attributes.add(id); + } + + throw new IllegalArgumentException("unknown attribute id:" + id + " inc:" + inc); + } +} diff --git a/src/main/java/de/geofroggerfx/model/Cache.java b/src/main/java/de/geofroggerfx/model/Cache.java new file mode 100644 index 0000000..a80fcfc --- /dev/null +++ b/src/main/java/de/geofroggerfx/model/Cache.java @@ -0,0 +1,317 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.model; + +import javafx.beans.property.*; +import javafx.collections.FXCollections; +import javafx.collections.ObservableList; + +public class Cache { + private LongProperty id = new SimpleLongProperty(); + private BooleanProperty available = new SimpleBooleanProperty(); + private BooleanProperty archived = new SimpleBooleanProperty(); + private BooleanProperty found = new SimpleBooleanProperty(); + private StringProperty name = new SimpleStringProperty(); + private StringProperty placedBy = new SimpleStringProperty(); + private ObjectProperty owner = new SimpleObjectProperty<>(); + private ObjectProperty type = new SimpleObjectProperty<>(); + private ObjectProperty container = new SimpleObjectProperty<>(); + private ObjectProperty> attributes = new SimpleObjectProperty<>(FXCollections.observableArrayList()); + private StringProperty difficulty = new SimpleStringProperty(); + private StringProperty terrain = new SimpleStringProperty(); + private StringProperty country = new SimpleStringProperty(); + private StringProperty state = new SimpleStringProperty(); + private StringProperty shortDescription = new SimpleStringProperty(); + private BooleanProperty shortDescriptionHtml = new SimpleBooleanProperty(); + private StringProperty longDescription = new SimpleStringProperty(); + private BooleanProperty longDescriptionHtml = new SimpleBooleanProperty(); + private StringProperty encodedHints = new SimpleStringProperty(); + private ObjectProperty mainWayPoint = new SimpleObjectProperty<>(); + + public long getId() { + return id.get(); + } + + public LongProperty idProperty() { + return id; + } + + public void setId(long id) { + this.id.set(id); + } + + public boolean getAvailable() { + return available.get(); + } + + public BooleanProperty availableProperty() { + return available; + } + + public void setAvailable(boolean available) { + this.available.set(available); + } + + public boolean getArchived() { + return archived.get(); + } + + public BooleanProperty archivedProperty() { + return archived; + } + + public void setArchived(boolean archived) { + this.archived.set(archived); + } + + public boolean getFound() { + return found.get(); + } + + public BooleanProperty foundProperty() { + return found; + } + + public void setFound(boolean found) { + this.found.set(found); + } + + public String getName() { + return name.get(); + } + + public StringProperty nameProperty() { + return name; + } + + public void setName(String name) { + this.name.set(name); + } + + public String getPlacedBy() { + return placedBy.get(); + } + + public StringProperty placedByProperty() { + return placedBy; + } + + public void setPlacedBy(String placedBy) { + this.placedBy.set(placedBy); + } + + public User getOwner() { + return owner.get(); + } + + public ObjectProperty ownerProperty() { + return owner; + } + + public void setOwner(User owner) { + this.owner.set(owner); + } + + public Type getType() { + return type.get(); + } + + public ObjectProperty typeProperty() { + return type; + } + + public void setType(Type type) { + this.type.set(type); + } + + public Container getContainer() { + return container.get(); + } + + public ObjectProperty containerProperty() { + return container; + } + + public void setContainer(Container container) { + this.container.set(container); + } + + public ObservableList getAttributes() { + return attributes.get(); + } + + public ObjectProperty> attributesProperty() { + return attributes; + } + + public void setAttributes(ObservableList attributes) { + this.attributes.set(attributes); + } + + public String getDifficulty() { + return difficulty.get(); + } + + public StringProperty difficultyProperty() { + return difficulty; + } + + public void setDifficulty(String difficulty) { + this.difficulty.set(difficulty); + } + + public String getTerrain() { + return terrain.get(); + } + + public StringProperty terrainProperty() { + return terrain; + } + + public void setTerrain(String terrain) { + this.terrain.set(terrain); + } + + public String getCountry() { + return country.get(); + } + + public StringProperty countryProperty() { + return country; + } + + public void setCountry(String country) { + this.country.set(country); + } + + public String getState() { + return state.get(); + } + + public StringProperty stateProperty() { + return state; + } + + public void setState(String state) { + this.state.set(state); + } + + public String getShortDescription() { + return shortDescription.get(); + } + + public StringProperty shortDescriptionProperty() { + return shortDescription; + } + + public void setShortDescription(String shortDescription) { + this.shortDescription.set(shortDescription); + } + + public boolean getShortDescriptionHtml() { + return shortDescriptionHtml.get(); + } + + public BooleanProperty shortDescriptionHtmlProperty() { + return shortDescriptionHtml; + } + + public void setShortDescriptionHtml(boolean shortDescriptionHtml) { + this.shortDescriptionHtml.set(shortDescriptionHtml); + } + + public String getLongDescription() { + return longDescription.get(); + } + + public StringProperty longDescriptionProperty() { + return longDescription; + } + + public void setLongDescription(String longDescription) { + this.longDescription.set(longDescription); + } + + public boolean getLongDescriptionHtml() { + return longDescriptionHtml.get(); + } + + public BooleanProperty longDescriptionHtmlProperty() { + return longDescriptionHtml; + } + + public void setLongDescriptionHtml(boolean longDescriptionHtml) { + this.longDescriptionHtml.set(longDescriptionHtml); + } + + public String getEncodedHints() { + return encodedHints.get(); + } + + public StringProperty encodedHintsProperty() { + return encodedHints; + } + + public void setEncodedHints(String encodedHints) { + this.encodedHints.set(encodedHints); + } + + public Waypoint getMainWayPoint() { + return mainWayPoint.get(); + } + + public ObjectProperty mainWayPointProperty() { + return mainWayPoint; + } + + public void setMainWayPoint(Waypoint mainWayPoint) { + this.mainWayPoint.set(mainWayPoint); + } + + @Override + public String toString() { + return "Cache{" + + "name=" + name + + '}'; + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + + Cache cache = (Cache) o; + + if (id != null ? !id.equals(cache.id) : cache.id != null) return false; + + return true; + } + + @Override + public int hashCode() { + return id != null ? id.hashCode() : 0; + } +} diff --git a/src/main/java/de/geofroggerfx/model/CacheListEntry.java b/src/main/java/de/geofroggerfx/model/CacheListEntry.java new file mode 100644 index 0000000..cd17648 --- /dev/null +++ b/src/main/java/de/geofroggerfx/model/CacheListEntry.java @@ -0,0 +1,110 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.model; + +import javafx.beans.property.*; + +/** + * Created by Andreas on 10.03.2015. + */ +public class CacheListEntry { + + private LongProperty id = new SimpleLongProperty(); + private StringProperty name = new SimpleStringProperty(); + private StringProperty difficulty = new SimpleStringProperty(); + private StringProperty terrain = new SimpleStringProperty(); + private StringProperty code = new SimpleStringProperty(); + private ObjectProperty type = new SimpleObjectProperty<>(); + + public CacheListEntry(long id, + String name, + String code, + String difficulty, + String terrain, + Type type) { + this.id.setValue(id); + this.name.setValue(name); + this.code.setValue(code); + this.difficulty.setValue(difficulty); + this.terrain.setValue(terrain); + this.type.setValue(type); + } + + public String getName() { + return name.get(); + } + + public ReadOnlyStringProperty nameProperty() { + return name; + } + + public String getCode() { + return code.get(); + } + + public ReadOnlyStringProperty codeProperty() { + return code; + } + + public long getId() { + return id.get(); + } + + public ReadOnlyLongProperty idProperty() { + return id; + } + + public String getDifficulty() { + return difficulty.get(); + } + + public ReadOnlyStringProperty difficultyProperty() { + return difficulty; + } + + public String getTerrain() { + return terrain.get(); + } + + public ReadOnlyStringProperty terrainProperty() { + return terrain; + } + + public Type getType() { + return type.get(); + } + + public ReadOnlyObjectProperty typeProperty() { + return type; + } + + @Override + public String toString() { + return "CacheListEntry{" + + "name=" + name + + '}'; + } +} diff --git a/src/main/java/de/geofroggerfx/model/Container.java b/src/main/java/de/geofroggerfx/model/Container.java new file mode 100644 index 0000000..b797213 --- /dev/null +++ b/src/main/java/de/geofroggerfx/model/Container.java @@ -0,0 +1,64 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.model; + +import groovy.lang.Closure; +import org.codehaus.groovy.runtime.DefaultGroovyMethods; + +/** + * Created by Andreas Billmann on 22.02.2015. + */ +public enum Container { + SMALL("Small"), + MICRO("Micro"), + REGULAR("Regular"), + OTHER("Other"), + NOT_CHOSEN("Not chosen"), + LARGE("Large"), + VIRTUAL("Virtual"); + + + private int id; + private String groundspeakString; + + private Container(String groundspeakString) { + this.groundspeakString = groundspeakString; + } + + public String toGroundspeakString() { + return groundspeakString; + } + + public static Container groundspeakStringToContainer(String groundspeakString) { + for (Container t : Container.values()) { + if (t.toGroundspeakString().equals(groundspeakString)) { + return t; + } + } + throw new IllegalArgumentException("unknown container:" + groundspeakString); + } + +} diff --git a/src/main/java/de/geofroggerfx/model/Type.java b/src/main/java/de/geofroggerfx/model/Type.java new file mode 100644 index 0000000..13329bd --- /dev/null +++ b/src/main/java/de/geofroggerfx/model/Type.java @@ -0,0 +1,68 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.model; + +import groovy.lang.Closure; +import org.codehaus.groovy.runtime.DefaultGroovyMethods; + +/** + * Created by Andreas Billmann on 22.02.2015. + */ +public enum Type { + TRADITIONAL_CACHE("Traditional Cache"), + MULTI_CACHE("Multi-cache"), + UNKNOWN_CACHE("Unknown Cache"), + EARTH_CACHE("Earthcache"), + LETTERBOX("Letterbox Hybrid"), + EVENT("Event Cache"), + WHERIGO("Wherigo Cache"), + WEBCAM_CACHE("Webcam Cache"), + VIRTUAL_CACHE("Virtual Cache"), + CITO_EVENT("Cache In Trash Out Event"), + MEGA_EVENT("Mega-Event Cache"), + MYSTERY_CACHE("Mystery Cache"); + + private int id; + private String groundspeakString; + + private Type(String groundspeakString) { + this.groundspeakString = groundspeakString; + } + + public String toGroundspeakString() { + return groundspeakString; + } + + public static Type groundspeakStringToType(String groundspeakString) { + for (Type t : Type.values()) { + if (t.toGroundspeakString().equals(groundspeakString)) { + return t; + } + } + throw new IllegalArgumentException("unknown type:" + groundspeakString); + } + +} diff --git a/src/main/java/de/geofroggerfx/model/User.java b/src/main/java/de/geofroggerfx/model/User.java new file mode 100644 index 0000000..47ed431 --- /dev/null +++ b/src/main/java/de/geofroggerfx/model/User.java @@ -0,0 +1,63 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.model; + +import javafx.beans.property.LongProperty; +import javafx.beans.property.SimpleLongProperty; +import javafx.beans.property.SimpleStringProperty; +import javafx.beans.property.StringProperty; + +/** + * Created by Andreas Billmann on 22.02.2015. + */ +public class User { + private LongProperty id = new SimpleLongProperty(); + private StringProperty name = new SimpleStringProperty(); + + public long getId() { + return id.get(); + } + + public LongProperty idProperty() { + return id; + } + + public void setId(long id) { + this.id.set(id); + } + + public String getName() { + return name.get(); + } + + public StringProperty nameProperty() { + return name; + } + + public void setName(String name) { + this.name.set(name); + } +} diff --git a/src/main/java/de/geofroggerfx/model/Waypoint.java b/src/main/java/de/geofroggerfx/model/Waypoint.java new file mode 100644 index 0000000..1c628ac --- /dev/null +++ b/src/main/java/de/geofroggerfx/model/Waypoint.java @@ -0,0 +1,166 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.model; + +import javafx.beans.property.*; + +import java.util.Date; + +/** + * Created by Andreas Billmann on 22.02.2015. + */ +public class Waypoint { + private ObjectProperty cache = new SimpleObjectProperty<>(); + private DoubleProperty latitude = new SimpleDoubleProperty(); + private DoubleProperty longitude = new SimpleDoubleProperty(); + private StringProperty name = new SimpleStringProperty(); + private ObjectProperty time = new SimpleObjectProperty<>(); + private StringProperty description = new SimpleStringProperty(); + private StringProperty url = new SimpleStringProperty(); + private StringProperty urlName = new SimpleStringProperty(); + private StringProperty symbol = new SimpleStringProperty(); + private ObjectProperty type = new SimpleObjectProperty<>(); + + public Cache getCache() { + return cache.get(); + } + + public ObjectProperty cacheProperty() { + return cache; + } + + public void setCache(Cache cache) { + this.cache.set(cache); + } + + public double getLatitude() { + return latitude.get(); + } + + public DoubleProperty latitudeProperty() { + return latitude; + } + + public void setLatitude(double latitude) { + this.latitude.set(latitude); + } + + public double getLongitude() { + return longitude.get(); + } + + public DoubleProperty longitudeProperty() { + return longitude; + } + + public void setLongitude(double longitude) { + this.longitude.set(longitude); + } + + public String getName() { + return name.get(); + } + + public StringProperty nameProperty() { + return name; + } + + public void setName(String name) { + this.name.set(name); + } + + public Date getTime() { + return time.get(); + } + + public ObjectProperty timeProperty() { + return time; + } + + public void setTime(Date time) { + this.time.set(time); + } + + public String getDescription() { + return description.get(); + } + + public StringProperty descriptionProperty() { + return description; + } + + public void setDescription(String description) { + this.description.set(description); + } + + public String getUrl() { + return url.get(); + } + + public StringProperty urlProperty() { + return url; + } + + public void setUrl(String url) { + this.url.set(url); + } + + public String getUrlName() { + return urlName.get(); + } + + public StringProperty urlNameProperty() { + return urlName; + } + + public void setUrlName(String urlName) { + this.urlName.set(urlName); + } + + public String getSymbol() { + return symbol.get(); + } + + public StringProperty symbolProperty() { + return symbol; + } + + public void setSymbol(String symbol) { + this.symbol.set(symbol); + } + + public WaypointType getType() { + return type.get(); + } + + public ObjectProperty typeProperty() { + return type; + } + + public void setType(WaypointType type) { + this.type.set(type); + } +} diff --git a/src/main/java/de/geofroggerfx/model/WaypointType.java b/src/main/java/de/geofroggerfx/model/WaypointType.java new file mode 100644 index 0000000..c304536 --- /dev/null +++ b/src/main/java/de/geofroggerfx/model/WaypointType.java @@ -0,0 +1,33 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.model; + +/** + * Created by Andreas Billmann on 22.02.2015. + */ +public enum WaypointType { + +} diff --git a/src/main/java/de/geofroggerfx/plugins/Plugin.java b/src/main/java/de/geofroggerfx/plugins/Plugin.java new file mode 100644 index 0000000..93751ef --- /dev/null +++ b/src/main/java/de/geofroggerfx/plugins/Plugin.java @@ -0,0 +1,31 @@ +package de.geofroggerfx.plugins; + +import java.util.Map; + +/** + * This interface defines the method a plugin has to provide to be called correctly + * + * @author abi + */ +public interface Plugin { + + /** + * @return name + */ + String getName(); + + /** + * @return version + */ + String getVersion(); + + /** + * Run the main method of the plugin. All the logic is done in this method. + * Every run method will get a context map, with all the services inside, + * to use them. + * + * @param context services and data + */ + void run(Map context); + +} diff --git a/src/main/java/de/geofroggerfx/service/CacheService.java b/src/main/java/de/geofroggerfx/service/CacheService.java new file mode 100644 index 0000000..d6b8a80 --- /dev/null +++ b/src/main/java/de/geofroggerfx/service/CacheService.java @@ -0,0 +1,47 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.service; + +import de.geofroggerfx.model.Cache; +import de.geofroggerfx.model.CacheListEntry; + +import java.util.List; + +/** + * Created by Andreas on 10.03.2015. + */ + +public interface CacheService { + + + void storeCaches(List cacheList); + + List getAllCacheEntriesSortBy(String name, String asc); + + Cache getCacheForId(long id); + + List getAllCaches(); +} diff --git a/src/main/java/de/geofroggerfx/service/CacheServiceImpl.java b/src/main/java/de/geofroggerfx/service/CacheServiceImpl.java new file mode 100644 index 0000000..a675b72 --- /dev/null +++ b/src/main/java/de/geofroggerfx/service/CacheServiceImpl.java @@ -0,0 +1,66 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.service; + +import de.geofroggerfx.dao.CacheDAO; +import de.geofroggerfx.model.Cache; +import de.geofroggerfx.model.CacheListEntry; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +import java.util.List; + +/** + * Created by Andreas on 10.03.2015. + */ +@Service +public class CacheServiceImpl implements CacheService { + + @Autowired + private CacheDAO cacheDAO; + + @Override + public void storeCaches(List cacheList) { + cacheDAO.save(cacheList); + } + + @Override + public List getAllCacheEntriesSortBy(String name, String asc) { + return cacheDAO.getAllCachEntriesSortBy(name, asc); + } + + @Override + public Cache getCacheForId(long id) { + return cacheDAO.getCacheForId(id); + } + + @Override + public List getAllCaches() { + return cacheDAO.getAllCaches(); + } + + +} diff --git a/src/main/java/de/geofroggerfx/service/PluginService.java b/src/main/java/de/geofroggerfx/service/PluginService.java new file mode 100644 index 0000000..6931bc6 --- /dev/null +++ b/src/main/java/de/geofroggerfx/service/PluginService.java @@ -0,0 +1,19 @@ +package de.geofroggerfx.service; + +import de.geofroggerfx.plugins.Plugin; + +import java.util.List; + +/** + * TODO: class description + * + * @author abi + */ +public interface PluginService { + + List getAllPlugins(); + + void executePlugin(Plugin plugin); + + +} diff --git a/src/main/java/de/geofroggerfx/service/PluginServiceImpl.java b/src/main/java/de/geofroggerfx/service/PluginServiceImpl.java new file mode 100644 index 0000000..4b966b4 --- /dev/null +++ b/src/main/java/de/geofroggerfx/service/PluginServiceImpl.java @@ -0,0 +1,79 @@ +package de.geofroggerfx.service; + +import de.geofroggerfx.application.SessionContext; +import de.geofroggerfx.dao.jdbc.DataConfig; +import de.geofroggerfx.plugins.Plugin; +import groovy.lang.GroovyClassLoader; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.jdbc.core.JdbcTemplate; +import org.springframework.stereotype.Service; + +import java.io.File; +import java.io.IOException; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +/** + * This service find, load and executes plugins based on the plugin interface. + * + * @author abi + */ +@Service +public class PluginServiceImpl implements PluginService { + + private final GroovyClassLoader gcl = new GroovyClassLoader(); + + @Autowired + private CacheService cacheService; + + @Autowired + private SessionContext sessionContext; + + private JdbcTemplate jdbcTemplate; + + @Autowired + public void setDataConfig(DataConfig dataConfig) { + this.jdbcTemplate = new JdbcTemplate(dataConfig.dataSource()); + } + + + @Override + public List getAllPlugins() { + + List plugins = new ArrayList<>(); + + try { + File file = new File("./plugins"); + if (!file.exists()) { + throw new IllegalArgumentException("plugins folder does not exist"); + } + + File[] pluginFiles = file.listFiles((dir, name) -> name.endsWith("Plugin.groovy")); + for (File pluginFile : pluginFiles) { + Class clazz = gcl.parseClass(pluginFile); + for (Class interf : clazz.getInterfaces()) { + if (interf.equals(Plugin.class)) { + plugins.add((Plugin) clazz.newInstance()); + break; + } + } + } + + } catch (IOException | InstantiationException | IllegalAccessException e) { + e.printStackTrace(); + } + + return plugins; + } + + @Override + public void executePlugin(final Plugin plugin) { + Map context = new HashMap<>(); + context.put("sessionContext", sessionContext); + context.put("cacheService", cacheService); + context.put("jdbcTemplate", jdbcTemplate); + plugin.run(context); + } +} diff --git a/src/main/java/de/geofroggerfx/ui/FXMLController.java b/src/main/java/de/geofroggerfx/ui/FXMLController.java new file mode 100644 index 0000000..337a9d1 --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/FXMLController.java @@ -0,0 +1,70 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui; + +import javafx.fxml.FXMLLoader; +import javafx.fxml.Initializable; +import javafx.scene.Node; +import org.springframework.beans.factory.InitializingBean; +import org.springframework.beans.factory.annotation.Value; + +import java.io.IOException; +import java.io.InputStream; +import java.util.ResourceBundle; + +public abstract class FXMLController implements InitializingBean, Initializable { + + protected Node view; + protected String fxmlFilePath; + protected String resourcePath; + + public abstract void setFxmlFilePath(String filePath); + + @Value("${resource.main}") + public void setResourceBundle(String resourcePath) { + this.resourcePath = resourcePath; + } + + @Override + public void afterPropertiesSet() throws Exception { + loadFXML(); + } + + protected final void loadFXML() throws IOException { + try (InputStream fxmlStream = getClass().getResourceAsStream(fxmlFilePath)) { + FXMLLoader loader = new FXMLLoader(); + loader.setResources(ResourceBundle.getBundle(this.resourcePath)); + loader.setController(this); + this.view = (loader.load(fxmlStream)); + } catch (Throwable t) { + t.printStackTrace(); + } + } + + public Node getView() { + return view; + } +} \ No newline at end of file diff --git a/src/main/java/de/geofroggerfx/ui/GeoFroggerFX.java b/src/main/java/de/geofroggerfx/ui/GeoFroggerFX.java new file mode 100644 index 0000000..64f53f7 --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/GeoFroggerFX.java @@ -0,0 +1,98 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui; + +import javafx.application.Application; +import javafx.event.EventHandler; +import javafx.scene.Parent; +import javafx.scene.Scene; +import javafx.scene.input.KeyCode; +import javafx.scene.input.KeyEvent; +import javafx.scene.text.Font; +import javafx.stage.Stage; +//import org.scenicview.ScenicView; +import org.springframework.context.annotation.*; +import org.springframework.context.support.PropertySourcesPlaceholderConfigurer; + +@Configuration +@ComponentScan("de.geofroggerfx") +@PropertySource(value = "classpath:/de/geofroggerfx/ui/application.properties") +public class GeoFroggerFX extends Application { + + private AnnotationConfigApplicationContext appContext; + + @Override + public void start(Stage primaryStage) throws Exception { + + loadCustomFonts(); + + appContext = new AnnotationConfigApplicationContext(GeoFroggerFX.class); + String name = appContext.getEnvironment().getProperty("application.name"); + String version = appContext.getEnvironment().getProperty("application.version"); + GeoFroggerFXController geoFroggerFXController = appContext.getBean(GeoFroggerFXController.class); + + Scene scene = new Scene((Parent) geoFroggerFXController.getView()); + + scene.setOnKeyPressed(new EventHandler() { + + @Override + public void handle(KeyEvent event) { + if (isScenicViewShortcutPressed(event)) { +// ScenicView.show(scene); + } + } + }); + primaryStage.setScene(scene); + primaryStage.setTitle(String.format("%s %s", name, version)); + primaryStage.show(); + } + + @Bean + public static PropertySourcesPlaceholderConfigurer placeholderConfigurer() { + return new PropertySourcesPlaceholderConfigurer(); + } + + @Override + public void stop() throws Exception { + if (appContext != null) { + appContext.close(); + } + + super.stop(); + } + + public static void main(String[] args) { + launch(args); + } + + private static boolean isScenicViewShortcutPressed(final KeyEvent keyEvent) { + return keyEvent.isAltDown() && keyEvent.isControlDown() && keyEvent.getCode().equals(KeyCode.V); + } + + private void loadCustomFonts() { + Font.loadFont(GeoFroggerFX.class.getResource("/fonts/sofia/Sofia-Regular.otf").toExternalForm(), 24); + } +} diff --git a/src/main/java/de/geofroggerfx/ui/GeoFroggerFXController.java b/src/main/java/de/geofroggerfx/ui/GeoFroggerFXController.java new file mode 100644 index 0000000..9c024c7 --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/GeoFroggerFXController.java @@ -0,0 +1,283 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui; + +import de.geofroggerfx.application.ProgressEvent; +import de.geofroggerfx.application.SessionContext; +import de.geofroggerfx.gpx.GPXReader; +import de.geofroggerfx.model.Cache; +import de.geofroggerfx.model.CacheListEntry; +import de.geofroggerfx.plugins.Plugin; +import de.geofroggerfx.service.CacheService; +import de.geofroggerfx.service.PluginService; +import de.geofroggerfx.ui.details.DetailsController; +import de.geofroggerfx.ui.list.ListController; +import javafx.application.Platform; +import javafx.beans.property.ObjectProperty; +import javafx.beans.property.SimpleObjectProperty; +import javafx.concurrent.Service; +import javafx.concurrent.Task; +import javafx.event.ActionEvent; +import javafx.fxml.FXML; +import javafx.scene.control.*; +import javafx.scene.layout.AnchorPane; +import javafx.scene.layout.BorderPane; +import javafx.scene.layout.HBox; +import javafx.scene.layout.Pane; +import javafx.stage.FileChooser; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.stereotype.Component; + +import java.io.File; +import java.io.IOException; +import java.net.URL; +import java.util.List; +import java.util.ResourceBundle; +import java.util.logging.Level; +import java.util.logging.Logger; + +import static de.geofroggerfx.application.SessionContext.*; + +/** + * Created by Andreas on 09.03.2015. + */ +@Component +public class GeoFroggerFXController extends FXMLController { + + private static final Logger LOGGER = Logger.getLogger(GeoFroggerFXController.class.getName()); + + @Autowired + private CacheService cacheService; + + @Autowired + private SessionContext sessionContext; + + @Autowired + private ListController listController; + + @Autowired + private DetailsController detailsController; + + @Autowired + private PluginService pluginService; + + @Autowired + private GPXReader reader; + + @FXML + private HBox cacheListContent; + + @FXML + private AnchorPane cacheDetailsContent; + + @FXML + private Label leftStatus; + + @FXML + private ProgressBar progress; + + @FXML + private Menu pluginsMenu; + + private ResourceBundle resourceBundle; + + private final LoadCachesFromFileService loadService = new LoadCachesFromFileService(); + private final LoadCacheListsFromDatabaseService loadListsFromDBService = new LoadCacheListsFromDatabaseService(); + + @Value("${fxml.geofrogger.view}") + @Override + public void setFxmlFilePath(String filePath) { + this.fxmlFilePath = filePath; + } + + @Override + public void initialize(URL location, ResourceBundle resources) { + this.resourceBundle = resources; + + LOGGER.info("load all sub controller"); + cacheListContent.getChildren().add(listController.getView()); + cacheDetailsContent.getChildren().add(detailsController.getView()); + + LOGGER.info("add listeners"); + reader.addListener((ProgressEvent event) -> updateStatus(event.getMessage(), event.getProgress())); + + loadListsFromDBService.start(); + + List plugins = pluginService.getAllPlugins(); + for (Plugin plugin: plugins) { + MenuItem menuItem = new MenuItem(plugin.getName()+" ("+plugin.getVersion()+")"); + menuItem.setOnAction(actionEvent -> pluginService.executePlugin(plugin)); + pluginsMenu.getItems().add(menuItem); + } + + } + + + @FXML + public void importGpx(ActionEvent actionEvent) { + final FileChooser fileChooser = new FileChooser(); + + //Set extension filter + final FileChooser.ExtensionFilter extFilter = new FileChooser.ExtensionFilter("GPX files (*.gpx)", "*.gpx"); + fileChooser.getExtensionFilters().add(extFilter); + + //Show open file dialog + final File file = fileChooser.showOpenDialog(null); + loadService.setFile(file); + loadService.restart(); + } + + @FXML + public void showAboutDialog(ActionEvent actionEvent) { +// Dialog dialog = new Dialog(null, resourceBundle.getString("dialog.title.about")); +// dialog.setMasthead(MASTHEAD_TEXT); +// dialog.setContent(ABOUT_TEXT); +// dialog.setExpandableContent(new TextArea(LICENSE)); +// dialog.show(); + } + + @FXML + public void showSettings(ActionEvent actionEvent) { +// mainPane.setCenter(); + +// FXMLLoader.load() + } + + @FXML + public void newList(ActionEvent actionEvent) { +// final Optional listNameOption = Dialogs. +// create(). +// title(resourceBundle.getString("dialog.title.new_list")). +// message(resourceBundle.getString("dialog.label.listname")). +// showTextInput(); +// if (hasValue(listNameOption)) { +// final String listName = listNameOption.get().trim(); +// if (cacheService.doesCacheListNameExist(listName)) { +// Dialogs. +// create(). +// message(resourceBundle.getString("dialog.msg.list.does.exist")). +// showError(); +// } else { +// CacheList list = new CacheList(); +// list.setName(listName); +// cacheService.storeCacheList(list); +// setCacheListInContext(); +// } +// } + } + + @FXML + public void deleteList(ActionEvent actionEvent) { +// final Optional listOption = Dialogs. +// create(). +// title("dialog.title.delete_list"). +// message("dialog.label.listname"). +// showChoices(cacheService.getAllCacheLists()); +// +// if (listOption.isPresent()) { +// cacheService.deleteCacheList(listOption.get()); +// setCacheListInContext(); +// } + } + + @FXML + public void exit(ActionEvent actionEvent) { + Platform.exit(); + } + + private void updateStatus(String text, double progressValue) { + Platform.runLater(() -> { + leftStatus.setText(text); + progress.setProgress(progressValue); + }); + } + + + private class LoadCachesFromFileService extends Service { + + private final ObjectProperty file = new SimpleObjectProperty(); + + public final void setFile(File value) { + file.set(value); + } + + public final File getFile() { + return file.get(); + } + + public final ObjectProperty fileProperty() { + return file; + } + + @Override + protected Task createTask() { + return new Task() { + @Override + protected Void call() throws Exception { + try { + LOGGER.info("load from file "+file.get().getAbsolutePath()); + final List cacheList = reader.load(file.get()); + LOGGER.info(cacheList.size()+" caches loaded"); + if (!cacheList.isEmpty()) { + updateStatus(resourceBundle.getString("status.store.all.caches"), ProgressIndicator.INDETERMINATE_PROGRESS); + cacheService.storeCaches(cacheList); + updateStatus(resourceBundle.getString("status.all.caches.stored"), 0); + LOGGER.info("caches stored in database"); + + loadAllCacheEntries(); + } + } catch (IOException ex) { + LOGGER.log(Level.SEVERE, ex.getMessage() ,ex); + } + return null; + } + }; + } + + } + + private class LoadCacheListsFromDatabaseService extends Service { + + @Override + protected Task createTask() { + return new Task() { + @Override + protected Void call() throws Exception { + loadAllCacheEntries(); + return null; + } + }; + } + + } + + private void loadAllCacheEntries() { + updateStatus(resourceBundle.getString("status.load.caches.from.db"), ProgressIndicator.INDETERMINATE_PROGRESS); + sessionContext.setData(CACHE_ENTRY_LIST, cacheService.getAllCacheEntriesSortBy("name", "asc")); + updateStatus(resourceBundle.getString("status.all.caches.loaded"), 0); + } +} diff --git a/src/main/java/de/geofroggerfx/ui/GeocachingIcons.java b/src/main/java/de/geofroggerfx/ui/GeocachingIcons.java new file mode 100644 index 0000000..4c604b6 --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/GeocachingIcons.java @@ -0,0 +1,334 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui; + +import de.geofroggerfx.model.Attribute; +import de.geofroggerfx.model.Type; +import de.jensd.fx.glyphs.GlyphIcon; +import de.jensd.fx.glyphs.GlyphIcons; +import de.jensd.fx.glyphs.fontawesome.FontAwesomeIcons; +import javafx.scene.text.Text; + +import java.util.HashMap; +import java.util.Map; + +import static de.geofroggerfx.model.Attribute.*; +import static de.geofroggerfx.model.Type.*; +import static de.geofroggerfx.ui.glyphs.GeofroggerGlyphsDude.createIcon; +import static de.jensd.fx.glyphs.fontawesome.FontAwesomeIcons.*; +import static de.jensd.fx.glyphs.weathericons.WeatherIcons.*; + +/** + * @author Andreas + */ +public class GeocachingIcons { + + + //////////////////////////////////////////////////////////////////////////////////////////////////////////////////// + // cache attribute + //////////////////////////////////////////////////////////////////////////////////////////////////////////////////// + + private static final Map attributeMap; + + static { + attributeMap = new HashMap<>(); + attributeMap.put(DOGS_TRUE, PAW); + attributeMap.put(DOGS_FALSE, PAW); + // attributeMap.put(ACCESS_OR_PARKING_FEE_TRUE,); + // attributeMap.put(ACCESS_OR_PARKING_FEE_FALSE, ); + // attributeMap.put(CLIMBING_GEAR_TRUE,); + // attributeMap.put(CLIMBING_GEAR_FALSE,); + attributeMap.put(BOAT_TRUE, SHIP); + attributeMap.put(BOAT_FALSE, SHIP); + // attributeMap.put(SCUBA_GEAR_TRUE(5); + // attributeMap.put(SCUBA_GEAR_FALSE(-5); + attributeMap.put(RECOMMENDED_FOR_KIDS_TRUE, CHILD); + attributeMap.put(RECOMMENDED_FOR_KIDS_FALSE, CHILD); + attributeMap.put(TAKES_LESS_THAN_AN_HOUR_TRUE, TIME_1); + attributeMap.put(TAKES_LESS_THAN_AN_HOUR_FALSE, TIME_1); + attributeMap.put(SCENIC_VIEW_TRUE, EYE); + attributeMap.put(SCENIC_VIEW_FALSE, EYE); + // attributeMap.put(SIGNIFICANT_HIKE_TRUE(9); + // attributeMap.put(SIGNIFICANT_HIKE_FALSE(-9); + // attributeMap.put(DIFFICULT_CLIMBING_TRUE(10); + // attributeMap.put(DIFFICULT_CLIMBING_FALSE(-10); + // attributeMap.put(MAY_REQUIRE_WADING_TRUE(11); + // attributeMap.put(MAY_REQUIRE_WADING_FALSE(-11); + // attributeMap.put(MAY_REQUIRE_SWIMMING_TRUE(12); + // attributeMap.put(MAY_REQUIRE_SWIMMING_FALSE(-12); + attributeMap.put(AVAILABLE_AT_ALL_TIMES_TRUE, TIME_12); + attributeMap.put(AVAILABLE_AT_ALL_TIMES_FALSE, TIME_12); + attributeMap.put(RECOMMENDED_AT_NIGHT_TRUE, MOON_ALT); + attributeMap.put(RECOMMENDED_AT_NIGHT_FALSE, MOON_ALT); + attributeMap.put(AVAILABLE_DURING_WINTER_TRUE, SNOW); + attributeMap.put(AVAILABLE_DURING_WINTER_FALSE, SNOW); + // attributeMap.put(POISON_PLANTS_TRUE(17); + // attributeMap.put(POISON_PLANTS_FALSE(-17); + // attributeMap.put(DANGEROUS_ANIMALS_TRUE(18); + // attributeMap.put(DANGEROUS_ANIMALS_FALSE(-18); + // attributeMap.put(TICKS_TRUE(19); + // attributeMap.put(TICKS_FALSE(-19); + // attributeMap.put(ABANDONED_MINES_TRUE(20); + // attributeMap.put(ABANDONED_MINES_FALSE(-20); + attributeMap.put(CLIFF_FALLING_ROCKS_TRUE, METEOR); + attributeMap.put(CLIFF_FALLING_ROCKS_FALSE, METEOR); + // attributeMap.put(HUNTING_TRUE(22); + // attributeMap.put(HUNTING_FALSE(-22); + // attributeMap.put(DANGEROUS_AREA_TRUE(23); + // attributeMap.put(DANGEROUS_AREA_FALSE(-23); + attributeMap.put(WHEELCHAIR_ACCESSIBLE_TRUE, WHEELCHAIR); + attributeMap.put(WHEELCHAIR_ACCESSIBLE_FALSE, WHEELCHAIR); + // attributeMap.put(PARKING_AVAILABLE_TRUE(25); + // attributeMap.put(PARKING_AVAILABLE_FALSE(-25); + attributeMap.put(PUBLIC_TRANSPORTATION_TRUE, BUS); + attributeMap.put(PUBLIC_TRANSPORTATION_FALSE, BUS); + // attributeMap.put(DRINKING_WATER_NEARBY_TRUE(27); + // attributeMap.put(DRINKING_WATER_NEARBY_FALSE(-27); + // attributeMap.put(PUBLIC_RESTROOMS_NEARBY_TRUE(28); + // attributeMap.put(PUBLIC_RESTROOMS_NEARBY_FALSE(-28); + attributeMap.put(TELEPHONE_NEARBY_TRUE, PHONE); + attributeMap.put(TELEPHONE_NEARBY_FALSE, PHONE); + // attributeMap.put(PICNIC_TABLES_NEARBY_TRUE(30); + // attributeMap.put(PICNIC_TABLES_NEARBY_FALSE(-30); + // attributeMap.put(CAMPING_AVAILABLE_TRUE(31); + // attributeMap.put(CAMPING_AVAILABLE_FALSE(-31); + attributeMap.put(BICYCLES_TRUE, BICYCLE); + attributeMap.put(BICYCLES_FALSE, BICYCLE); + attributeMap.put(MOTORCYCLES_TRUE, MOTORCYCLE); + attributeMap.put(MOTORCYCLES_FALSE, MOTORCYCLE); + // attributeMap.put(QUADS_TRUE(34); + // attributeMap.put(QUADS_FALSE(-34); + // attributeMap.put(OFF_ROAD_VEHICLES_TRUE(35); + // attributeMap.put(OFF_ROAD_VEHICLES_FALSE(-35); + // attributeMap.put(SNOWMOBILES_TRUE(36); + // attributeMap.put(SNOWMOBILES_FALSE(-36); + // attributeMap.put(HORSES_TRUE(37); + // attributeMap.put(HORSES_FALSE(-37); + // attributeMap.put(CAMPFIRES_TRUE(38); + // attributeMap.put(CAMPFIRES_FALSE(-38); + // attributeMap.put(THORNS_TRUE(39); + // attributeMap.put(THORNS_FALSE(-39); + // attributeMap.put(STEALTH_REQUIRED_TRUE(40); + // attributeMap.put(STEALTH_REQUIRED_FALSE(-40); + // attributeMap.put(STROLLER_ACCESSIBLE_TRUE(41); + // attributeMap.put(STROLLER_ACCESSIBLE_FALSE(-41); + // attributeMap.put(WATCH_FOR_LIVESTOCK_TRUE(43); + // attributeMap.put(WATCH_FOR_LIVESTOCK_FALSE(-43); + // attributeMap.put(NEEDS_MAINTENANCE_TRUE(42); + // attributeMap.put(NEEDS_MAINTENANCE_FALSE(-42); + // attributeMap.put(FLASHLIGHT_REQUIRED_TRUE(44); + // attributeMap.put(FLASHLIGHT_REQUIRED_FALSE(-44); + // attributeMap.put(LOST_AND_FOUND_TOUR_TRUE(45); + // attributeMap.put(LOST_AND_FOUND_TOUR_FALSE(-45); + // attributeMap.put(TRUCK_DRIVER_RV_TRUE(46); + // attributeMap.put(TRUCK_DRIVER_RV_FALSE(-46); + // attributeMap.put(FIELD_PUZZLE_TRUE(47); + // attributeMap.put(FIELD_PUZZLE_FALSE(-47); + // attributeMap.put(UV_LIGHT_REQUIRED_TRUE(48); + // attributeMap.put(UV_LIGHT_REQUIRED_FALSE(-48); + // attributeMap.put(SNOWSHOES_TRUE(49); + // attributeMap.put(SNOWSHOES_FALSE(-49); + // attributeMap.put(CROSS_COUNTRY_SKIS_TRUE(50); + // attributeMap.put(CROSS_COUNTRY_SKIS_FALSE(-50); + // attributeMap.put(SPECIAL_TOOL_REQUIRED_TRUE(51); + // attributeMap.put(SPECIAL_TOOL_REQUIRED_FALSE(-51); + attributeMap.put(NIGHT_CACHE_TRUE, MOON_WANING_CRESCENT_2); + attributeMap.put(NIGHT_CACHE_FALSE, MOON_WANING_CRESCENT_2); + // attributeMap.put(PARK_AND_GRAB_TRUE(53); + // attributeMap.put(PARK_AND_GRAB_FALSE(-53); + // attributeMap.put(ABANDONED_STRUCTURE_TRUE(54); + // attributeMap.put(ABANDONED_STRUCTURE_FALSE(-54); + // attributeMap.put(SHORT_HIKE_LESS_THAN_1KM_TRUE(55); + // attributeMap.put(SHORT_HIKE_LESS_THAN_1KM_FALSE(-55); + // attributeMap.put(MEDIUM_HIKE_1KM_10KM_TRUE(56); + // attributeMap.put(MEDIUM_HIKE_1KM_10KM_FALSE(-56); + // attributeMap.put(LONG_HIKE_10KM_TRUE(57); + // attributeMap.put(LONG_HIKE_10KM_FALSE(-57); + // attributeMap.put(FUEL_NEARBY_TRUE(58); + // attributeMap.put(FUEL_NEARBY_FALSE(-58); + // attributeMap.put(FOOD_NEARBY_TRUE(59); + // attributeMap.put(FOOD_NEARBY_FALSE(-59); + // attributeMap.put(WIRELESS_BEACON_TRUE(60); + // attributeMap.put(WIRELESS_BEACON_FALSE(-60); + // attributeMap.put(PARTNERSHIP_CACHE_TRUE(61); + // attributeMap.put(PARTNERSHIP_CACHE_FALSE(-61); + attributeMap.put(SEASONAL_ACCESS_TRUE, THERMOMETER); + attributeMap.put(SEASONAL_ACCESS_FALSE, THERMOMETER); + // attributeMap.put(TOURIST_FRIENDLY_TRUE(63); + // attributeMap.put(TOURIST_FRIENDLY_FALSE(-63); + // attributeMap.put(TREE_CLIMBING_TRUE(64); + // attributeMap.put(TREE_CLIMBING_FALSE(-64); + // attributeMap.put(FRONT_YARD_PRIVATE_RESIDENCE_TRUE(65); + // attributeMap.put(FRONT_YARD_PRIVATE_RESIDENCE_FALSE(-65); + // attributeMap.put(TEAMWORK_REQUIRED_TRUE(66); + // attributeMap.put(TEAMWORK_REQUIRED_FALSE(-66); + // attributeMap.put(GEOTOUR_TRUE(67); + // attributeMap.put(GEOTOUR_FALSE(-67); + } + + public static Text getIconAsText(Attribute attribute, String iconSize) { + return createIcon(getIcon(attribute), iconSize); + } + + public static Text getIconAsText(Attribute attribute) { + return getIconAsText(attribute, GlyphIcon.DEFAULT_ICON_SIZE); + } + + public static String getIconAsString(Attribute attribute) { + return getIcon(attribute).characterToString(); + } + + public static GlyphIcons getIcon(Attribute attribute) { + GlyphIcons iconName = attributeMap.get(attribute); + if (iconName == null) { + iconName = FontAwesomeIcons.BLANK; + } + return iconName; + } + + //////////////////////////////////////////////////////////////////////////////////////////////////////////////////// + // cache type + //////////////////////////////////////////////////////////////////////////////////////////////////////////////////// + + private static final Map typeMap; + + static { + typeMap = new HashMap<>(); + typeMap.put(MULTI_CACHE, TAGS); + typeMap.put(TRADITIONAL_CACHE, TAG); + typeMap.put(UNKNOWN_CACHE, QUESTION); + typeMap.put(EARTH_CACHE, GLOBE); + typeMap.put(LETTERBOX, ENVELOPE); + typeMap.put(EVENT, CALENDAR); + typeMap.put(CITO_EVENT, CALENDAR); + typeMap.put(MEGA_EVENT, CALENDAR); + typeMap.put(WHERIGO, COMPASS); + typeMap.put(WEBCAM_CACHE, CAMERA); + typeMap.put(VIRTUAL_CACHE, LAPTOP); + } + + public static Text getIconAsText(Type type, String iconSize) { + return createIcon(getIcon(type), iconSize); + } + + public static Text getIconAsText(Type type) { + return getIconAsText(type, GlyphIcon.DEFAULT_ICON_SIZE); + } + + public static String getIconAsString(Type type) { + return getIcon(type).characterToString(); + } + + public static GlyphIcons getIcon(Type type) { + GlyphIcons iconName = typeMap.get(type); + if (iconName == null) { + iconName = FontAwesomeIcons.BLANK; + } + return iconName; + } + + + //////////////////////////////////////////////////////////////////////////////////////////////////////////////////// + // star icon + //////////////////////////////////////////////////////////////////////////////////////////////////////////////////// + + public static Text getStars(String value) { + return getStarsAsText(value, GlyphIcon.DEFAULT_ICON_SIZE); + } + + public static String getStarsAsString(String value) { + StringBuffer stringBuffer = new StringBuffer(); + switch (value) { + case "1": + stringBuffer.append(STAR.characterToString()); + break; + + case "1.5": + stringBuffer.append(STAR.characterToString()) + .append(STAR_HALF.characterToString()); + break; + + case "2": + stringBuffer.append(STAR.characterToString()) + .append(STAR.characterToString()); + break; + + case "2.5": + stringBuffer.append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR_HALF.characterToString()); + break; + + case "3": + stringBuffer.append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()); + break; + + case "3.5": + stringBuffer.append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR_HALF.characterToString()); + break; + + case "4": + stringBuffer.append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()); + break; + + case "4.5": + stringBuffer.append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR_HALF.characterToString()); + break; + + case "5": + stringBuffer.append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()) + .append(STAR.characterToString()); + break; + + default: + stringBuffer.append(FontAwesomeIcons.BLANK.characterToString()); + System.out.println(value); + } + return stringBuffer.toString(); + } + + public static Text getStarsAsText(String value, String iconSize) { + Text text = createIcon(FontAwesomeIcons.BLANK, iconSize); + text.setText(value); + return text; + } + +} diff --git a/src/main/java/de/geofroggerfx/ui/details/DetailsController.java b/src/main/java/de/geofroggerfx/ui/details/DetailsController.java new file mode 100644 index 0000000..fcde0c4 --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/details/DetailsController.java @@ -0,0 +1,158 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui.details; + +import com.lynden.gmapsfx.GoogleMapView; +import com.lynden.gmapsfx.MapComponentInitializedListener; +import com.lynden.gmapsfx.javascript.object.*; +import de.geofroggerfx.application.SessionContext; +import de.geofroggerfx.application.SessionContextListener; +import de.geofroggerfx.model.Cache; +import de.geofroggerfx.ui.FXMLController; +import javafx.fxml.FXML; +import javafx.scene.control.Label; +import javafx.scene.control.TitledPane; +import javafx.scene.layout.VBox; +import javafx.scene.text.Text; +import javafx.scene.web.WebEngine; +import javafx.scene.web.WebView; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.stereotype.Component; + +import java.net.URL; +import java.util.ResourceBundle; + +import static de.geofroggerfx.application.SessionContext.CURRENT_CACHE; +import static de.geofroggerfx.ui.GeocachingIcons.getStarsAsString; + +/** + * Created by Andreas on 09.03.2015. + */ +@Component +public class DetailsController extends FXMLController { + + @Autowired + private SessionContext sessionContext; + + @FXML + private Label cacheName; + + @FXML + private Text cacheDifficulty; + + @FXML + private Text cacheTerrain; + + @FXML + private VBox mainContent; + + @FXML + private WebView description; + + @FXML + private GoogleMapView mapView; + + private GoogleMap map; + private Marker marker; + + + @Value("${fxml.geofrogger.details.view}") + @Override + public void setFxmlFilePath(String filePath) { + this.fxmlFilePath = filePath; + } + + @Override + public void initialize(URL location, ResourceBundle resources) { + sessionContext.addListener(CURRENT_CACHE, new SessionContextListener() { + @Override + public void sessionContextChanged() { + fillContent(); + } + }); + + mapView.addMapInializedListener(new MapComponentInitializedListener() { + @Override + public void mapInitialized() { + //Set the initial properties of the map. + MapOptions mapOptions = new MapOptions(); + mapOptions.center(new LatLong(47.6097, -122.3331)) + .mapType(MapTypeIdEnum.ROADMAP) + .overviewMapControl(false) + .panControl(false) + .rotateControl(false) + .scaleControl(false) + .streetViewControl(false) + .zoomControl(false) + .zoom(12); + + map = mapView.createMap(mapOptions); + + LatLong latLong = new LatLong(49.045458, 9.189835); + MarkerOptions options = new MarkerOptions(); + options.position(latLong); + marker = new Marker(options); + map.addMarker(marker); + map.setCenter(latLong); + } + }); + } + + private void fillContent() { + Cache cache = (Cache) sessionContext.getData(CURRENT_CACHE); + cacheName.setText(cache.getName()); + cacheDifficulty.setText(getStarsAsString(cache.getDifficulty())); + cacheTerrain.setText(getStarsAsString(cache.getTerrain())); + + String shortDescription = cache.getShortDescription(); + if (!cache.getLongDescriptionHtml()) { + shortDescription = shortDescription.replaceAll("\n","
"); + } + + String longDescription = cache.getLongDescription(); + if (!cache.getLongDescriptionHtml()) { + longDescription = longDescription.replaceAll("\n","
"); + } + + String description = "

"+shortDescription+"

"+longDescription+"

"; + final WebEngine webEngine = this.description.getEngine(); + webEngine.loadContent(description); + + LatLong latLong = new LatLong(cache.getMainWayPoint().getLatitude(), cache.getMainWayPoint().getLongitude()); + MarkerOptions options = new MarkerOptions(); + options.position(latLong); + options.title(cache.getMainWayPoint().getName()); + + map.removeMarker(marker); + + marker.setTitle(cache.getMainWayPoint().getName()); + marker = new Marker(options); + map.addMarker(marker); + map.setCenter(latLong); + mapView.requestLayout(); + } +} diff --git a/src/main/java/de/geofroggerfx/ui/glyphs/ElusiveIcon.java b/src/main/java/de/geofroggerfx/ui/glyphs/ElusiveIcon.java new file mode 100644 index 0000000..85ca19a --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/glyphs/ElusiveIcon.java @@ -0,0 +1,45 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui.glyphs; + +import de.jensd.fx.glyphs.GlyphIcon; +import javafx.scene.text.Font; + +public class ElusiveIcon extends GlyphIcon { + + public final static String TTF_PATH = "/fonts/elusive/Elusive-Icons.ttf"; + public final static String FONT_FAMILY = "\'Elusive-Icons\'"; + + static { + Font.loadFont(ElusiveIcon.class.getResource(TTF_PATH).toExternalForm(), 10.0); + } + + @Override + public ElusiveIcons getDefaultGlyph() { + return ElusiveIcons.USER; + } + +} \ No newline at end of file diff --git a/src/main/java/de/geofroggerfx/ui/glyphs/ElusiveIcons.java b/src/main/java/de/geofroggerfx/ui/glyphs/ElusiveIcons.java new file mode 100644 index 0000000..3ab636b --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/glyphs/ElusiveIcons.java @@ -0,0 +1,359 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui.glyphs; + +import de.jensd.fx.glyphs.GlyphIcons; + +public enum ElusiveIcons implements GlyphIcons { + + ZOOM_OUT('\uE600'), + ZOOM_IN('\uE601'), + YOUTUBE('\uE602'), + WRENCH_ALT('\uE603'), + WRENCH('\uE604'), + WORDPRESS('\uE605'), + WHEELCHAIR('\uE606'), + WEBSITE_ALT('\uE607'), + WEBSITE('\uE608'), + WARNING_SIGN('\uE609'), + W3C('\uE60A'), + VOLUME_UP('\uE60B'), + VOLUME_OFF('\uE60C'), + VOLUME_DOWN('\uE60D'), + VKONTAKTE('\uE60E'), + VIMEO('\uE60F'), + VIEW_MODE('\uE610'), + VIDEO_CHAT('\uE611'), + VIDEO_ALT('\uE612'), + VIDEO('\uE613'), + VIADEO('\uE614'), + USER('\uE615'), + USD('\uE616'), + UPLOAD('\uE617'), + UNLOCK_ALT('\uE618'), + UNLOCK('\uE619'), + UNIVERSAL_ACCESS('\uE61A'), + TWITTER('\uE61B'), + TUMBLR('\uE61C'), + TRASH_ALT('\uE61D'), + TRASH('\uE61E'), + TORSO('\uE61F'), + TINT('\uE620'), + TIME_ALT('\uE621'), + TIME('\uE622'), + THUMBS_UP('\uE623'), + THUMBS_DOWN('\uE624'), + TH_LIST('\uE625'), + TH_LARGE('\uE626'), + TH('\uE627'), + TEXT_WIDTH('\uE628'), + TEXT_HEIGHT('\uE629'), + TASKS('\uE62A'), + TAGS('\uE62B'), + TAG('\uE62C'), + STUMBLEUPON('\uE62D'), + STOP_ALT('\uE62E'), + STOP('\uE62F'), + STEP_FORWARD('\uE630'), + STEP_BACKWARD('\uE631'), + STAR_EMPTY('\uE632'), + STAR_ALT('\uE633'), + STAR('\uE634'), + STACKOVERFLOW('\uE635'), + SPOTIFY('\uE636'), + SPEAKER('\uE637'), + SOUNDCLOUD('\uE638'), + SMILEY_ALT('\uE639'), + SMILEY('\uE63A'), + SLIDESHARE('\uE63B'), + SKYPE('\uE63C'), + SIGNAL('\uE63D'), + SHOPPING_CART_SIGN('\uE63E'), + SHOPPING_CART('\uE63F'), + SHARE_ALT('\uE640'), + SHARE('\uE641'), + SEARCH_ALT('\uE642'), + SEARCH('\uE643'), + SCREENSHOT('\uE644'), + SCREEN_ALT('\uE645'), + SCREEN('\uE646'), + SCISSORS('\uE647'), + RSS('\uE648'), + ROAD('\uE649'), + REVERSE_ALT('\uE64A'), + RETWEET('\uE64B'), + RETURN_KEY('\uE64C'), + RESIZE_VERTICAL('\uE64D'), + RESIZE_SMALL('\uE64E'), + RESIZE_HORIZONTAL('\uE64F'), + RESIZE_FULL('\uE650'), + REPEAT_ALT('\uE651'), + REPEAT('\uE652'), + REMOVE_SIGN('\uE653'), + REMOVE_CIRCLE('\uE654'), + REMOVE('\uE655'), + REFRESH('\uE656'), + REDDIT('\uE657'), + RECORD('\uE658'), + RANDOM('\uE659'), + QUOTES_ALT('\uE65A'), + QUOTES('\uE65B'), + QUESTION_SIGN('\uE65C'), + QUESTION('\uE65D'), + QRCODE('\uE65E'), + PUZZLE('\uE65F'), + PRINT('\uE660'), + PODCAST('\uE661'), + PLUS_SIGN('\uE662'), + PLUS('\uE663'), + PLAY_CIRCLE('\uE664'), + PLAY_ALT('\uE665'), + PLAY('\uE666'), + PLANE('\uE667'), + PINTEREST('\uE668'), + PICTURE('\uE669'), + PICASA('\uE66A'), + PHOTO_ALT('\uE66B'), + PHOTO('\uE66C'), + PHONE_ALT('\uE66D'), + PHONE('\uE66E'), + PERSON('\uE66F'), + PENCIL_ALT('\uE670'), + PENCIL('\uE671'), + PAUSE_ALT('\uE672'), + PAUSE('\uE673'), + PATH('\uE674'), + PAPER_CLIP_ALT('\uE675'), + PAPER_CLIP('\uE676'), + OPENSOURCE('\uE677'), + OK_SIGN('\uE678'), + OK_CIRCLE('\uE679'), + OK('\uE67A'), + OFF('\uE67B'), + NETWORK('\uE67C'), + MYSPACE('\uE67D'), + MUSIC('\uE67E'), + MOVE('\uE67F'), + MINUS_SIGN('\uE680'), + MINUS('\uE681'), + MIC_ALT('\uE682'), + MIC('\uE683'), + MAP_MARKER_ALT('\uE684'), + MAP_MARKER('\uE685'), + MALE('\uE686'), + MAGNET('\uE687'), + MAGIC('\uE688'), + LOCK_ALT('\uE689'), + LOCK('\uE68A'), + LIVEJOURNAL('\uE68B'), + LIST_ALT('\uE68C'), + LIST('\uE68D'), + LINKEDIN('\uE68E'), + LINK('\uE68F'), + LINES('\uE690'), + LEAF('\uE691'), + LASTFM('\uE692'), + LAPTOP_ALT('\uE693'), + LAPTOP('\uE694'), + KEY('\uE695'), + ITALIC('\uE696'), + IPHONE_HOME('\uE697'), + INSTAGRAM('\uE698'), + INFO_SIGN('\uE699'), + INDENT_RIGHT('\uE69A'), + INDENT_LEFT('\uE69B'), + INBOX_BOX('\uE69C'), + INBOX_ALT('\uE69D'), + INBOX('\uE69E'), + IDEA_ALT('\uE69F'), + IDEA('\uE6A0'), + HOURGLASS('\uE6A1'), + HOME_ALT('\uE6A2'), + HOME('\uE6A3'), + HEART_EMPTY('\uE6A4'), + HEART_ALT('\uE6A5'), + HEART('\uE6A6'), + HEARING_IMPAIRED('\uE6A7'), + HEADPHONES('\uE6A8'), + HDD('\uE6A9'), + HAND_UP('\uE6AA'), + HAND_RIGHT('\uE6AB'), + HAND_LEFT('\uE6AC'), + HAND_DOWN('\uE6AD'), + GUIDEDOG('\uE6AE'), + GROUP_ALT('\uE6AF'), + GROUP('\uE6B0'), + GRAPH_ALT('\uE6B1'), + GRAPH('\uE6B2'), + GOOGLEPLUS('\uE6B3'), + GLOBE_ALT('\uE6B4'), + GLOBE('\uE6B5'), + GLASSES('\uE6B6'), + GLASS('\uE6B7'), + GITHUB_TEXT('\uE6B8'), + GITHUB('\uE6B9'), + GIFT('\uE6BA'), + GBP('\uE6BB'), + FULLSCREEN('\uE6BC'), + FRIENDFEED_RECT('\uE6BD'), + FRIENDFEED('\uE6BE'), + FOURSQUARE('\uE6BF'), + FORWARD_ALT('\uE6C0'), + FORWARD('\uE6C1'), + FORK('\uE6C2'), + FONTSIZE('\uE6C3'), + FONT('\uE6C4'), + FOLDER_SIGN('\uE6C5'), + FOLDER_OPEN('\uE6C6'), + FOLDER_CLOSE('\uE6C7'), + FOLDER('\uE6C8'), + FLICKR('\uE6C9'), + FLAG_ALT('\uE6CA'), + FLAG('\uE6CB'), + FIRE('\uE6CC'), + FILTER('\uE6CD'), + FILM('\uE6CE'), + FILE_NEW_ALT('\uE6CF'), + FILE_NEW('\uE6D0'), + FILE_EDIT_ALT('\uE6D1'), + FILE_EDIT('\uE6D2'), + FILE_ALT('\uE6D3'), + FILE('\uE6D4'), + FEMALE('\uE6D5'), + FAST_FORWARD('\uE6D6'), + FAST_BACKWARD('\uE6D7'), + FACETIME_VIDEO('\uE6D8'), + FACEBOOK('\uE6D9'), + EYE_OPEN('\uE6DA'), + EYE_CLOSE('\uE6DB'), + EXCLAMATION_SIGN('\uE6DC'), + EUR('\uE6DD'), + ERROR_ALT('\uE6DE'), + ERROR('\uE6DF'), + ENVELOPE_ALT('\uE6E0'), + ENVELOPE('\uE6E1'), + EJECT('\uE6E2'), + EDIT('\uE6E3'), + DRIBBBLE('\uE6E4'), + DOWNLOAD_ALT('\uE6E5'), + DOWNLOAD('\uE6E6'), + DIGG('\uE6E7'), + DEVIANTART('\uE6E8'), + DELICIOUS('\uE6E9'), + DASHBOARD('\uE6EA'), + CSS('\uE6EB'), + CREDIT_CARD('\uE6EC'), + COMPASS_ALT('\uE6ED'), + COMPASS('\uE6EE'), + COMMENT_ALT('\uE6EF'), + COMMENT('\uE6F0'), + COGS('\uE6F1'), + COG_ALT('\uE6F2'), + COG('\uE6F3'), + CLOUD_ALT('\uE6F4'), + CLOUD('\uE6F5'), + CIRCLE_ARROW_UP('\uE6F6'), + CIRCLE_ARROW_RIGHT('\uE6F7'), + CIRCLE_ARROW_LEFT('\uE6F8'), + CIRCLE_ARROW_DOWN('\uE6F9'), + CHILD('\uE6FA'), + CHEVRON_UP('\uE6FB'), + CHEVRON_RIGHT('\uE6FC'), + CHEVRON_LEFT('\uE6FD'), + CHEVRON_DOWN('\uE6FE'), + CHECK_EMPTY('\uE6FF'), + CHECK('\uE700'), + CERTIFICATE('\uE701'), + CC('\uE702'), + CARET_UP('\uE703'), + CARET_RIGHT('\uE704'), + CARET_LEFT('\uE705'), + CARET_DOWN('\uE706'), + CAR('\uE707'), + CAMERA('\uE708'), + CALENDAR_SIGN('\uE709'), + CALENDAR('\uE70A'), + BULLHORN('\uE70B'), + BULB('\uE70C'), + BRUSH('\uE70D'), + BROOM('\uE70E'), + BRIEFCASE('\uE70F'), + BRAILLE('\uE710'), + BOOKMARK_EMPTY('\uE711'), + BOOKMARK('\uE712'), + BOOK('\uE713'), + BOLD('\uE714'), + BLOGGER('\uE715'), + BLIND('\uE716'), + BELL('\uE717'), + BEHANCE('\uE718'), + BARCODE('\uE719'), + BAN_CIRCLE('\uE71A'), + BACKWARD('\uE71B'), + ASL('\uE71C'), + ARROW_UP('\uE71D'), + ARROW_RIGHT('\uE71E'), + ARROW_LEFT('\uE71F'), + ARROW_DOWN('\uE720'), + ALIGN_RIGHT('\uE721'), + ALIGN_LEFT('\uE722'), + ALIGN_JUSTIFY('\uE723'), + ALIGN_CENTER('\uE724'), + ADULT('\uE725'), + ADJUST_ALT('\uE726'), + ADJUST('\uE727'), + ADDRESS_BOOK_ALT('\uE728'), + ADDRESS_BOOK('\uE729'), + ASTERISK('\uE72A'); + + private final char character; + + private ElusiveIcons(char character) { + this.character = character; + } + + + @Override + public char getChar() { + return character; + } + + @Override + public String unicodeToString() { + return String.format("\\u%04x", (int) character); + } + + @Override + public String characterToString() { + return Character.toString(character); + } + + @Override + public String getFontFamily() { + return ElusiveIcon.FONT_FAMILY; + } + +} diff --git a/src/main/java/de/geofroggerfx/ui/glyphs/GeofroggerGlyphsDude.java b/src/main/java/de/geofroggerfx/ui/glyphs/GeofroggerGlyphsDude.java new file mode 100644 index 0000000..9e0c45f --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/glyphs/GeofroggerGlyphsDude.java @@ -0,0 +1,14 @@ +package de.geofroggerfx.ui.glyphs; + +import de.jensd.fx.glyphs.GlyphsDude; +import javafx.scene.text.Font; + +/** + * Created by Andreas on 23.03.2015. + */ +public class GeofroggerGlyphsDude extends GlyphsDude { + + static { + Font.loadFont(GeofroggerGlyphsDude.class.getResource(ElusiveIcon.TTF_PATH).toExternalForm(), 10.0); + } +} diff --git a/src/main/java/de/geofroggerfx/ui/list/CacheListCell.java b/src/main/java/de/geofroggerfx/ui/list/CacheListCell.java new file mode 100644 index 0000000..b01da0c --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/list/CacheListCell.java @@ -0,0 +1,148 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui.list; + +import de.geofroggerfx.model.CacheListEntry; +import de.geofroggerfx.ui.GeocachingIcons; +import de.jensd.fx.glyphs.GlyphsDude; +import de.jensd.fx.glyphs.fontawesome.FontAwesomeIcons; +import javafx.geometry.Insets; +import javafx.scene.control.Label; +import javafx.scene.control.ListCell; +import javafx.scene.layout.ColumnConstraints; +import javafx.scene.layout.GridPane; +import javafx.scene.layout.Priority; +import javafx.scene.text.Text; + + +/** + * Multi-Column-Row list cell to shows the most important data in a list. + * + * @author Andreas + */ +public class CacheListCell extends ListCell { + private static final String YELLOW = ";-fx-fill: linear-gradient(#e8e474 0%, #edcf59 70%, #bfba26 85%);"; + private static final String GRAY = ";-fx-fill: linear-gradient(#cccccc 0%, #999999 70%, #888888 85%);"; + private final GridPane grid = new GridPane(); + private final Text icon = GlyphsDude.createIcon(FontAwesomeIcons.BLANK, "20.0"); + private final Label name = new Label(); + private final Text difficultyStars = GlyphsDude.createIcon(FontAwesomeIcons.BLANK, "8.0"); + private final Text terrainStars = GlyphsDude.createIcon(FontAwesomeIcons.BLANK, "8.0"); + + public CacheListCell() { + configureGrid(); + configureIcon(); + configureName(); + configureDifficulty(); + configureTerrain(); + addControlsToGrid(); + } + + @Override + public void updateItem(CacheListEntry cache, boolean empty) { + super.updateItem(cache, empty); + if (empty) { + clearContent(); + } else { + addContent(cache); + } + } + + private void configureGrid() { + grid.setHgap(10); + grid.setVgap(4); + grid.setPadding(new Insets(0, 10, 0, 10)); + + ColumnConstraints column1 = new ColumnConstraints(32); + ColumnConstraints column2 = new ColumnConstraints(USE_COMPUTED_SIZE , USE_COMPUTED_SIZE, Double.MAX_VALUE); + column2.setHgrow(Priority.NEVER); + ColumnConstraints column3 = new ColumnConstraints(30 , 50 , Double.MAX_VALUE); + column3.setHgrow(Priority.ALWAYS); + column3.setFillWidth(true); + ColumnConstraints column4 = new ColumnConstraints(USE_COMPUTED_SIZE , USE_COMPUTED_SIZE , Double.MAX_VALUE); + column4.setHgrow(Priority.NEVER); + ColumnConstraints column5 = new ColumnConstraints(30 , 50 , Double.MAX_VALUE); + column5.setHgrow(Priority.ALWAYS); + column5.setFillWidth(true); + grid.getColumnConstraints().addAll(column1, column2, column3, column4, column5); + } + + private void configureIcon() { + icon.setStyle(icon.getStyle()+ GRAY); + } + + private void configureName() { + name.setStyle("-fx-font-weight: bold;"); + } + + private void configureDifficulty() { + difficultyStars.setStyle(difficultyStars.getStyle() + YELLOW); + } + + private void configureTerrain() { + terrainStars.setStyle(difficultyStars.getStyle() + YELLOW); + } + + + private void addControlsToGrid() { + grid.add(icon, 0, 0, 1, 2); + grid.add(name, 1, 0, 4, 1); + grid.add(new Label("Difficulty:"), 1, 1); + grid.add(difficultyStars, 2, 1); + grid.add(new Label("Terrain:"), 3, 1); + grid.add(terrainStars, 4, 1); + } + + private void clearContent() { + setText(null); + setGraphic(null); + } + + private void addContent(CacheListEntry cache) { + setIcon(cache); + setCacheName(cache); + setDifficulty(cache); + setTerrain(cache); + setGraphic(grid); + } + + private void setCacheName(CacheListEntry cache) { + name.setText(cache.getName()); + } + + private void setIcon(CacheListEntry cache) { + icon.setText(GeocachingIcons.getIconAsString(cache.getType())); + } + + private void setDifficulty(CacheListEntry cache) { + difficultyStars.setText(GeocachingIcons.getStarsAsString(cache.getDifficulty())); + } + + private void setTerrain(CacheListEntry cache) { + terrainStars.setText(GeocachingIcons.getStarsAsString(cache.getTerrain())); + } + +} diff --git a/src/main/java/de/geofroggerfx/ui/list/ListController.java b/src/main/java/de/geofroggerfx/ui/list/ListController.java new file mode 100644 index 0000000..1b03fb5 --- /dev/null +++ b/src/main/java/de/geofroggerfx/ui/list/ListController.java @@ -0,0 +1,96 @@ +/* + * Copyright (c) Andreas Billmann + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ +package de.geofroggerfx.ui.list; + +import de.geofroggerfx.application.SessionContext; +import de.geofroggerfx.model.Cache; +import de.geofroggerfx.model.CacheListEntry; +import de.geofroggerfx.service.CacheService; +import de.geofroggerfx.ui.FXMLController; +import javafx.application.Platform; +import javafx.beans.InvalidationListener; +import javafx.fxml.FXML; +import javafx.scene.control.ListView; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.stereotype.Component; + +import java.net.URL; +import java.util.List; +import java.util.ResourceBundle; + +import static de.geofroggerfx.application.SessionContext.CACHE_ENTRY_LIST; +import static de.geofroggerfx.application.SessionContext.CURRENT_CACHE; + +/** + * Created by Andreas on 09.03.2015. + */ +@Component +public class ListController extends FXMLController { + + @Autowired + private SessionContext sessionContext; + + @Autowired + private CacheService cacheService; + + @FXML + ListView cacheListView; + + @Value("${fxml.geofrogger.list.view}") + @Override + public void setFxmlFilePath(String filePath) { + this.fxmlFilePath = filePath; + } + + @Override + public void initialize(URL location, ResourceBundle resources) { + setCellFactory(); + sessionContext.addListener(CACHE_ENTRY_LIST, () -> Platform.runLater(this::resetCacheList)); + cacheListView.getSelectionModel().selectedItemProperty().addListener( + (InvalidationListener) observable -> setSelectedCacheIntoSession() + ); + } + + private void resetCacheList() { + List caches = (List) sessionContext.getData(CACHE_ENTRY_LIST); + cacheListView.getItems().setAll(caches); + } + + @SuppressWarnings("unchecked") + private void setCellFactory() { + cacheListView.setCellFactory(param -> new CacheListCell()); + } + + private void setSelectedCacheIntoSession() { + CacheListEntry entry = (CacheListEntry) cacheListView.getSelectionModel().getSelectedItem(); + Cache cache = null; + if (entry != null) { + cache = cacheService.getCacheForId(entry.getId()); + } + sessionContext.setData(CURRENT_CACHE, cache); + } +} diff --git a/src/main/resources/de/geofroggerfx/dao/jdbc/database.properties b/src/main/resources/de/geofroggerfx/dao/jdbc/database.properties new file mode 100644 index 0000000..933590a --- /dev/null +++ b/src/main/resources/de/geofroggerfx/dao/jdbc/database.properties @@ -0,0 +1,3 @@ +jdbc.url=jdbc:h2:file:C:/billmann/projects/GeoFroggerFX2/geofroggerfx +jdbc.username = sa +jdbc.password = sa \ No newline at end of file diff --git a/src/main/resources/de/geofroggerfx/dao/jdbc/updates/1.sql b/src/main/resources/de/geofroggerfx/dao/jdbc/updates/1.sql new file mode 100644 index 0000000..e7a424b --- /dev/null +++ b/src/main/resources/de/geofroggerfx/dao/jdbc/updates/1.sql @@ -0,0 +1,40 @@ +CREATE TABLE cache ( + id INT PRIMARY KEY, + name VARCHAR (255), + placed_by VARCHAR (255), + available BOOLEAN, + archived BOOLEAN, + found BOOLEAN, + difficulty VARCHAR (255), + terrain VARCHAR (255), + country VARCHAR (255), + state VARCHAR (255), + short_description VARCHAR(2147483647), + short_description_html BOOLEAN, + long_description VARCHAR(2147483647), + long_description_html BOOLEAN, + encoded_hints VARCHAR(2147483647), + container VARCHAR (255), + type VARCHAR (255), + user_id INT +); + +CREATE TABLE waypoint ( + name VARCHAR (255) PRIMARY KEY , + cache_id INT, + latitude DOUBLE, + longitude DOUBLE, + time TIMESTAMP, + description VARCHAR (255), + url VARCHAR (255), + urlName VARCHAR (255), + symbol VARCHAR (255), + type VARCHAR (255), + FOREIGN KEY(cache_id) REFERENCES cache(id) ON DELETE CASCADE +); + +CREATE TABLE version ( + version INT +); + +INSERT INTO version(version) values(1); \ No newline at end of file diff --git a/src/main/resources/de/geofroggerfx/ui/application.properties b/src/main/resources/de/geofroggerfx/ui/application.properties new file mode 100644 index 0000000..3426da8 --- /dev/null +++ b/src/main/resources/de/geofroggerfx/ui/application.properties @@ -0,0 +1,10 @@ +application.name = GeoFroggerFX +application.version = 2.0 + +# fxml views +fxml.geofrogger.view = /de/geofroggerfx/ui/geofroggerfx.fxml +fxml.geofrogger.list.view = /de/geofroggerfx/ui/list/list.fxml +fxml.geofrogger.details.view = /de/geofroggerfx/ui/details/details.fxml + +# resources +resource.main = de.geofroggerfx.ui.geofrogger \ No newline at end of file diff --git a/src/main/resources/de/geofroggerfx/ui/details/details.fxml b/src/main/resources/de/geofroggerfx/ui/details/details.fxml new file mode 100644 index 0000000..fbc1c99 --- /dev/null +++ b/src/main/resources/de/geofroggerfx/ui/details/details.fxml @@ -0,0 +1,140 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + + + + + + +
+ + + + + + + + + +
diff --git a/src/main/resources/de/geofroggerfx/ui/geofrogger_de.properties b/src/main/resources/de/geofroggerfx/ui/geofrogger_de.properties new file mode 100644 index 0000000..abd2741 --- /dev/null +++ b/src/main/resources/de/geofroggerfx/ui/geofrogger_de.properties @@ -0,0 +1,52 @@ +menu.title.import.gpx = Importiere GPX +menu.title.file = Datei +menu.title.quit = Beenden +menu.title.help = Hilfe +menu.title.settings = Einstellungen +menu.title.about = \u00dcber GeoFroggerFX +menu.title.plugins = Plugins +menu.title.list = Listen +menu.title.list.new = Liste anlegen +menu.title.list.delete = Liste l\u00F6schen + +menu.title.sort = Sortieren +menu.title.filter = Filtern + +label.text.cache.list=Liste: +label.text.cache.list.count=Anzahl: +label.text.name=Name: +label.text.difficulty=Schwierigkeit: +label.text.terrain=Gel\u00E4nde +label.text.placedBy=Platziert von: +label.text.owner=Betreut von: +label.text.date=Datum: +label.text.type=Typ: +label.text.container=Gr\u00F6\u00dfe: +label.text.shortdescription=Kurze Beschreibung: +label.text.htmldescription=HTML Beschreibung +label.text.longdescription=Lange Beschreibung: + +tab.text.descriptions=Beschreibungen +tab.text.general=Allgemein + +sort.cache.name = GC Code +sort.cache.type = Art +sort.cache.difficulty = Schwierigkeitsgrad +sort.cache.terrain = Gel\u00E4nde +sort.cache.placedBy = Platziert von +sort.cache.owner = Betreut von + +dialog.title.about = Über +dialog.title.new_list = Neue Liste +dialog.label.listname = Name der Liste: +dialog.msg.list.does.exist = Diese Liste existiert schon! +dialog.title.delete_list = Liste löschen + +all.caches = Alle Caches + +status.load.all.caches.from.db = Lade alle Caches von der Datenbank. +status.all.cache.lists.loaded = Alle Listen geladen. +status.load.caches.from.db = Lade Caches von der Datenbank. +status.all.caches.loaded = Alle Caches geladen. +status.store.all.caches = Speichere Caches in Datenbank. +status.all.caches.stored = Alle Caches in der Datenbank gespeichert. \ No newline at end of file diff --git a/src/main/resources/de/geofroggerfx/ui/geofrogger_en.properties b/src/main/resources/de/geofroggerfx/ui/geofrogger_en.properties new file mode 100644 index 0000000..41802fb --- /dev/null +++ b/src/main/resources/de/geofroggerfx/ui/geofrogger_en.properties @@ -0,0 +1,53 @@ +menu.title.import.gpx = Import GPX +menu.title.file = File +menu.title.quit = Quit +menu.title.help = Help +menu.title.settings = Settings +menu.title.about = About GeoFroggerFX +menu.title.plugins = Plugins +menu.title.list = Lists +menu.title.list.new = New list +menu.title.list.delete = Delete list + + +menu.title.sort = Sort +menu.title.filter = Filter + +label.text.cache.list=List: +label.text.cache.list.count=Number: +label.text.name=Name: +label.text.difficulty=Difficulty: +label.text.terrain=Terrain: +label.text.placedBy=Placed By: +label.text.owner=Owner: +label.text.date=Date: +label.text.type=Type: +label.text.container=Container: +label.text.shortdescription=Short description: +label.text.htmldescription=HTML Description +label.text.longdescription=Long description: + +tab.text.descriptions=Descriptions +tab.text.general=General + +sort.cache.name = GC Code +sort.cache.type = Type +sort.cache.difficulty = Difficulty +sort.cache.terrain = Terrain +sort.cache.placedBy = Placed by +sort.cache.owner = Owner + +dialog.title.about = About +dialog.title.new_list = New list +dialog.label.listname = Name of list: +dialog.msg.list.does.exist = List does already exist! +dialog.title.delete_list = Delete list + +all.caches = All caches + +status.load.all.caches.from.db = Load cache lists from database. +status.all.cache.lists.loaded = All cache lists loaded. +status.load.caches.from.db = Load caches from database. +status.all.caches.loaded = All caches loaded. +status.store.all.caches = Store caches in database. +status.all.caches.stored = All caches are stored in database. \ No newline at end of file diff --git a/src/main/resources/de/geofroggerfx/ui/geofroggerfx.css b/src/main/resources/de/geofroggerfx/ui/geofroggerfx.css new file mode 100644 index 0000000..ad78d49 --- /dev/null +++ b/src/main/resources/de/geofroggerfx/ui/geofroggerfx.css @@ -0,0 +1,4 @@ +.cache-h1 { + -fx-font-size: 24pt; + -fx-font-family: "Sofia-Regular"; +} diff --git a/src/main/resources/de/geofroggerfx/ui/geofroggerfx.fxml b/src/main/resources/de/geofroggerfx/ui/geofroggerfx.fxml new file mode 100644 index 0000000..e508715 --- /dev/null +++ b/src/main/resources/de/geofroggerfx/ui/geofroggerfx.fxml @@ -0,0 +1,71 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + + + + + + + +
+
+ + + + + + + + + + + + + + + diff --git a/src/main/resources/de/geofroggerfx/ui/list/list.fxml b/src/main/resources/de/geofroggerfx/ui/list/list.fxml new file mode 100644 index 0000000..00a1630 --- /dev/null +++ b/src/main/resources/de/geofroggerfx/ui/list/list.fxml @@ -0,0 +1,34 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/resources/fonts/elusive/Elusive-Icons.ttf b/src/main/resources/fonts/elusive/Elusive-Icons.ttf new file mode 100644 index 0000000..ba2bafe Binary files /dev/null and b/src/main/resources/fonts/elusive/Elusive-Icons.ttf differ diff --git a/src/main/resources/fonts/elusive/license.txt b/src/main/resources/fonts/elusive/license.txt new file mode 100644 index 0000000..9f139b3 --- /dev/null +++ b/src/main/resources/fonts/elusive/license.txt @@ -0,0 +1,86 @@ +SIL OPEN FONT LICENSE + +Version 1.1 - 26 February 2007 + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting — in part or in whole — any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. \ No newline at end of file diff --git a/src/main/resources/fonts/elusive/readme.txt b/src/main/resources/fonts/elusive/readme.txt new file mode 100644 index 0000000..6a2ed90 --- /dev/null +++ b/src/main/resources/fonts/elusive/readme.txt @@ -0,0 +1,10 @@ +Elusive-Iconfont +================ + +The Elusive Iconfont is an icons webfont, optimized for use with twitter's bootstrap. + +For examples & usage see http://shoestrap.org/downloads/elusive-icons-webfont/ + +Licence: [SIL](http://scripts.sil.org/cms/scripts/page.php?site_id=nrsi&id=OFL) + +https://github.com/reduxframework/elusive-iconfont \ No newline at end of file diff --git a/src/main/resources/fonts/sofia/SIL OFL Font License Sofia.txt b/src/main/resources/fonts/sofia/SIL OFL Font License Sofia.txt new file mode 100644 index 0000000..bdeef80 --- /dev/null +++ b/src/main/resources/fonts/sofia/SIL OFL Font License Sofia.txt @@ -0,0 +1,94 @@ +Copyright (c) 2011 by LatinoType Limitada (luciano@latinotype.com), +with Reserved Font Names "Sofia" + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +http://scripts.sil.org/OFL + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/src/main/resources/fonts/sofia/Sofia-Regular.otf b/src/main/resources/fonts/sofia/Sofia-Regular.otf new file mode 100644 index 0000000..1f76d2d Binary files /dev/null and b/src/main/resources/fonts/sofia/Sofia-Regular.otf differ