20 changed files with 734 additions and 1040 deletions
@ -0,0 +1,27 @@ |
|||||||
|
<?xml version="1.0" encoding="UTF-8"?> |
||||||
|
<classpath> |
||||||
|
<classpathentry kind="src" output="target/classes" path="src/main/java"> |
||||||
|
<attributes> |
||||||
|
<attribute name="optional" value="true"/> |
||||||
|
<attribute name="maven.pomderived" value="true"/> |
||||||
|
</attributes> |
||||||
|
</classpathentry> |
||||||
|
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-11"> |
||||||
|
<attributes> |
||||||
|
<attribute name="maven.pomderived" value="true"/> |
||||||
|
</attributes> |
||||||
|
</classpathentry> |
||||||
|
<classpathentry kind="src" output="target/test-classes" path="src/test/java"> |
||||||
|
<attributes> |
||||||
|
<attribute name="optional" value="true"/> |
||||||
|
<attribute name="maven.pomderived" value="true"/> |
||||||
|
<attribute name="test" value="true"/> |
||||||
|
</attributes> |
||||||
|
</classpathentry> |
||||||
|
<classpathentry kind="con" path="org.eclipse.m2e.MAVEN2_CLASSPATH_CONTAINER"> |
||||||
|
<attributes> |
||||||
|
<attribute name="maven.pomderived" value="true"/> |
||||||
|
</attributes> |
||||||
|
</classpathentry> |
||||||
|
<classpathentry kind="output" path="target/classes"/> |
||||||
|
</classpath> |
@ -1,2 +1,4 @@ |
|||||||
/backup |
/backup |
||||||
/Belegscanner |
/Belegscanner |
||||||
|
/bin/ |
||||||
|
/target/ |
||||||
|
@ -0,0 +1,23 @@ |
|||||||
|
<?xml version="1.0" encoding="UTF-8"?> |
||||||
|
<projectDescription> |
||||||
|
<name>BelegScanner</name> |
||||||
|
<comment></comment> |
||||||
|
<projects> |
||||||
|
</projects> |
||||||
|
<buildSpec> |
||||||
|
<buildCommand> |
||||||
|
<name>org.eclipse.jdt.core.javabuilder</name> |
||||||
|
<arguments> |
||||||
|
</arguments> |
||||||
|
</buildCommand> |
||||||
|
<buildCommand> |
||||||
|
<name>org.eclipse.m2e.core.maven2Builder</name> |
||||||
|
<arguments> |
||||||
|
</arguments> |
||||||
|
</buildCommand> |
||||||
|
</buildSpec> |
||||||
|
<natures> |
||||||
|
<nature>org.eclipse.m2e.core.maven2Nature</nature> |
||||||
|
<nature>org.eclipse.jdt.core.javanature</nature> |
||||||
|
</natures> |
||||||
|
</projectDescription> |
@ -0,0 +1,8 @@ |
|||||||
|
eclipse.preferences.version=1 |
||||||
|
org.eclipse.jdt.core.compiler.codegen.targetPlatform=11 |
||||||
|
org.eclipse.jdt.core.compiler.compliance=11 |
||||||
|
org.eclipse.jdt.core.compiler.problem.enablePreviewFeatures=disabled |
||||||
|
org.eclipse.jdt.core.compiler.problem.forbiddenReference=warning |
||||||
|
org.eclipse.jdt.core.compiler.problem.reportPreviewFeatures=ignore |
||||||
|
org.eclipse.jdt.core.compiler.release=enabled |
||||||
|
org.eclipse.jdt.core.compiler.source=11 |
@ -0,0 +1,4 @@ |
|||||||
|
activeProfiles= |
||||||
|
eclipse.preferences.version=1 |
||||||
|
resolveWorkspaceProjects=true |
||||||
|
version=1 |
Before Width: | Height: | Size: 134 KiB |
@ -1,74 +0,0 @@ |
|||||||
<?xml version="1.0" encoding="UTF-8"?> |
|
||||||
<CONFIG> |
|
||||||
<ProjectOptions> |
|
||||||
<Version Value="11"/> |
|
||||||
<General> |
|
||||||
<SessionStorage Value="InProjectDir"/> |
|
||||||
<MainUnit Value="0"/> |
|
||||||
<Title Value="Belegscanner"/> |
|
||||||
<ResourceType Value="res"/> |
|
||||||
<UseXPManifest Value="True"/> |
|
||||||
<Icon Value="0"/> |
|
||||||
</General> |
|
||||||
<BuildModes Count="1"> |
|
||||||
<Item1 Name="Default" Default="True"/> |
|
||||||
</BuildModes> |
|
||||||
<PublishOptions> |
|
||||||
<Version Value="2"/> |
|
||||||
</PublishOptions> |
|
||||||
<RunParams> |
|
||||||
<FormatVersion Value="2"/> |
|
||||||
<Modes Count="1"> |
|
||||||
<Mode0 Name="default"/> |
|
||||||
</Modes> |
|
||||||
</RunParams> |
|
||||||
<RequiredPackages Count="1"> |
|
||||||
<Item1> |
|
||||||
<PackageName Value="LCL"/> |
|
||||||
</Item1> |
|
||||||
</RequiredPackages> |
|
||||||
<Units Count="2"> |
|
||||||
<Unit0> |
|
||||||
<Filename Value="Belegscanner.lpr"/> |
|
||||||
<IsPartOfProject Value="True"/> |
|
||||||
</Unit0> |
|
||||||
<Unit1> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<IsPartOfProject Value="True"/> |
|
||||||
<ComponentName Value="ScanForm"/> |
|
||||||
<HasResources Value="True"/> |
|
||||||
<ResourceBaseClass Value="Form"/> |
|
||||||
</Unit1> |
|
||||||
</Units> |
|
||||||
</ProjectOptions> |
|
||||||
<CompilerOptions> |
|
||||||
<Version Value="11"/> |
|
||||||
<Target> |
|
||||||
<Filename Value="Belegscanner"/> |
|
||||||
</Target> |
|
||||||
<SearchPaths> |
|
||||||
<IncludeFiles Value="$(ProjOutDir)"/> |
|
||||||
<UnitOutputDirectory Value="lib/$(TargetCPU)-$(TargetOS)"/> |
|
||||||
</SearchPaths> |
|
||||||
<Linking> |
|
||||||
<Options> |
|
||||||
<Win32> |
|
||||||
<GraphicApplication Value="True"/> |
|
||||||
</Win32> |
|
||||||
</Options> |
|
||||||
</Linking> |
|
||||||
</CompilerOptions> |
|
||||||
<Debugging> |
|
||||||
<Exceptions Count="3"> |
|
||||||
<Item1> |
|
||||||
<Name Value="EAbort"/> |
|
||||||
</Item1> |
|
||||||
<Item2> |
|
||||||
<Name Value="ECodetoolError"/> |
|
||||||
</Item2> |
|
||||||
<Item3> |
|
||||||
<Name Value="EFOpenError"/> |
|
||||||
</Item3> |
|
||||||
</Exceptions> |
|
||||||
</Debugging> |
|
||||||
</CONFIG> |
|
@ -1,21 +0,0 @@ |
|||||||
program Belegscanner; |
|
||||||
|
|
||||||
{$mode objfpc}{$H+} |
|
||||||
|
|
||||||
uses |
|
||||||
{$IFDEF UNIX} |
|
||||||
cthreads, |
|
||||||
{$ENDIF} |
|
||||||
Interfaces, // this includes the LCL widgetset |
|
||||||
Forms, scanner |
|
||||||
{ you can add units after this }; |
|
||||||
|
|
||||||
{$R *.res} |
|
||||||
|
|
||||||
begin |
|
||||||
RequireDerivedFormResource:=True; |
|
||||||
Application.Initialize; |
|
||||||
Application.CreateForm(TScanForm, ScanForm); |
|
||||||
Application.Run; |
|
||||||
end. |
|
||||||
|
|
@ -1,260 +0,0 @@ |
|||||||
<?xml version="1.0" encoding="UTF-8"?> |
|
||||||
<CONFIG> |
|
||||||
<ProjectSession> |
|
||||||
<Version Value="11"/> |
|
||||||
<BuildModes Active="Default"/> |
|
||||||
<Units Count="16"> |
|
||||||
<Unit0> |
|
||||||
<Filename Value="Belegscanner.lpr"/> |
|
||||||
<IsPartOfProject Value="True"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<CursorPos X="17" Y="10"/> |
|
||||||
<UsageCount Value="36"/> |
|
||||||
</Unit0> |
|
||||||
<Unit1> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<IsPartOfProject Value="True"/> |
|
||||||
<ComponentName Value="ScanForm"/> |
|
||||||
<HasResources Value="True"/> |
|
||||||
<ResourceBaseClass Value="Form"/> |
|
||||||
<IsVisibleTab Value="True"/> |
|
||||||
<TopLine Value="374"/> |
|
||||||
<CursorPos X="45" Y="377"/> |
|
||||||
<UsageCount Value="36"/> |
|
||||||
<Loaded Value="True"/> |
|
||||||
<LoadedDesigner Value="True"/> |
|
||||||
</Unit1> |
|
||||||
<Unit2> |
|
||||||
<Filename Value="/usr/share/fpcsrc/3.0.4/rtl/objpas/sysutils/syshelph.inc"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="111"/> |
|
||||||
<CursorPos X="14" Y="151"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit2> |
|
||||||
<Unit3> |
|
||||||
<Filename Value="/usr/lib/lazarus/1.8.2/lcl/extdlgs.pas"/> |
|
||||||
<UnitName Value="ExtDlgs"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="175"/> |
|
||||||
<CursorPos X="29" Y="215"/> |
|
||||||
<UsageCount Value="9"/> |
|
||||||
</Unit3> |
|
||||||
<Unit4> |
|
||||||
<Filename Value="/usr/lib/lazarus/1.8.2/lcl/stdctrls.pp"/> |
|
||||||
<UnitName Value="StdCtrls"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="389"/> |
|
||||||
<CursorPos X="14" Y="437"/> |
|
||||||
<UsageCount Value="9"/> |
|
||||||
</Unit4> |
|
||||||
<Unit5> |
|
||||||
<Filename Value="/usr/share/fpcsrc/3.0.4/packages/fcl-process/src/process.pp"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="99"/> |
|
||||||
<CursorPos X="14" Y="131"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit5> |
|
||||||
<Unit6> |
|
||||||
<Filename Value="/usr/lib/lazarus/1.8.2/lcl/interfaces/gtk2/gtk2int.pas"/> |
|
||||||
<UnitName Value="Gtk2Int"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="811"/> |
|
||||||
<CursorPos Y="852"/> |
|
||||||
<UsageCount Value="9"/> |
|
||||||
</Unit6> |
|
||||||
<Unit7> |
|
||||||
<Filename Value="/usr/lib/lazarus/1.8.2/lcl/graphics.pp"/> |
|
||||||
<UnitName Value="Graphics"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="1426"/> |
|
||||||
<CursorPos X="15" Y="1478"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit7> |
|
||||||
<Unit8> |
|
||||||
<Filename Value="/usr/lib/lazarus/1.8.2/lcl/include/fpimagebitmap.inc"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="100"/> |
|
||||||
<CursorPos Y="141"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit8> |
|
||||||
<Unit9> |
|
||||||
<Filename Value="/usr/share/fpcsrc/3.0.4/rtl/objpas/classes/classesh.inc"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="647"/> |
|
||||||
<CursorPos X="14" Y="681"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit9> |
|
||||||
<Unit10> |
|
||||||
<Filename Value="/usr/lib/lazarus/1.8.2/lcl/calendar.pp"/> |
|
||||||
<UnitName Value="Calendar"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="64"/> |
|
||||||
<CursorPos X="14" Y="104"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit10> |
|
||||||
<Unit11> |
|
||||||
<Filename Value="scanner.lfm"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<CursorPos X="20" Y="22"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
<DefaultSyntaxHighlighter Value="LFM"/> |
|
||||||
</Unit11> |
|
||||||
<Unit12> |
|
||||||
<Filename Value="/usr/share/fpcsrc/3.0.4/rtl/objpas/sysutils/filutilh.inc"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="110"/> |
|
||||||
<CursorPos X="10" Y="155"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit12> |
|
||||||
<Unit13> |
|
||||||
<Filename Value="/usr/share/fpcsrc/3.0.4/rtl/unix/unix.pp"/> |
|
||||||
<UnitName Value="Unix"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="58"/> |
|
||||||
<CursorPos X="6" Y="98"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit13> |
|
||||||
<Unit14> |
|
||||||
<Filename Value="/usr/lib/lazarus/1.8.2/lcl/controls.pp"/> |
|
||||||
<UnitName Value="Controls"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<TopLine Value="1663"/> |
|
||||||
<CursorPos X="14" Y="1696"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit14> |
|
||||||
<Unit15> |
|
||||||
<Filename Value="/usr/lib/lazarus/2.0.6/components/lazutils/laztracer.pas"/> |
|
||||||
<UnitName Value="LazTracer"/> |
|
||||||
<EditorIndex Value="-1"/> |
|
||||||
<CursorPos Y="50"/> |
|
||||||
<UsageCount Value="10"/> |
|
||||||
</Unit15> |
|
||||||
</Units> |
|
||||||
<JumpHistory Count="30" HistoryIndex="29"> |
|
||||||
<Position1> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="207" Column="21" TopLine="173"/> |
|
||||||
</Position1> |
|
||||||
<Position2> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="215" Column="22" TopLine="175"/> |
|
||||||
</Position2> |
|
||||||
<Position3> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="207" Column="82" TopLine="175"/> |
|
||||||
</Position3> |
|
||||||
<Position4> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="62" Column="42" TopLine="29"/> |
|
||||||
</Position4> |
|
||||||
<Position5> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="60" Column="61" TopLine="27"/> |
|
||||||
</Position5> |
|
||||||
<Position6> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="62" Column="42" TopLine="29"/> |
|
||||||
</Position6> |
|
||||||
<Position7> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="432" Column="5" TopLine="364"/> |
|
||||||
</Position7> |
|
||||||
<Position8> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="62" Column="42" TopLine="29"/> |
|
||||||
</Position8> |
|
||||||
<Position9> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="56" Column="40" TopLine="27"/> |
|
||||||
</Position9> |
|
||||||
<Position10> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="62" Column="32" TopLine="29"/> |
|
||||||
</Position10> |
|
||||||
<Position11> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="59" Column="37" TopLine="27"/> |
|
||||||
</Position11> |
|
||||||
<Position12> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="203" Column="45" TopLine="187"/> |
|
||||||
</Position12> |
|
||||||
<Position13> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="62" Column="39" TopLine="19"/> |
|
||||||
</Position13> |
|
||||||
<Position14> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="208" Column="13" TopLine="174"/> |
|
||||||
</Position14> |
|
||||||
<Position15> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="213" Column="13" TopLine="174"/> |
|
||||||
</Position15> |
|
||||||
<Position16> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="206" Column="19" TopLine="176"/> |
|
||||||
</Position16> |
|
||||||
<Position17> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="214" Column="42" TopLine="177"/> |
|
||||||
</Position17> |
|
||||||
<Position18> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="217" Column="93" TopLine="177"/> |
|
||||||
</Position18> |
|
||||||
<Position19> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="219" Column="65" TopLine="183"/> |
|
||||||
</Position19> |
|
||||||
<Position20> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="204" Column="117" TopLine="186"/> |
|
||||||
</Position20> |
|
||||||
<Position21> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="203" Column="117" TopLine="203"/> |
|
||||||
</Position21> |
|
||||||
<Position22> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="204" Column="117" TopLine="204"/> |
|
||||||
</Position22> |
|
||||||
<Position23> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="403" Column="63" TopLine="365"/> |
|
||||||
</Position23> |
|
||||||
<Position24> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="376" Column="32" TopLine="320"/> |
|
||||||
</Position24> |
|
||||||
<Position25> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="382" Column="24" TopLine="320"/> |
|
||||||
</Position25> |
|
||||||
<Position26> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="21" Column="19"/> |
|
||||||
</Position26> |
|
||||||
<Position27> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="100" Column="26" TopLine="34"/> |
|
||||||
</Position27> |
|
||||||
<Position28> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="382" Column="24" TopLine="316"/> |
|
||||||
</Position28> |
|
||||||
<Position29> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="21" Column="19"/> |
|
||||||
</Position29> |
|
||||||
<Position30> |
|
||||||
<Filename Value="scanner.pas"/> |
|
||||||
<Caret Line="116" Column="134" TopLine="67"/> |
|
||||||
</Position30> |
|
||||||
</JumpHistory> |
|
||||||
<RunParams> |
|
||||||
<FormatVersion Value="2"/> |
|
||||||
<Modes Count="0" ActiveMode="default"/> |
|
||||||
</RunParams> |
|
||||||
</ProjectSession> |
|
||||||
</CONFIG> |
|
Binary file not shown.
@ -0,0 +1,52 @@ |
|||||||
|
<project xmlns="http://maven.apache.org/POM/4.0.0" |
||||||
|
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" |
||||||
|
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"> |
||||||
|
<modelVersion>4.0.0</modelVersion> |
||||||
|
<groupId>BelegScanner</groupId> |
||||||
|
<artifactId>BelegScanner</artifactId> |
||||||
|
<version>0.0.2</version> |
||||||
|
<name>BelegScanner</name> |
||||||
|
|
||||||
|
<dependencies> |
||||||
|
<dependency> |
||||||
|
<groupId>de.srsoftware</groupId> |
||||||
|
<artifactId>tools</artifactId> |
||||||
|
<version>1.1.17</version> |
||||||
|
<scope>compile</scope> |
||||||
|
</dependency> |
||||||
|
<dependency> |
||||||
|
<groupId>de.srsoftware</groupId> |
||||||
|
<artifactId>tools.translations</artifactId> |
||||||
|
<version>1.1.3</version> |
||||||
|
<scope>compile</scope> |
||||||
|
</dependency> |
||||||
|
<dependency> |
||||||
|
<groupId>de.srsoftware</groupId> |
||||||
|
<artifactId>tools.gui.selectcombobox</artifactId> |
||||||
|
<version>0.1.1</version> |
||||||
|
<scope>compile</scope> |
||||||
|
</dependency> |
||||||
|
<dependency> |
||||||
|
<groupId>org.json</groupId> |
||||||
|
<artifactId>json</artifactId> |
||||||
|
<version>20200518</version> |
||||||
|
</dependency> |
||||||
|
<dependency> |
||||||
|
<groupId>ch.qos.logback</groupId> |
||||||
|
<artifactId>logback-classic</artifactId> |
||||||
|
<version>1.2.3</version> |
||||||
|
</dependency> |
||||||
|
</dependencies> |
||||||
|
|
||||||
|
<build> |
||||||
|
<plugins> |
||||||
|
<plugin> |
||||||
|
<artifactId>maven-compiler-plugin</artifactId> |
||||||
|
<version>3.8.1</version> |
||||||
|
<configuration> |
||||||
|
<release>11</release> |
||||||
|
</configuration> |
||||||
|
</plugin> |
||||||
|
</plugins> |
||||||
|
</build> |
||||||
|
</project> |
@ -1,226 +0,0 @@ |
|||||||
object ScanForm: TScanForm |
|
||||||
Left = 2222 |
|
||||||
Height = 880 |
|
||||||
Top = 198 |
|
||||||
Width = 1188 |
|
||||||
Caption = 'Belegscanner' |
|
||||||
ClientHeight = 880 |
|
||||||
ClientWidth = 1188 |
|
||||||
OnCreate = FormCreate |
|
||||||
LCLVersion = '2.0.6.0' |
|
||||||
object TypeSelector: TComboBox |
|
||||||
Left = 904 |
|
||||||
Height = 27 |
|
||||||
Top = 208 |
|
||||||
Width = 276 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Enabled = False |
|
||||||
ItemHeight = 0 |
|
||||||
OnChange = TypeSelectorChange |
|
||||||
OnKeyDown = ComboKey |
|
||||||
TabOrder = 1 |
|
||||||
Text = 'Herkunft' |
|
||||||
end |
|
||||||
object Origin: TComboBox |
|
||||||
Left = 904 |
|
||||||
Height = 27 |
|
||||||
Top = 240 |
|
||||||
Width = 272 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Enabled = False |
|
||||||
ItemHeight = 0 |
|
||||||
OnChange = OriginChange |
|
||||||
OnKeyDown = ComboKey |
|
||||||
TabOrder = 3 |
|
||||||
Text = 'Start' |
|
||||||
end |
|
||||||
object Destination: TComboBox |
|
||||||
Left = 904 |
|
||||||
Height = 27 |
|
||||||
Top = 304 |
|
||||||
Width = 272 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Enabled = False |
|
||||||
ItemHeight = 0 |
|
||||||
OnChange = DestinationChange |
|
||||||
OnKeyDown = ComboKey |
|
||||||
TabOrder = 5 |
|
||||||
Text = 'Ziel' |
|
||||||
end |
|
||||||
object FolderName: TLabel |
|
||||||
Left = 8 |
|
||||||
Height = 17 |
|
||||||
Top = 842 |
|
||||||
Width = 101 |
|
||||||
Anchors = [akLeft, akBottom] |
|
||||||
Caption = 'Ordnername' |
|
||||||
Font.Height = -16 |
|
||||||
Font.Name = 'Sans' |
|
||||||
ParentColor = False |
|
||||||
ParentFont = False |
|
||||||
end |
|
||||||
object Product: TComboBox |
|
||||||
Left = 904 |
|
||||||
Height = 27 |
|
||||||
Top = 240 |
|
||||||
Width = 276 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Enabled = False |
|
||||||
ItemHeight = 0 |
|
||||||
OnChange = ProductChange |
|
||||||
OnKeyDown = ComboKey |
|
||||||
TabOrder = 2 |
|
||||||
Text = 'Produkt' |
|
||||||
Visible = False |
|
||||||
end |
|
||||||
object ScanButton: TButton |
|
||||||
Left = 904 |
|
||||||
Height = 49 |
|
||||||
Top = 400 |
|
||||||
Width = 272 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Caption = 'scannen!' |
|
||||||
Enabled = False |
|
||||||
OnClick = ScanButtonClick |
|
||||||
TabOrder = 8 |
|
||||||
end |
|
||||||
object Resolution: TComboBox |
|
||||||
Left = 904 |
|
||||||
Height = 27 |
|
||||||
Top = 368 |
|
||||||
Width = 72 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
ItemHeight = 0 |
|
||||||
ItemIndex = 0 |
|
||||||
Items.Strings = ( |
|
||||||
'150' |
|
||||||
'300' |
|
||||||
) |
|
||||||
TabOrder = 7 |
|
||||||
Text = '150' |
|
||||||
end |
|
||||||
object DPI: TLabel |
|
||||||
Left = 984 |
|
||||||
Height = 14 |
|
||||||
Top = 376 |
|
||||||
Width = 19 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Caption = 'dpi' |
|
||||||
ParentColor = False |
|
||||||
end |
|
||||||
object BaseFolder: TLabel |
|
||||||
Left = 8 |
|
||||||
Height = 17 |
|
||||||
Top = 818 |
|
||||||
Width = 89 |
|
||||||
Anchors = [akLeft, akBottom] |
|
||||||
Caption = 'BaseFolder' |
|
||||||
Font.Height = -16 |
|
||||||
Font.Name = 'Sans' |
|
||||||
ParentColor = False |
|
||||||
ParentFont = False |
|
||||||
OnClick = BaseFolderClick |
|
||||||
end |
|
||||||
object Stop: TComboBox |
|
||||||
Left = 904 |
|
||||||
Height = 27 |
|
||||||
Top = 272 |
|
||||||
Width = 272 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Enabled = False |
|
||||||
ItemHeight = 0 |
|
||||||
OnChange = StopChange |
|
||||||
OnKeyDown = ComboKey |
|
||||||
TabOrder = 4 |
|
||||||
Text = 'Zwischenhalt' |
|
||||||
end |
|
||||||
object Preview: TImage |
|
||||||
Left = 8 |
|
||||||
Height = 800 |
|
||||||
Top = 8 |
|
||||||
Width = 880 |
|
||||||
Anchors = [akTop, akLeft, akRight, akBottom] |
|
||||||
Center = True |
|
||||||
Proportional = True |
|
||||||
end |
|
||||||
object Calendar: TCalendar |
|
||||||
Left = 904 |
|
||||||
Height = 190 |
|
||||||
Top = 8 |
|
||||||
Width = 276 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
DateTime = 0 |
|
||||||
OnChange = CalendarChange |
|
||||||
TabOrder = 0 |
|
||||||
end |
|
||||||
object PicSize: TComboBox |
|
||||||
Left = 904 |
|
||||||
Height = 27 |
|
||||||
Top = 336 |
|
||||||
Width = 272 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
ItemHeight = 0 |
|
||||||
TabOrder = 6 |
|
||||||
Text = '209 x 297 mm' |
|
||||||
end |
|
||||||
object DropButton: TButton |
|
||||||
Left = 904 |
|
||||||
Height = 32 |
|
||||||
Top = 776 |
|
||||||
Width = 276 |
|
||||||
Anchors = [akRight, akBottom] |
|
||||||
Caption = 'Löschen' |
|
||||||
Enabled = False |
|
||||||
OnClick = DropButtonClick |
|
||||||
ParentShowHint = False |
|
||||||
ShowHint = True |
|
||||||
TabOrder = 9 |
|
||||||
end |
|
||||||
object Swap: TButton |
|
||||||
Left = 1048 |
|
||||||
Height = 30 |
|
||||||
Top = 368 |
|
||||||
Width = 128 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Caption = 'Start/Ziel tauschen' |
|
||||||
OnClick = SwapClick |
|
||||||
TabOrder = 10 |
|
||||||
end |
|
||||||
object extButton: TButton |
|
||||||
Left = 904 |
|
||||||
Height = 49 |
|
||||||
Top = 456 |
|
||||||
Width = 272 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Caption = 'extern öffnen' |
|
||||||
Enabled = False |
|
||||||
OnClick = extButtonClick |
|
||||||
TabOrder = 11 |
|
||||||
end |
|
||||||
object dropBtn: TButton |
|
||||||
Left = 904 |
|
||||||
Height = 49 |
|
||||||
Top = 512 |
|
||||||
Width = 272 |
|
||||||
Anchors = [akTop, akRight] |
|
||||||
Caption = 'Datensatz löschen' |
|
||||||
OnClick = dropBtnClick |
|
||||||
TabOrder = 12 |
|
||||||
end |
|
||||||
object OpenDir: TButton |
|
||||||
Left = 904 |
|
||||||
Height = 32 |
|
||||||
Top = 744 |
|
||||||
Width = 276 |
|
||||||
Anchors = [akRight, akBottom] |
|
||||||
Caption = 'Ordner öffnen' |
|
||||||
OnClick = OpenDirClick |
|
||||||
ParentShowHint = False |
|
||||||
ShowHint = True |
|
||||||
TabOrder = 13 |
|
||||||
end |
|
||||||
object BaseFolderDialog: TSelectDirectoryDialog |
|
||||||
left = 520 |
|
||||||
top = 128 |
|
||||||
end |
|
||||||
end |
|
@ -1,459 +0,0 @@ |
|||||||
unit scanner; |
|
||||||
|
|
||||||
{$mode objfpc}{$H+} |
|
||||||
|
|
||||||
interface |
|
||||||
|
|
||||||
uses |
|
||||||
Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, ExtDlgs, |
|
||||||
StdCtrls, ExtCtrls, Calendar, Unix; |
|
||||||
|
|
||||||
type |
|
||||||
|
|
||||||
{ ScanThread } |
|
||||||
ScanThread = class(TThread) |
|
||||||
private |
|
||||||
dbtn, obtn, sbtn : TButton; |
|
||||||
folder,r :String; |
|
||||||
s:TPoint; |
|
||||||
p:TImage; |
|
||||||
protected |
|
||||||
procedure Execute; override; |
|
||||||
public |
|
||||||
constructor Create(scanButton: TButton; dir: String; size: TPoint; resolution: String; preview: TImage; dropButton: TButton; openButton: TButton); |
|
||||||
end; |
|
||||||
|
|
||||||
{ TScanForm } |
|
||||||
TScanForm = class(TForm) |
|
||||||
dropBtn: TButton; |
|
||||||
OpenDir: TButton; |
|
||||||
extButton: TButton; |
|
||||||
Swap: TButton; |
|
||||||
DropButton: TButton; |
|
||||||
Calendar: TCalendar; |
|
||||||
PicSize: TComboBox; |
|
||||||
Preview: TImage; |
|
||||||
Stop: TComboBox; |
|
||||||
DPI: TLabel; |
|
||||||
BaseFolder: TLabel; |
|
||||||
Resolution: TComboBox; |
|
||||||
BaseFolderDialog: TSelectDirectoryDialog; |
|
||||||
ScanButton: TButton; |
|
||||||
Product: TComboBox; |
|
||||||
Destination: TComboBox; |
|
||||||
FolderName: TLabel; |
|
||||||
Origin: TComboBox; |
|
||||||
TypeSelector: TComboBox; |
|
||||||
|
|
||||||
procedure BaseFolderClick(Sender: TObject); |
|
||||||
procedure dropBtnClick(Sender: TObject); |
|
||||||
procedure extButtonClick(Sender: TObject); |
|
||||||
procedure DropButtonClick(Sender: TObject); |
|
||||||
procedure CalendarChange(Sender: TObject); |
|
||||||
procedure FormCreate(Sender: TObject); |
|
||||||
procedure OpenDirClick(Sender: TObject); |
|
||||||
procedure ProductChange(Sender: TObject); |
|
||||||
procedure DestinationChange(Sender: TObject); |
|
||||||
procedure OriginChange(Sender: TObject); |
|
||||||
procedure ScanButtonClick(Sender: TObject); |
|
||||||
procedure StopChange(Sender: TObject); |
|
||||||
procedure SwapClick(Sender: TObject); |
|
||||||
procedure TypeSelectorChange(Sender: TObject); |
|
||||||
function ExportConfig(): string; |
|
||||||
function ExportOptions(dropDown: TComboBox): string; |
|
||||||
procedure ComboKey(Sender: TObject; var Key: Word; Shift: TShiftState); |
|
||||||
procedure UpdateFolder(); |
|
||||||
procedure MixLocations(d1: TComboBox; d2: TComboBox; d3: TComboBox); |
|
||||||
procedure DeleteStationFrom(combo: TComboBox; station: string; defaultName : string); |
|
||||||
procedure DeleteStation(station : string); |
|
||||||
private |
|
||||||
date: TDateTime; |
|
||||||
function getSize(): TPoint; |
|
||||||
|
|
||||||
public |
|
||||||
const |
|
||||||
SCANNING : Integer = 1; |
|
||||||
IDLE: Integer = 0; |
|
||||||
end; |
|
||||||
|
|
||||||
var |
|
||||||
ScanForm: TScanForm; |
|
||||||
|
|
||||||
implementation |
|
||||||
|
|
||||||
{$R *.lfm} |
|
||||||
|
|
||||||
{ ScanThread } |
|
||||||
|
|
||||||
constructor ScanThread.Create(scanButton: TButton; dir: String; size: TPoint; resolution: String; preview: TImage; dropButton: TButton; openButton: TButton ); |
|
||||||
begin |
|
||||||
sbtn := scanButton; |
|
||||||
obtn := openButton; |
|
||||||
dbtn := dropButton; |
|
||||||
folder:=dir; |
|
||||||
s:=size; |
|
||||||
r:=resolution; |
|
||||||
p:=preview; |
|
||||||
inherited Create(false); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure ScanThread.Execute; |
|
||||||
var |
|
||||||
fname: String; |
|
||||||
num: Integer; |
|
||||||
pic: TPicture; |
|
||||||
begin |
|
||||||
ForceDirectories(folder); |
|
||||||
num := 0; |
|
||||||
repeat |
|
||||||
num := num +1; |
|
||||||
fname := 'scan_'; |
|
||||||
if (num<10) then fname:=fname+'0'; |
|
||||||
if (num<100) then fname:=fname+'0'; |
|
||||||
if (num<1000) then fname:=fname+'0'; |
|
||||||
fname := fname+IntToStr(num)+'.jpg'; |
|
||||||
until not FileExists(folder+fname); |
|
||||||
fpSystem('scanimage -x '+IntToStr(s.x)+' -y '+IntToStr(s.y)+' --mode Color --resolution '+r+' --format jpeg > "'+folder+fname+'"'); |
|
||||||
try |
|
||||||
pic:=TPicture.Create; |
|
||||||
pic.LoadFromFile(folder+fname); |
|
||||||
p.Picture:=pic; |
|
||||||
p.Hint:=folder+fname; |
|
||||||
finally |
|
||||||
end; |
|
||||||
dbtn.Hint:=folder+fname; |
|
||||||
dbtn.Caption:=fname+' löschen'; |
|
||||||
dbtn.Enabled:=true; |
|
||||||
obtn.Enabled:=true; |
|
||||||
sbtn.Enabled:=true; |
|
||||||
sbtn.Tag := TScanForm.IDLE; |
|
||||||
end; |
|
||||||
|
|
||||||
function allowed(s: String): boolean; |
|
||||||
begin |
|
||||||
Result := true; |
|
||||||
if (s = '') then Result := false; |
|
||||||
if (s = 'Start') then Result := false; |
|
||||||
if (s = 'Ziel') then Result := false; |
|
||||||
if (s = 'Zwischenhalt') then Result := false; |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.MixLocations(d1: TComboBox; d2: TComboBox; d3: TComboBox); |
|
||||||
var |
|
||||||
list: TStringList; |
|
||||||
begin |
|
||||||
list := TStringList.Create; |
|
||||||
list.Sorted := True; |
|
||||||
if (allowed(d1.Text)) then d1.Items.Add(d1.Text); |
|
||||||
if (allowed(d2.Text)) then d2.Items.Add(d2.Text); |
|
||||||
if (allowed(d3.Text)) then d3.Items.Add(d3.Text); |
|
||||||
list.Assign(d1.Items); |
|
||||||
list.AddStrings(d2.Items); |
|
||||||
list.AddStrings(d3.Items); |
|
||||||
d1.Items.Assign(list); |
|
||||||
d2.Items.Assign(list); |
|
||||||
d3.Items.Assign(list); |
|
||||||
end; |
|
||||||
|
|
||||||
function TScanForm.ExportConfig(): string; |
|
||||||
begin |
|
||||||
Result := 'folder:'+BaseFolder.Caption+#13; |
|
||||||
Result := Result + 'types:' + ExportOptions(TypeSelector) + #13; |
|
||||||
Result := Result + 'items:' + ExportOptions(Product) + #13; |
|
||||||
MixLocations(Origin, Destination, Stop); |
|
||||||
Result := Result + 'locations:' + ExportOptions(Origin) + #13; |
|
||||||
Result := Result + 'sizes:' + ExportOptions(PicSize) +#13; |
|
||||||
end; |
|
||||||
|
|
||||||
function TScanForm.ExportOptions(dropDown: TComboBox): string; |
|
||||||
var |
|
||||||
list: TStringList; |
|
||||||
item, current: string; |
|
||||||
i: integer; |
|
||||||
drop: Boolean; |
|
||||||
begin |
|
||||||
// make sure the current text appears in future lists |
|
||||||
item := dropDown.Text; |
|
||||||
drop := item.StartsWith(' '); |
|
||||||
|
|
||||||
if drop then |
|
||||||
begin |
|
||||||
i := 0; |
|
||||||
while i < dropDown.Items.Count do |
|
||||||
begin |
|
||||||
item := Trim(item); |
|
||||||
current := Trim(dropDown.Items[i]); |
|
||||||
if current = item then dropDown.Items.Delete(i) else i := i+1; |
|
||||||
end; |
|
||||||
end else dropDown.Items.Add(item); |
|
||||||
|
|
||||||
// create a StringList to sort and concatenate |
|
||||||
list := TStringList.Create; |
|
||||||
list.StrictDelimiter := True; |
|
||||||
list.Sorted := True; |
|
||||||
|
|
||||||
// put all items in the list, will sort and remove duplicates |
|
||||||
list.Assign(dropDown.Items); |
|
||||||
|
|
||||||
// update dropdown |
|
||||||
dropDown.Items.Assign(list); |
|
||||||
|
|
||||||
// return json array |
|
||||||
Result := list.DelimitedText |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.ComboKey(Sender: TObject; var Key: Word; Shift: TShiftState); |
|
||||||
var |
|
||||||
combo : TComboBox; |
|
||||||
index : integer; |
|
||||||
tx : string; |
|
||||||
begin |
|
||||||
if key = 40 then |
|
||||||
begin |
|
||||||
if TObject(Sender) is TComboBox then |
|
||||||
begin |
|
||||||
combo := TComboBox(Sender); |
|
||||||
tx := combo.Text; |
|
||||||
for index := 0 to combo.Items.Count-1 do |
|
||||||
begin |
|
||||||
if combo.Items[index].StartsWith(tx,true) then |
|
||||||
begin |
|
||||||
combo.ItemIndex:=index-1; |
|
||||||
Exit; |
|
||||||
end; |
|
||||||
end; |
|
||||||
end; |
|
||||||
end; |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.TypeSelectorChange(Sender: TObject); |
|
||||||
var |
|
||||||
state: boolean; |
|
||||||
begin |
|
||||||
TypeSelector.Tag := 1; |
|
||||||
state := TypeSelector.Text = 'Ticket'; |
|
||||||
Origin.Enabled := state; |
|
||||||
Origin.Visible := state; |
|
||||||
Stop.Enabled := state; |
|
||||||
Stop.Visible := state; |
|
||||||
Destination.Enabled := state; |
|
||||||
Destination.Visible := state; |
|
||||||
Swap.Enabled:=state; |
|
||||||
Product.Enabled := not state; |
|
||||||
Product.Visible := not state; |
|
||||||
if (ScanButton.Tag <> TScanForm.SCANNING) then ScanButton.Enabled:=true; |
|
||||||
UpdateFolder(); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.CalendarChange(Sender: TObject); |
|
||||||
begin |
|
||||||
date := Calendar.DateTime; |
|
||||||
TypeSelector.Enabled := True; |
|
||||||
UpdateFolder(); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.OriginChange(Sender: TObject); |
|
||||||
begin |
|
||||||
Origin.Tag := 1; |
|
||||||
UpdateFolder(); |
|
||||||
end; |
|
||||||
|
|
||||||
function TScanForm.getSize(): TPoint; |
|
||||||
var |
|
||||||
arr: TStringArray; |
|
||||||
s: String; |
|
||||||
w, h: Integer; |
|
||||||
begin |
|
||||||
s:=PicSize.Text; |
|
||||||
arr:=s.Split(['x','m']); |
|
||||||
w:=StrToInt(arr[0].Trim); |
|
||||||
h:=StrToInt(arr[1].Trim); |
|
||||||
PicSize.Caption:=IntToStr(w)+' x '+IntToStr(h)+' mm'; |
|
||||||
Result := TPoint.Create(w,h); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.ScanButtonClick(Sender: TObject); |
|
||||||
var |
|
||||||
config: TFileStream; |
|
||||||
filename: string; |
|
||||||
json: string; |
|
||||||
size: TPoint; |
|
||||||
begin |
|
||||||
ScanButton.Enabled:=false; |
|
||||||
ScanButton.Tag:=TScanForm.SCANNING; |
|
||||||
filename := GetEnvironmentVariable('HOME') + '/.config/belegscanner.conf'; |
|
||||||
size := getSize(); |
|
||||||
json := ExportConfig(); |
|
||||||
try |
|
||||||
config := TFilestream.Create(filename, fmCreate); |
|
||||||
config.Write(json[1], json.Length); |
|
||||||
finally |
|
||||||
config.Free; |
|
||||||
end; |
|
||||||
ScanThread.Create(ScanButton,BaseFolder.Caption+'/'+FolderName.Caption+'/',size,Resolution.Caption,Preview,DropButton,extButton); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.StopChange(Sender: TObject); |
|
||||||
begin |
|
||||||
Stop.Tag := 1; |
|
||||||
UpdateFolder(); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.SwapClick(Sender: TObject); |
|
||||||
var |
|
||||||
dummy: String; |
|
||||||
begin |
|
||||||
dummy:=Origin.Text; |
|
||||||
Origin.Text := Destination.Text; |
|
||||||
Destination.Text := dummy; |
|
||||||
UpdateFolder(); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.DestinationChange(Sender: TObject); |
|
||||||
begin |
|
||||||
Destination.Tag := 1; |
|
||||||
UpdateFolder(); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.ProductChange(Sender: TObject); |
|
||||||
begin |
|
||||||
Product.Tag := 1; |
|
||||||
UpdateFolder(); |
|
||||||
end; |
|
||||||
|
|
||||||
|
|
||||||
procedure addItemsTo(combo: TComboBox; line: String); |
|
||||||
var |
|
||||||
parts: TStringArray; |
|
||||||
fixed, part: string; |
|
||||||
begin |
|
||||||
parts := line.Split(','); |
|
||||||
for part in parts do |
|
||||||
begin |
|
||||||
fixed := part.Replace('"',''); |
|
||||||
if (fixed <> '') then combo.Items.Add(fixed); |
|
||||||
end; |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.FormCreate(Sender: TObject); |
|
||||||
var |
|
||||||
filename: String; |
|
||||||
lines: TStringList; |
|
||||||
line: String; |
|
||||||
index: integer; |
|
||||||
begin |
|
||||||
BaseFolder.Caption:=GetEnvironmentVariable('HOME'); |
|
||||||
filename := GetEnvironmentVariable('HOME') + '/.config/belegscanner.conf'; |
|
||||||
lines := TStringList.Create; |
|
||||||
Calendar.DateTime:=Now; |
|
||||||
try |
|
||||||
lines.LoadFromFile(filename); |
|
||||||
for index := 0 to lines.Count-1 do |
|
||||||
begin |
|
||||||
line:=lines.Strings[index]; |
|
||||||
if line.StartsWith('folder:') then |
|
||||||
begin |
|
||||||
line:=line.Substring(7); |
|
||||||
BaseFolder.Caption:=line; |
|
||||||
end; |
|
||||||
if line.StartsWith('types:') then addItemsTo(TypeSelector,line.Substring(6)); |
|
||||||
if line.StartsWith('items:') then addItemsTo(Product,line.Substring(6)); |
|
||||||
if line.StartsWith('sizes:') then addItemsTo(PicSize,line.Substring(6)); |
|
||||||
if line.StartsWith('locations:') then |
|
||||||
begin |
|
||||||
line := line.Substring(10); |
|
||||||
addItemsTo(Origin,line); |
|
||||||
addItemsTo(Destination,line); |
|
||||||
addItemsTo(Stop,line); |
|
||||||
end; |
|
||||||
end |
|
||||||
finally |
|
||||||
end; |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.OpenDirClick(Sender: TObject); |
|
||||||
begin |
|
||||||
WriteLn(BaseFolder.Caption); |
|
||||||
fpSystem('gio open "'+BaseFolder.Caption+'"'); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.BaseFolderClick(Sender: TObject); |
|
||||||
begin |
|
||||||
BaseFolderDialog.FileName:=BaseFolder.Caption; |
|
||||||
BaseFolderDialog.Execute; |
|
||||||
BaseFolder.Caption := BaseFolderDialog.FileName; |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.DeleteStationFrom(combo: TComboBox; station : string; defaultName : string); |
|
||||||
var |
|
||||||
index : integer; |
|
||||||
begin |
|
||||||
index := combo.Items.IndexOf(station); |
|
||||||
if index > -1 then |
|
||||||
begin |
|
||||||
combo.Items.Delete(index); |
|
||||||
combo.Text := defaultName; |
|
||||||
end; |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.DeleteStation(station : string); |
|
||||||
begin |
|
||||||
DeleteStationFrom(Origin,station,'Start'); |
|
||||||
DeleteStationFrom(Stop,station,'Zwischenhalt'); |
|
||||||
DeleteStationFrom(Destination,station,'Ziel'); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.dropBtnClick(Sender: TObject); |
|
||||||
var |
|
||||||
tx : string; |
|
||||||
begin |
|
||||||
tx := TypeSelector.Text; |
|
||||||
if (tx <> 'Herkunft') and (tx <> 'Ticket') then |
|
||||||
begin |
|
||||||
TypeSelector.Items.Delete(TypeSelector.ItemIndex); |
|
||||||
TypeSelector.Text := 'Herkunft'; |
|
||||||
end; |
|
||||||
|
|
||||||
tx := Product.Text; |
|
||||||
if Product.Enabled and (tx <> 'Produkt') then |
|
||||||
begin |
|
||||||
Product.Items.Delete(Product.ItemIndex); |
|
||||||
Product.Text := 'Produkt'; |
|
||||||
end; |
|
||||||
|
|
||||||
if Origin.Enabled and (Origin.Text <> 'Start') then deleteStation(Origin.Text); |
|
||||||
if Stop.Enabled and (Stop.Text <> 'Zwischenhalt') then deleteStation(Stop.Text); |
|
||||||
if Destination.Enabled and (Destination.Text <> 'Ziel') then deleteStation(Destination.Text); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.extButtonClick(Sender: TObject); |
|
||||||
var |
|
||||||
cmd: string; |
|
||||||
begin |
|
||||||
cmd := 'gvfs-open "'+DropButton.Hint+'"'; |
|
||||||
fpSystem(cmd); |
|
||||||
end; |
|
||||||
|
|
||||||
procedure TScanForm.DropButtonClick(Sender: TObject); |
|
||||||
begin |
|
||||||
DeleteFile(DropButton.Hint); |
|
||||||
Preview.Picture:=nil; |
|
||||||
DropButton.Enabled:=false; |
|
||||||
extButton.Enabled:=false; |
|
||||||
end; |
|
||||||
|
|
||||||
|
|
||||||
procedure TScanForm.UpdateFolder(); |
|
||||||
var |
|
||||||
tx: string; |
|
||||||
begin |
|
||||||
tx := FormatDateTime('YYYY-MM-DD', date) + ' - '; |
|
||||||
if (Product.Enabled and (Product.Tag > 0) and not( Product.Text = '') and not (Product.Text = 'Produkt')) then tx := tx + Trim(Product.Text) + ' von '; |
|
||||||
if (TypeSelector.Tag > 0) then tx := tx + Trim(TypeSelector.Text); |
|
||||||
if (Origin.Enabled and (Origin.Tag > 0)) then tx := tx + ': ' + Trim(Origin.Text); |
|
||||||
if (Stop.Enabled and (Stop.Tag > 0) and not (Stop.Text = '')and not (Stop.Text = 'Zwischenhalt')) then tx := tx + ' - ' + Trim(Stop.Text); |
|
||||||
if (Destination.Enabled and (Destination.Tag > 0)) then tx := tx + ' - ' + Trim(Destination.Text); |
|
||||||
FolderName.Caption := tx; |
|
||||||
end; |
|
||||||
|
|
||||||
end. |
|
@ -0,0 +1,14 @@ |
|||||||
|
package de.srsoftware.belegscanner; |
||||||
|
|
||||||
|
import java.io.IOException; |
||||||
|
|
||||||
|
import de.srsoftware.belegscanner.gui.MainFrame; |
||||||
|
|
||||||
|
public class Application { |
||||||
|
|
||||||
|
public static void main(String[] args) throws IOException { |
||||||
|
Configuration config = new Configuration(Constants.APPLICATION_NAME); |
||||||
|
MainFrame app = new MainFrame(config); |
||||||
|
app.setDefaultCloseOperation(MainFrame.EXIT_ON_CLOSE); |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,145 @@ |
|||||||
|
package de.srsoftware.belegscanner; |
||||||
|
|
||||||
|
import java.io.ByteArrayOutputStream; |
||||||
|
import java.io.File; |
||||||
|
import java.io.FileReader; |
||||||
|
import java.io.FileWriter; |
||||||
|
import java.io.IOException; |
||||||
|
import java.io.OutputStreamWriter; |
||||||
|
import java.nio.charset.StandardCharsets; |
||||||
|
|
||||||
|
import org.json.JSONArray; |
||||||
|
import org.json.JSONObject; |
||||||
|
import org.slf4j.Logger; |
||||||
|
import org.slf4j.LoggerFactory; |
||||||
|
|
||||||
|
public class Configuration { |
||||||
|
|
||||||
|
private static final Logger LOG = LoggerFactory.getLogger(Configuration.class); |
||||||
|
private File file; |
||||||
|
private JSONObject json = new JSONObject(); |
||||||
|
|
||||||
|
public Configuration(String appName) throws IOException { |
||||||
|
String home = System.getProperty("user.home"); |
||||||
|
String fileName = new StringBuilder().append(home).append(File.separator).append(".config").append(File.separator).append(appName).append(File.separator).append("config.json").toString(); |
||||||
|
file = new File(fileName); |
||||||
|
if (file.exists()) { |
||||||
|
LOG.info("{} found, loading…",file); |
||||||
|
FileReader in = new FileReader(file); |
||||||
|
ByteArrayOutputStream buffer = new ByteArrayOutputStream(); |
||||||
|
OutputStreamWriter writer = new OutputStreamWriter(buffer); |
||||||
|
in.transferTo(writer); |
||||||
|
writer.close(); |
||||||
|
String jsonString = buffer.toString(StandardCharsets.UTF_8); |
||||||
|
LOG.debug("Loaded json: {}",jsonString); |
||||||
|
json = jsonString.startsWith("{") ? new JSONObject(jsonString) : new JSONObject(); |
||||||
|
in.close(); |
||||||
|
} else { |
||||||
|
LOG.info("{} not found, creating new config.",file); |
||||||
|
json = new JSONObject(); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
private void save() throws IOException { |
||||||
|
LOG.debug("Trying to save config…"); |
||||||
|
File dir = file.getParentFile(); |
||||||
|
if (!dir.exists()) dir.mkdirs(); |
||||||
|
FileWriter out = new FileWriter(file); |
||||||
|
json.write(out, 2, 0); |
||||||
|
out.close(); |
||||||
|
} |
||||||
|
|
||||||
|
public JSONArray getOrCreateArray(String key) { |
||||||
|
LOG.debug("requesting {} from config.",key); |
||||||
|
String[] parts = key.split("\\."); |
||||||
|
JSONObject localJson = json; |
||||||
|
boolean update = false; |
||||||
|
JSONArray result = null; |
||||||
|
for (int i=0; i<parts.length; i++) { |
||||||
|
String localKey = parts[i]; |
||||||
|
LOG.debug("localKey = {}",localKey); |
||||||
|
boolean lastPart = i == parts.length-1; |
||||||
|
if (!localJson.has(localKey)) { |
||||||
|
LOG.debug("{} not present in {}, creating…",localKey,localJson); |
||||||
|
localJson.put(localKey, lastPart ? new JSONArray() : new JSONObject()); |
||||||
|
update = true; |
||||||
|
} |
||||||
|
if (lastPart) { |
||||||
|
result = localJson.getJSONArray(localKey); |
||||||
|
} else localJson = localJson.getJSONObject(localKey); |
||||||
|
} |
||||||
|
if (update) try { |
||||||
|
save(); |
||||||
|
} catch (IOException ex) { |
||||||
|
LOG.warn("Was not able to write config to {}!",file); |
||||||
|
} |
||||||
|
return result; |
||||||
|
} |
||||||
|
|
||||||
|
@SuppressWarnings("unchecked") |
||||||
|
public <T> T get(String key) { |
||||||
|
LOG.debug("requesting {} from config.",key); |
||||||
|
String[] parts = key.split("\\."); |
||||||
|
JSONObject localJson = json; |
||||||
|
for (int i=0; i<parts.length; i++) { |
||||||
|
String localKey = parts[i]; |
||||||
|
LOG.debug("localKey = {}",localKey); |
||||||
|
boolean lastPart = i == parts.length-1; |
||||||
|
if (!localJson.has(localKey)) return null; |
||||||
|
if (lastPart) return (T) localJson.get(localKey); |
||||||
|
localJson = localJson.getJSONObject(localKey); |
||||||
|
} |
||||||
|
return null; |
||||||
|
} |
||||||
|
|
||||||
|
@SuppressWarnings("unchecked") |
||||||
|
public <T> T getOrCreate(String key, T preset) { |
||||||
|
LOG.debug("requesting {} from config.",key); |
||||||
|
String[] parts = key.split("\\."); |
||||||
|
JSONObject localJson = json; |
||||||
|
boolean update = false; |
||||||
|
Object result = preset; |
||||||
|
for (int i=0; i<parts.length; i++) { |
||||||
|
String localKey = parts[i]; |
||||||
|
LOG.debug("localKey = {}",localKey); |
||||||
|
boolean lastPart = i == parts.length-1; |
||||||
|
if (!localJson.has(localKey)) { |
||||||
|
LOG.debug("{} not present in {}, creating…",localKey,localJson); |
||||||
|
localJson.put(localKey, lastPart ? preset : new JSONObject()); |
||||||
|
update = true; |
||||||
|
} |
||||||
|
if (lastPart) { |
||||||
|
result = localJson.get(localKey); |
||||||
|
} else localJson = localJson.getJSONObject(localKey); |
||||||
|
} |
||||||
|
if (update) try { |
||||||
|
save(); |
||||||
|
} catch (IOException ex) { |
||||||
|
LOG.warn("Was not able to write config to {}!",file); |
||||||
|
} |
||||||
|
return (T) result; |
||||||
|
} |
||||||
|
|
||||||
|
public void set(String key, Object value) { |
||||||
|
LOG.debug("setting {} to {}",key,value); |
||||||
|
String[] parts = key.split("\\."); |
||||||
|
JSONObject localJson = json; |
||||||
|
for (int i=0; i<parts.length; i++) { |
||||||
|
String localKey = parts[i]; |
||||||
|
LOG.debug("localKey = {}",localKey); |
||||||
|
boolean lastPart = i == parts.length-1; |
||||||
|
if (!localJson.has(localKey)) { |
||||||
|
LOG.debug("{} not present in {}, creating…",localKey,localJson); |
||||||
|
localJson.put(localKey, lastPart ? value : new JSONObject()); |
||||||
|
} |
||||||
|
if (lastPart) break; |
||||||
|
localJson = localJson.getJSONObject(localKey); |
||||||
|
} |
||||||
|
LOG.debug("altered json: {}",json); |
||||||
|
try { |
||||||
|
save(); |
||||||
|
} catch (IOException ex) { |
||||||
|
LOG.warn("Was not able to write config to {}!",file); |
||||||
|
} |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,7 @@ |
|||||||
|
package de.srsoftware.belegscanner; |
||||||
|
|
||||||
|
public class Constants { |
||||||
|
|
||||||
|
public static final String APPLICATION_NAME = "BelegScanner"; |
||||||
|
|
||||||
|
} |
@ -0,0 +1,112 @@ |
|||||||
|
package de.srsoftware.belegscanner.gui; |
||||||
|
|
||||||
|
import java.awt.EventQueue; |
||||||
|
import java.awt.event.ItemEvent; |
||||||
|
import java.awt.event.ItemListener; |
||||||
|
import java.awt.event.KeyAdapter; |
||||||
|
import java.awt.event.KeyEvent; |
||||||
|
import java.util.ArrayList; |
||||||
|
import java.util.List; |
||||||
|
|
||||||
|
import javax.swing.DefaultComboBoxModel; |
||||||
|
import javax.swing.JComboBox; |
||||||
|
import javax.swing.JFrame; |
||||||
|
import javax.swing.JTextField; |
||||||
|
import javax.swing.SwingUtilities; |
||||||
|
|
||||||
|
public class FilterComboBoxText { |
||||||
|
|
||||||
|
private JFrame frame; |
||||||
|
private final JComboBox<String> comboBox = new JComboBox<>(); |
||||||
|
private static List<String>listForComboBox= new ArrayList<String>(); |
||||||
|
|
||||||
|
/** |
||||||
|
* Launch the application. |
||||||
|
*/ |
||||||
|
public static void main(String[] args) { |
||||||
|
EventQueue.invokeLater(new Runnable() { |
||||||
|
public void run() { |
||||||
|
try { |
||||||
|
FilterComboBoxText window = new FilterComboBoxText(); |
||||||
|
window.frame.setVisible(true); |
||||||
|
} catch (Exception e) { |
||||||
|
e.printStackTrace(); |
||||||
|
} |
||||||
|
} |
||||||
|
}); |
||||||
|
|
||||||
|
listForComboBox.add("Lion"); |
||||||
|
listForComboBox.add("LionKing"); |
||||||
|
listForComboBox.add("Mufasa"); |
||||||
|
listForComboBox.add("Nala"); |
||||||
|
listForComboBox.add("KingNala"); |
||||||
|
listForComboBox.add("Animals"); |
||||||
|
listForComboBox.add("Anims"); |
||||||
|
listForComboBox.add("Fish"); |
||||||
|
listForComboBox.add("Jelly Fish"); |
||||||
|
listForComboBox.add("I am the boss"); |
||||||
|
|
||||||
|
|
||||||
|
} |
||||||
|
|
||||||
|
public FilterComboBoxText() { |
||||||
|
initialize(); |
||||||
|
} |
||||||
|
|
||||||
|
private void initialize() { |
||||||
|
frame = new JFrame(); |
||||||
|
frame.setBounds(100, 100, 412, 165); |
||||||
|
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); |
||||||
|
frame.getContentPane().setLayout(null); |
||||||
|
comboBox.setEditable(true); |
||||||
|
|
||||||
|
comboBox.addItemListener(new ItemListener() { |
||||||
|
public void itemStateChanged(ItemEvent arg0) { |
||||||
|
|
||||||
|
} |
||||||
|
}); |
||||||
|
|
||||||
|
for(String detail : listForComboBox) comboBox.addItem(detail); |
||||||
|
final JTextField textfield = (JTextField) comboBox.getEditor().getEditorComponent(); |
||||||
|
textfield.addKeyListener(new KeyAdapter() { |
||||||
|
public void keyReleased(KeyEvent ke) { |
||||||
|
SwingUtilities.invokeLater(new Runnable() { |
||||||
|
public void run() { |
||||||
|
if(!textfield.getText().isEmpty()){ |
||||||
|
comboBoxFilter(textfield.getText()); |
||||||
|
} |
||||||
|
} |
||||||
|
}); |
||||||
|
|
||||||
|
} |
||||||
|
}); |
||||||
|
comboBox.setBounds(10, 39, 364, 29); |
||||||
|
frame.getContentPane().add(comboBox); |
||||||
|
} |
||||||
|
|
||||||
|
public void comboBoxFilter(String enteredText) { |
||||||
|
System.out.println(comboBox.getItemCount()); |
||||||
|
|
||||||
|
if (!comboBox.isPopupVisible()) { |
||||||
|
comboBox.showPopup(); |
||||||
|
} |
||||||
|
|
||||||
|
List<String> filterArray= new ArrayList<String>(); |
||||||
|
for (int i = 0; i < listForComboBox.size(); i++) { |
||||||
|
if (listForComboBox.get(i).toLowerCase().contains(enteredText.toLowerCase())) { |
||||||
|
filterArray.add(listForComboBox.get(i)); |
||||||
|
} |
||||||
|
} |
||||||
|
if (filterArray.size() > 0) { |
||||||
|
DefaultComboBoxModel<String> model = (DefaultComboBoxModel<String>) comboBox.getModel(); |
||||||
|
model.removeAllElements(); |
||||||
|
model.addElement(""); |
||||||
|
for (String s: filterArray) |
||||||
|
model.addElement(s); |
||||||
|
|
||||||
|
JTextField textfield = (JTextField) comboBox.getEditor().getEditorComponent(); |
||||||
|
textfield.setText(enteredText); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
} |
@ -0,0 +1,118 @@ |
|||||||
|
package de.srsoftware.belegscanner.gui; |
||||||
|
|
||||||
|
import java.awt.BorderLayout; |
||||||
|
import java.awt.Dimension; |
||||||
|
import java.awt.event.ActionEvent; |
||||||
|
import java.util.Date; |
||||||
|
import java.util.HashMap; |
||||||
|
import java.util.Map.Entry; |
||||||
|
import java.util.Vector; |
||||||
|
import java.util.regex.Matcher; |
||||||
|
import java.util.regex.Pattern; |
||||||
|
|
||||||
|
import javax.swing.JFrame; |
||||||
|
|
||||||
|
import org.slf4j.Logger; |
||||||
|
import org.slf4j.LoggerFactory; |
||||||
|
|
||||||
|
import de.srsoftware.belegscanner.Configuration; |
||||||
|
|
||||||
|
|
||||||
|
public class MainFrame extends JFrame { |
||||||
|
private static final Logger LOG = LoggerFactory.getLogger(MainFrame.class); |
||||||
|
|
||||||
|
private static final long serialVersionUID = 210283601541223645L; |
||||||
|
|
||||||
|
private static final String HOME = System.getProperty("user.home"); |
||||||
|
private static final Pattern MARKEN = Pattern.compile("\\$([a-zA-Z]+)"); |
||||||
|
|
||||||
|
private StatusBar statusBar; |
||||||
|
private Toolbar toolbar; |
||||||
|
|
||||||
|
private HashMap<String,String> fields = new HashMap<>(); |
||||||
|
|
||||||
|
private String path = ""; |
||||||
|
|
||||||
|
private String category =""; |
||||||
|
|
||||||
|
private Date date = new Date(); |
||||||
|
|
||||||
|
private String patchedPath = ""; |
||||||
|
|
||||||
|
private Configuration config; |
||||||
|
|
||||||
|
public MainFrame(Configuration config) { |
||||||
|
this.config = config; |
||||||
|
int width = config.getOrCreate("app.main.dimenstion.w",800); |
||||||
|
int height = config.getOrCreate("app.main.dimenstion.h",600); |
||||||
|
|
||||||
|
BorderLayout layout = new BorderLayout(); |
||||||
|
setLayout(layout); |
||||||
|
|
||||||
|
toolbar = new Toolbar(config); |
||||||
|
statusBar = new StatusBar(); |
||||||
|
|
||||||
|
add(toolbar,BorderLayout.EAST); |
||||||
|
add(statusBar,BorderLayout.SOUTH); |
||||||
|
toolbar.addCategoryListener(this::setCategory) |
||||||
|
.addDateListener(this::setDate) |
||||||
|
.addFieldListener(this::setField) |
||||||
|
.addPathListener(this::setPath) |
||||||
|
.addScanListener(this::scan); |
||||||
|
|
||||||
|
setPreferredSize(new Dimension(width,height)); |
||||||
|
pack(); |
||||||
|
setVisible(true); |
||||||
|
} |
||||||
|
|
||||||
|
private void addFieldsFor(String path) { |
||||||
|
Vector<String> marks = new Vector<>(); |
||||||
|
Matcher matches = MARKEN.matcher(path); |
||||||
|
while (matches.find()) marks.add(matches.group(1)); |
||||||
|
toolbar.addFieldsFor(marks); |
||||||
|
}; |
||||||
|
|
||||||
|
private void scan(ActionEvent ev) { |
||||||
|
LOG.debug("Scanning into '{}'",patchedPath); |
||||||
|
config.set("app.categories."+category+".path",path); |
||||||
|
} |
||||||
|
|
||||||
|
private void setCategory(String category) { |
||||||
|
this.category = category; |
||||||
|
updatePath(); |
||||||
|
|
||||||
|
} |
||||||
|
|
||||||
|
private void setDate(Date date) { |
||||||
|
this.date = date; |
||||||
|
updatePath(); |
||||||
|
} |
||||||
|
|
||||||
|
private void setField(String key, String val) { |
||||||
|
fields.put(key, val); |
||||||
|
updatePath(); |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
private void setPath(String path) { |
||||||
|
this.path = path; |
||||||
|
updatePath(); |
||||||
|
} |
||||||
|
|
||||||
|
@SuppressWarnings("deprecation") |
||||||
|
private void updatePath() { |
||||||
|
LOG.debug("updatePath() [path = {}]",path); |
||||||
|
int year = 1900+date.getYear(); |
||||||
|
int month = date.getMonth()+1; |
||||||
|
int day = date.getDate(); |
||||||
|
patchedPath = path.replace("$HOME",HOME) |
||||||
|
.replace("$KATEGORIE", category) |
||||||
|
.replace("$JAHR", year+"") |
||||||
|
.replace("$MONAT", month<10 ? "0"+month : ""+month) |
||||||
|
.replace("$TAG", day < 10 ? "0"+day : ""+day); |
||||||
|
|
||||||
|
addFieldsFor(patchedPath); |
||||||
|
for (Entry<String, String> entry : fields.entrySet()) patchedPath = patchedPath.replace("$"+entry.getKey(), entry.getValue()); |
||||||
|
statusBar.setPath(patchedPath); |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,27 @@ |
|||||||
|
package de.srsoftware.belegscanner.gui; |
||||||
|
|
||||||
|
import javax.swing.BoxLayout; |
||||||
|
import javax.swing.JLabel; |
||||||
|
import javax.swing.JPanel; |
||||||
|
|
||||||
|
import org.slf4j.Logger; |
||||||
|
import org.slf4j.LoggerFactory; |
||||||
|
|
||||||
|
public class StatusBar extends JPanel { |
||||||
|
|
||||||
|
private static final Logger LOG = LoggerFactory.getLogger(StatusBar.class); |
||||||
|
|
||||||
|
private static final long serialVersionUID = 8102800846089594705L; |
||||||
|
private JLabel path; |
||||||
|
|
||||||
|
public StatusBar() { |
||||||
|
setLayout(new BoxLayout(this, BoxLayout.Y_AXIS)); |
||||||
|
add(path = new JLabel()); |
||||||
|
} |
||||||
|
|
||||||
|
public StatusBar setPath(String path) { |
||||||
|
LOG.debug("setPath({})",path); |
||||||
|
this.path.setText(path); |
||||||
|
return this; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,195 @@ |
|||||||
|
package de.srsoftware.belegscanner.gui; |
||||||
|
|
||||||
|
import java.awt.Component; |
||||||
|
import java.awt.Dimension; |
||||||
|
import java.awt.event.ActionEvent; |
||||||
|
import java.awt.event.ActionListener; |
||||||
|
import java.util.Date; |
||||||
|
import java.util.HashMap; |
||||||
|
import java.util.HashSet; |
||||||
|
import java.util.List; |
||||||
|
import java.util.Vector; |
||||||
|
import java.util.stream.Collectors; |
||||||
|
|
||||||
|
import javax.swing.BoxLayout; |
||||||
|
import javax.swing.JButton; |
||||||
|
import javax.swing.JLabel; |
||||||
|
import javax.swing.JPanel; |
||||||
|
|
||||||
|
import org.json.JSONObject; |
||||||
|
import org.slf4j.Logger; |
||||||
|
import org.slf4j.LoggerFactory; |
||||||
|
|
||||||
|
import de.srsoftware.belegscanner.Configuration; |
||||||
|
import de.srsoftware.tools.gui.DateChooser; |
||||||
|
import de.srsoftware.tools.gui.SelectComboBox; |
||||||
|
|
||||||
|
public class Toolbar extends JPanel { |
||||||
|
|
||||||
|
private static final Logger LOG = LoggerFactory.getLogger(Toolbar.class); |
||||||
|
|
||||||
|
public interface CategoryListener{ |
||||||
|
public void setCategory(String category); |
||||||
|
} |
||||||
|
|
||||||
|
public interface DateListener{ |
||||||
|
public void setDate(Date date); |
||||||
|
} |
||||||
|
|
||||||
|
public interface FieldListener{ |
||||||
|
public void setField(String name, String value); |
||||||
|
} |
||||||
|
|
||||||
|
public interface PathListener{ |
||||||
|
public void setPath(String path); |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
private static final long serialVersionUID = -5834326573752788233L; |
||||||
|
|
||||||
|
private Vector<Object> categories = new Vector<>(); |
||||||
|
private Vector<Object> paths = new Vector<>(); |
||||||
|
|
||||||
|
private HashSet<CategoryListener> categoryListeners = new HashSet<>(); |
||||||
|
private HashSet<DateListener> dateListeners = new HashSet<>(); |
||||||
|
private HashSet<FieldListener> fieldListeners = new HashSet<>(); |
||||||
|
private HashSet<PathListener> pathListeners = new HashSet<>(); |
||||||
|
private HashSet<ActionListener> scanListeners = new HashSet<>(); |
||||||
|
private HashMap<String,Component> additonalComponents = new HashMap<>(); |
||||||
|
|
||||||
|
private DateChooser date; |
||||||
|
|
||||||
|
private Configuration config; |
||||||
|
|
||||||
|
private SelectComboBox pathPicker; |
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
public Toolbar(Configuration config) { |
||||||
|
this.config = config; |
||||||
|
setLayout(new BoxLayout(this, BoxLayout.Y_AXIS)); |
||||||
|
add(datePicker()); |
||||||
|
add(input("Kategorie",categoryPicker(config))); |
||||||
|
add(input("Pfad",pathPicker = pathPicker())); |
||||||
|
add(scanButton()); |
||||||
|
add(externButton()); |
||||||
|
} |
||||||
|
|
||||||
|
public void addFieldsFor(Vector<String> marks) { |
||||||
|
LOG.debug("addFieldsFor({})",marks); |
||||||
|
|
||||||
|
List<String> deleted = additonalComponents.keySet().stream().filter(key -> !marks.contains(key)).collect(Collectors.toList()); |
||||||
|
deleted.forEach(name -> remove(additonalComponents.remove(name))); |
||||||
|
|
||||||
|
for (String name : marks) { |
||||||
|
if (additonalComponents.containsKey(name)) continue; |
||||||
|
List<Object> knownValues = List.of(); |
||||||
|
SelectComboBox valuePicker = new SelectComboBox(knownValues).onUpdateText(newText -> updateField(name,newText)); |
||||||
|
Component input = input(name, valuePicker); |
||||||
|
add(input,getComponentCount()-2); |
||||||
|
additonalComponents.put(name, input); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
public Toolbar addCategoryListener(CategoryListener listener) { |
||||||
|
categoryListeners.add(listener); |
||||||
|
return this; |
||||||
|
} |
||||||
|
|
||||||
|
public Toolbar addDateListener(DateListener listener) { |
||||||
|
dateListeners.add(listener); |
||||||
|
return this; |
||||||
|
} |
||||||
|
|
||||||
|
public Toolbar addFieldListener(FieldListener listener) { |
||||||
|
fieldListeners.add(listener); |
||||||
|
return this; |
||||||
|
} |
||||||
|
|
||||||
|
public Toolbar addPathListener(PathListener listener){ |
||||||
|
pathListeners.add(listener); |
||||||
|
return this; |
||||||
|
} |
||||||
|
|
||||||
|
public Toolbar addScanListener(ActionListener listener) { |
||||||
|
scanListeners.add(listener); |
||||||
|
return this; |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
private Component categoryPicker(Configuration config) { |
||||||
|
JSONObject elements = config.getOrCreate("app.categories",new JSONObject()); |
||||||
|
elements.keySet().forEach(categories::add); |
||||||
|
return new SelectComboBox(categories).onUpdateText(this::updateCat); |
||||||
|
} |
||||||
|
|
||||||
|
private Component datePicker() { |
||||||
|
date = new DateChooser(); |
||||||
|
Dimension dim = new Dimension(400, 250); |
||||||
|
date.setMaximumSize(dim); |
||||||
|
date.addActionListener(ev -> dateListeners.forEach(listener -> listener.setDate(date.getSelectedDate()))); |
||||||
|
return date; |
||||||
|
} |
||||||
|
|
||||||
|
private JButton externButton() { |
||||||
|
JButton btn = new JButton("extern öffnen"); |
||||||
|
return btn; |
||||||
|
} |
||||||
|
|
||||||
|
private Component input(String caption, Component component) { |
||||||
|
JPanel panel = new JPanel(); |
||||||
|
panel.setLayout(new BoxLayout(panel, BoxLayout.X_AXIS)); |
||||||
|
panel.add(new JLabel(caption+" ")); |
||||||
|
panel.add(component); |
||||||
|
return panel; |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
public Date getDate() { |
||||||
|
return date.getSelectedDate(); |
||||||
|
} |
||||||
|
|
||||||
|
private SelectComboBox pathPicker() { |
||||||
|
JSONObject cats = config.getOrCreate("app.categories",new JSONObject()); |
||||||
|
for (String catName : cats.keySet()) { |
||||||
|
JSONObject catInfo = cats.getJSONObject(catName); |
||||||
|
if (catInfo.has("path")) paths.add(catInfo.get("path")); |
||||||
|
} |
||||||
|
paths.add("$HOME/$JAHR/$MONAT-$TAG - $KATEGORIE"); |
||||||
|
return new SelectComboBox(paths).onUpdateText(this::updatePath); |
||||||
|
} |
||||||
|
|
||||||
|
private Component scanButton() { |
||||||
|
JButton scanButton = new JButton("scannen!"); |
||||||
|
scanButton.addActionListener(this::scanPressed); |
||||||
|
return scanButton; |
||||||
|
} |
||||||
|
|
||||||
|
private void scanPressed(ActionEvent evt) { |
||||||
|
scanListeners.forEach(l->l.actionPerformed(evt)); |
||||||
|
} |
||||||
|
|
||||||
|
protected void updateCat(String newCat) { |
||||||
|
LOG.debug("updateCat({})",newCat); |
||||||
|
categoryListeners.forEach(l -> l.setCategory(newCat)); |
||||||
|
if (!newCat.isEmpty()) { |
||||||
|
String path = config.get("app.categories."+newCat+".path"); |
||||||
|
LOG.debug("path: {}",path); |
||||||
|
if (path != null) { |
||||||
|
pathPicker.setSelectedItem(path); |
||||||
|
updatePath(path); |
||||||
|
} |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
private void updateField(String name, String val) { |
||||||
|
LOG.debug("updateField({},{})",name,val); |
||||||
|
fieldListeners.forEach(l -> l.setField(name,val)); |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
protected void updatePath(String newPath) { |
||||||
|
LOG.debug("updatePath({})",newPath); |
||||||
|
pathListeners.forEach(l -> l.setPath(newPath)); |
||||||
|
} |
||||||
|
} |
Loading…
Reference in new issue