瀏覽代碼

Projektdateien hinzufügen.

Kolja Strohm 6 年之前
父節點
當前提交
e17f9d8e29
共有 128 個文件被更改,包括 6672 次插入0 次删除
  1. 25 0
      Fertig - Kopie/ip.bat
  2. 二進制
      Fertig - Kopie/x32/data/bilder/icons.ltdb
  3. 二進制
      Fertig - Kopie/x32/data/bilder/startbg.ltdb
  4. 二進制
      Fertig - Kopie/x32/data/schrift/normal.ltds
  5. 5 0
      Fertig - Kopie/x32/data/start/ladebilder.ini
  6. 1 0
      Fertig - Kopie/x32/data/start/ladeschriften.ini
  7. 14 0
      Fertig - Kopie/x32/data/start/optionen.ini
  8. 二進制
      Fertig - Kopie/x32/framework.dll
  9. 二進制
      Fertig - Kopie/x32/network.dll
  10. 二進制
      Fertig - Kopie/x32/smp.exe
  11. 二進制
      Fertig - Kopie/x32/sql.dll
  12. 25 0
      Fertig/ip.bat
  13. 1 0
      Fertig/ip.txt
  14. 二進制
      Fertig/x32/data/bilder/icons.ltdb
  15. 二進制
      Fertig/x32/data/bilder/startbg.ltdb
  16. 二進制
      Fertig/x32/data/schrift/normal.ltds
  17. 5 0
      Fertig/x32/data/start/ladebilder.ini
  18. 1 0
      Fertig/x32/data/start/ladeschriften.ini
  19. 14 0
      Fertig/x32/data/start/optionen.ini
  20. 二進制
      Fertig/x32/framework.dll
  21. 二進制
      Fertig/x32/network.dll
  22. 二進制
      Fertig/x32/smp.exe
  23. 二進制
      Fertig/x32/sql.dll
  24. 28 0
      SMP.sln
  25. 422 0
      SMP/Netzwerk/LTSKlient.cpp
  26. 53 0
      SMP/Netzwerk/LTSKlient.h
  27. 412 0
      SMP/Netzwerk/Main/MSKlient.cpp
  28. 71 0
      SMP/Netzwerk/Main/MSKlient.h
  29. 400 0
      SMP/Netzwerk/Patch/PSKlient.cpp
  30. 53 0
      SMP/Netzwerk/Patch/PSKlient.h
  31. 41 0
      SMP/Programm/Basic/Abschnitt.cpp
  32. 32 0
      SMP/Programm/Basic/Abschnitt.h
  33. 111 0
      SMP/Programm/Beenden/Beenden.cpp
  34. 36 0
      SMP/Programm/Beenden/Beenden.h
  35. 372 0
      SMP/Programm/Login/Login.cpp
  36. 97 0
      SMP/Programm/Login/Login.h
  37. 206 0
      SMP/Programm/Programm.cpp
  38. 52 0
      SMP/Programm/Programm.h
  39. 1688 0
      SMP/Programm/Server/Patch/PatchServer.cpp
  40. 175 0
      SMP/Programm/Server/Patch/PatchServer.h
  41. 1044 0
      SMP/Programm/Version/Version.cpp
  42. 81 0
      SMP/Programm/Version/Version.h
  43. 60 0
      SMP/Render/Render.cpp
  44. 31 0
      SMP/Render/Render.h
  45. 276 0
      SMP/Ressourcen/Ressourcen.cpp
  46. 73 0
      SMP/Ressourcen/Ressourcen.h
  47. 197 0
      SMP/SMP.vcxproj
  48. 93 0
      SMP/SMP.vcxproj.filters
  49. 268 0
      SMP/Start/Start.cpp
  50. 37 0
      SMP/Start/Start.h
  51. 2 0
      SMP/data/Client.ini
  52. 2 0
      SMP/data/Minigames.ini
  53. 2 0
      SMP/data/Spiel_Asteroids.ini
  54. 2 0
      SMP/data/Spiel_Linie.ini
  55. 2 0
      SMP/data/Spiel_Stickman World Online.ini
  56. 二進制
      SMP/data/bilder/icons.ltdb
  57. 二進制
      SMP/data/bilder/startbg.ltdb
  58. 二進制
      SMP/data/schrift/normal.ltds
  59. 5 0
      SMP/data/start/ladebilder.ini
  60. 1 0
      SMP/data/start/ladeschriften.ini
  61. 14 0
      SMP/data/start/optionen Test.ini
  62. 14 0
      SMP/data/start/optionen.ini
  63. 14 0
      SMP/data/start/optionen1.ini
  64. 14 0
      SMP/data/start/optionen2.ini
  65. 二進制
      SMP/framework.dll
  66. 二進制
      SMP/network.dll
  67. 二進制
      SMP/sql.dll
  68. 二進制
      SMP/vx32/data/bilder/game.ltdb
  69. 二進制
      SMP/vx32/data/bilder/system.ltdb
  70. 二進制
      SMP/vx32/data/client/bilder/chat.ltdb
  71. 二進制
      SMP/vx32/data/client/bilder/ladeanimation.ltdb
  72. 二進制
      SMP/vx32/data/client/bilder/spielen.ltdb
  73. 二進制
      SMP/vx32/data/client/bilder/titel.ltdb
  74. 2 0
      SMP/vx32/data/optionen.ini
  75. 二進制
      SMP/vx32/data/patch/bilder/news.ltdb
  76. 二進制
      SMP/vx32/data/patch/bilder/patcher.ltdb
  77. 4 0
      SMP/vx32/data/patch/news/Willkommen/data.new
  78. 二進制
      SMP/vx32/data/schriften/normal.ltds
  79. 二進制
      SMP/vx32/data/spiele/Linie/bilder/start.ltdb
  80. 1 0
      SMP/vx32/data/spiele/Linie/data/beschreibung.ltgb
  81. 3 0
      SMP/vx32/data/spiele/Linie/data/game.ini
  82. 二進制
      SMP/vx32/data/spiele/Linie/data/id.ltgid
  83. 二進制
      SMP/vx32/data/spiele/Linie/maps/offiziell/Normal/bilder/bilder.ltdb
  84. 6 0
      SMP/vx32/data/spiele/Linie/maps/offiziell/Normal/data/beschreibung.ltgb
  85. 4 0
      SMP/vx32/data/spiele/Linie/maps/offiziell/Normal/data/map.ini
  86. 二進制
      SMP/vx32/data/spiele/Stickman World Online/bilder/start.ltdb
  87. 1 0
      SMP/vx32/data/spiele/Stickman World Online/data/beschreibung.ltgb
  88. 3 0
      SMP/vx32/data/spiele/Stickman World Online/data/game.ini
  89. 二進制
      SMP/vx32/data/spiele/Stickman World Online/data/id.ltgid
  90. 二進制
      SMP/vx32/data/spiele/Stickman World Online/maps/offiziell/Test Karte/bilder/bilder.ltdb
  91. 22 0
      SMP/vx32/data/spiele/Stickman World Online/maps/offiziell/Test Karte/data/beschreibung.ltgb
  92. 3 0
      SMP/vx32/data/spiele/Stickman World Online/maps/offiziell/Test Karte/data/map.ini
  93. 二進制
      SMP/vx32/data/start/icon.exe
  94. 二進制
      SMP/vx32/data/version
  95. 二進制
      SMP/vx32/framework.dll
  96. 二進制
      SMP/vx32/network.dll
  97. 二進制
      SMP/vx32/start.exe
  98. 二進制
      SMP/vx64/data/bilder/game.ltdb
  99. 二進制
      SMP/vx64/data/bilder/system.ltdb
  100. 二進制
      SMP/vx64/data/client/bilder/chat.ltdb
  101. 二進制
      SMP/vx64/data/client/bilder/ladeanimation.ltdb
  102. 二進制
      SMP/vx64/data/client/bilder/spielen.ltdb
  103. 二進制
      SMP/vx64/data/client/bilder/titel.ltdb
  104. 2 0
      SMP/vx64/data/optionen.ini
  105. 二進制
      SMP/vx64/data/patch/bilder/news.ltdb
  106. 二進制
      SMP/vx64/data/patch/bilder/patcher.ltdb
  107. 4 0
      SMP/vx64/data/patch/news/Willkommen/data.new
  108. 二進制
      SMP/vx64/data/schriften/normal.ltds
  109. 二進制
      SMP/vx64/data/spiele/Linie/bilder/start.ltdb
  110. 1 0
      SMP/vx64/data/spiele/Linie/data/beschreibung.ltgb
  111. 3 0
      SMP/vx64/data/spiele/Linie/data/game.ini
  112. 二進制
      SMP/vx64/data/spiele/Linie/data/id.ltgid
  113. 二進制
      SMP/vx64/data/spiele/Linie/maps/offiziell/Normal/bilder/bilder.ltdb
  114. 6 0
      SMP/vx64/data/spiele/Linie/maps/offiziell/Normal/data/beschreibung.ltgb
  115. 4 0
      SMP/vx64/data/spiele/Linie/maps/offiziell/Normal/data/map.ini
  116. 二進制
      SMP/vx64/data/spiele/Stickman World Online/bilder/start.ltdb
  117. 1 0
      SMP/vx64/data/spiele/Stickman World Online/data/beschreibung.ltgb
  118. 3 0
      SMP/vx64/data/spiele/Stickman World Online/data/game.ini
  119. 二進制
      SMP/vx64/data/spiele/Stickman World Online/data/id.ltgid
  120. 二進制
      SMP/vx64/data/spiele/Stickman World Online/maps/offiziell/Test Karte/bilder/bilder.ltdb
  121. 22 0
      SMP/vx64/data/spiele/Stickman World Online/maps/offiziell/Test Karte/data/beschreibung.ltgb
  122. 3 0
      SMP/vx64/data/spiele/Stickman World Online/maps/offiziell/Test Karte/data/map.ini
  123. 二進制
      SMP/vx64/data/start/icon.exe
  124. 二進制
      SMP/vx64/data/version
  125. 二進制
      SMP/vx64/framework.dll
  126. 二進制
      SMP/vx64/network.dll
  127. 二進制
      SMP/vx64/start.exe
  128. 2 0
      build.bat

+ 25 - 0
Fertig - Kopie/ip.bat

@@ -0,0 +1,25 @@
+@echo off
+
+
+if exist ip.txt del ip.txt
+
+@echo off & setlocal 
+
+set URL=http://checkip.dyndns.com/
+
+set G=%temp%\GetHTML.vbs 
+
+echo On Error Resume Next:Set Http=CreateObject("WinHttp.WinHttpRequest.5.1"):Http.Open "GET",WScript.Arguments(0),False:Http.Send:Q=Split(Http.ResponseText,":")(1):WScript.Echo Trim(Split(Q,"<")(0))>%G%
+
+set ExtIP=
+
+for /f %%i in ('cscript //nologo %G% "%URL%"') do set "ExtIP=%%i"
+
+del %G%
+
+if not defined ExtIP echo Externe IP konnte nicht ermittelt werden. & goto :eof 
+
+echo %ExtIP% >> ip.txt
+
+
+exit

二進制
Fertig - Kopie/x32/data/bilder/icons.ltdb


二進制
Fertig - Kopie/x32/data/bilder/startbg.ltdb


二進制
Fertig - Kopie/x32/data/schrift/normal.ltds


+ 5 - 0
Fertig - Kopie/x32/data/start/ladebilder.ini

@@ -0,0 +1,5 @@
+neuladen.png=data/bilder/icons.ltdb/neuladen.png
+weiter.png=data/bilder/icons.ltdb/weiter.png
+zurück.png=data/bilder/icons.ltdb/zurück.png
+speichern.png=data/bilder/icons.ltdb/speichern.png
+neu.png=data/bilder/icons.ltdb/neu.png

+ 1 - 0
Fertig - Kopie/x32/data/start/ladeschriften.ini

@@ -0,0 +1 @@
+normal=data/schrift/normal.ltds

+ 14 - 0
Fertig - Kopie/x32/data/start/optionen.ini

@@ -0,0 +1,14 @@
+DisplayMonitor=0
+LadenSchriftDatei=data/schrift/normal.ltds
+Schrift=normal
+LadenHintergrundDatei=data/bilder/startbg.ltdb
+LadenHintergrundBild=bg.png
+LadeBilder=data/start/ladebilder.ini
+LadeSchriften=data/start/ladeschriften.ini
+DBBenutzer=smpuser
+DBPasswort=SMPUserP
+DBDatenbank=koljadb
+DBIP=127.0.0.1
+DBPort=49134
+MainServerIP=192.168.2.102
+MainServerPort=4252

二進制
Fertig - Kopie/x32/framework.dll


二進制
Fertig - Kopie/x32/network.dll


二進制
Fertig - Kopie/x32/smp.exe


二進制
Fertig - Kopie/x32/sql.dll


+ 25 - 0
Fertig/ip.bat

@@ -0,0 +1,25 @@
+@echo off
+
+
+if exist ip.txt del ip.txt
+
+@echo off & setlocal 
+
+set URL=http://checkip.dyndns.com/
+
+set G=%temp%\GetHTML.vbs 
+
+echo On Error Resume Next:Set Http=CreateObject("WinHttp.WinHttpRequest.5.1"):Http.Open "GET",WScript.Arguments(0),False:Http.Send:Q=Split(Http.ResponseText,":")(1):WScript.Echo Trim(Split(Q,"<")(0))>%G%
+
+set ExtIP=
+
+for /f %%i in ('cscript //nologo %G% "%URL%"') do set "ExtIP=%%i"
+
+del %G%
+
+if not defined ExtIP echo Externe IP konnte nicht ermittelt werden. & goto :eof 
+
+echo %ExtIP% >> ip.txt
+
+
+exit

+ 1 - 0
Fertig/ip.txt

@@ -0,0 +1 @@
+93.201.122.27 

二進制
Fertig/x32/data/bilder/icons.ltdb


二進制
Fertig/x32/data/bilder/startbg.ltdb


二進制
Fertig/x32/data/schrift/normal.ltds


+ 5 - 0
Fertig/x32/data/start/ladebilder.ini

@@ -0,0 +1,5 @@
+neuladen.png=data/bilder/icons.ltdb/neuladen.png
+weiter.png=data/bilder/icons.ltdb/weiter.png
+zurück.png=data/bilder/icons.ltdb/zurück.png
+speichern.png=data/bilder/icons.ltdb/speichern.png
+neu.png=data/bilder/icons.ltdb/neu.png

+ 1 - 0
Fertig/x32/data/start/ladeschriften.ini

@@ -0,0 +1 @@
+normal=data/schrift/normal.ltds

+ 14 - 0
Fertig/x32/data/start/optionen.ini

@@ -0,0 +1,14 @@
+DisplayMonitor=0
+LadenSchriftDatei=data/schrift/normal.ltds
+Schrift=normal
+LadenHintergrundDatei=data/bilder/startbg.ltdb
+LadenHintergrundBild=bg.png
+LadeBilder=data/start/ladebilder.ini
+LadeSchriften=data/start/ladeschriften.ini
+DBBenutzer=smpuser
+DBPasswort=SMPUserP
+DBDatenbank=koljadb
+DBIP=127.0.0.1
+DBPort=49134
+MainServerIP=192.168.2.102
+MainServerPort=4252

二進制
Fertig/x32/framework.dll


二進制
Fertig/x32/network.dll


二進制
Fertig/x32/smp.exe


二進制
Fertig/x32/sql.dll


+ 28 - 0
SMP.sln

@@ -0,0 +1,28 @@
+
+Microsoft Visual Studio Solution File, Format Version 12.00
+# Visual Studio 14
+VisualStudioVersion = 14.0.22823.1
+MinimumVisualStudioVersion = 10.0.40219.1
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "SMP", "SMP\SMP.vcxproj", "{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}"
+EndProject
+Global
+	GlobalSection(SolutionConfigurationPlatforms) = preSolution
+		Debug|Win32 = Debug|Win32
+		Debug|x64 = Debug|x64
+		Release|Win32 = Release|Win32
+		Release|x64 = Release|x64
+	EndGlobalSection
+	GlobalSection(ProjectConfigurationPlatforms) = postSolution
+		{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}.Debug|Win32.ActiveCfg = Debug|Win32
+		{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}.Debug|Win32.Build.0 = Debug|Win32
+		{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}.Debug|x64.ActiveCfg = Debug|x64
+		{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}.Debug|x64.Build.0 = Debug|x64
+		{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}.Release|Win32.ActiveCfg = Release|Win32
+		{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}.Release|Win32.Build.0 = Release|Win32
+		{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}.Release|x64.ActiveCfg = Release|x64
+		{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}.Release|x64.Build.0 = Release|x64
+	EndGlobalSection
+	GlobalSection(SolutionProperties) = preSolution
+		HideSolutionNode = FALSE
+	EndGlobalSection
+EndGlobal

+ 422 - 0
SMP/Netzwerk/LTSKlient.cpp

@@ -0,0 +1,422 @@
+#include "LTSKlient.h"
+
+// Inhalt der LTSKlient Klasse aus LTSKlient.h
+// Konstruktor
+LTSKlient::LTSKlient( const char *ip, int port )
+{
+	k = new SSLKlient();
+	fehler = new Text( "Keine Verbindung zum Server." );
+	this->ip = new Text( ip );
+	this->port = port;
+	verbunden = 0;
+	eingeloggt = 0;
+	InitializeCriticalSection( &cs );
+	ref = 1;
+}
+
+// Destruktor
+LTSKlient::~LTSKlient()
+{
+	if( verbunden )
+		trenne();
+	k->release();
+	ip->release();
+	fehler->release();
+	DeleteCriticalSection( &cs );
+}
+
+// nicht constant
+void LTSKlient::lock()
+{
+	EnterCriticalSection( &cs );
+}
+
+void LTSKlient::unlock()
+{
+	LeaveCriticalSection( &cs );
+}
+
+bool LTSKlient::verbinden()
+{
+	if( verbunden )
+		return 1;
+	lock();
+	bool b = k->verbinde( port, ip->getText() );
+	if( !b )
+	{
+		fehler->setText( "Fehler beim verbinden mit dem Server.\nPort:" );
+		fehler->append( port );
+		fehler->append( " IP:" );
+		fehler->append( ip->getText() );
+	}
+	verbunden = b;
+	eingeloggt = 0;
+	unlock();
+	return b;
+}
+
+bool LTSKlient::login( const char *name, const char *passwort )
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\1", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 1 )
+	{
+		unsigned char län = (unsigned char)textLength( name );
+		k->sende( (char*)&län, 1 );
+		if( län )
+			k->sende( name, län );
+		län = (unsigned char)textLength( passwort );
+		k->sende( (char*)&län, 1 );
+		if( län )
+			k->sende( passwort, län );
+		k->getNachricht( (char*)&res, 1 );
+	}
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während login beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	else
+	{
+		eingeloggt = 1;
+		unlock();
+		return 1;
+	}
+	unlock();
+	return 0;
+}
+
+bool LTSKlient::logout()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\2", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während logout beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+int LTSKlient::getStatus()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return -1;
+	lock();
+	k->sende( "\x8", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	int status = 0;
+	if( res == 1 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		if( res == 1 )
+			status = 1;
+	}
+	else if( res == 3 )
+	{
+		status = -2;
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Status Request beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return (int)res;
+}
+
+bool LTSKlient::stop()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\5", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Stoppen beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+bool LTSKlient::pause()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\x9", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Pausieren beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	k->sende( "\1", 1 );
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Pausieren beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+bool LTSKlient::fortsetzen()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\x9", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Fortsetzen beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	k->sende( "\0", 1 );
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Fortsetzen beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+bool LTSKlient::start()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\4", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Starten beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+bool LTSKlient::setMaxTasks( int maxC )
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\xA", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während SetMaxClients beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	k->sende( (char*)&maxC, 4 );
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während SetMaxClients beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+bool LTSKlient::beenden()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\6", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Beenden beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	if( res == 1 )
+	{
+		eingeloggt = 0;
+		verbunden = 0;
+	}
+	return res == 1;
+}
+
+bool LTSKlient::terminieren()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\7", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Terminieren beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	if( res == 1 )
+	{
+		eingeloggt = 0;
+		verbunden = 0;
+	}
+	return res == 1;
+}
+
+bool LTSKlient::trenne()
+{
+	if( !verbunden )
+		return 1;
+	lock();
+	k->sende( "\3", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Trennen beim Server.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	eingeloggt = 0;
+	verbunden = 0;
+	k->trenne();
+	return res == 1;
+}
+
+void LTSKlient::abbruch()
+{
+	if( verbunden )
+		k->trenne();
+	eingeloggt = 0;
+	verbunden = 0;
+}
+
+// constant
+bool LTSKlient::istVerbunden() const
+{
+	return verbunden;
+}
+
+bool LTSKlient::istEingeloggt() const
+{
+	return eingeloggt;
+}
+
+const char *LTSKlient::getLetzterFehler() const
+{
+	return fehler->getText();
+}
+
+SSLKlient *LTSKlient::zKlient() const
+{
+	return k;
+}

+ 53 - 0
SMP/Netzwerk/LTSKlient.h

@@ -0,0 +1,53 @@
+#ifndef LTSKlient_H
+#define LTSKlient_H
+
+#include <Klient.h>
+#include <Text.h>
+
+using namespace Network;
+using namespace Framework;
+
+class LTSKlient
+{
+protected:
+	SSLKlient *k;
+	CRITICAL_SECTION cs;
+	Text *fehler;
+	Text *ip;
+	int port;
+	bool verbunden;
+	bool eingeloggt;
+	int ref;
+
+public:
+	// Konstruktor
+	LTSKlient( const char *ip, int port );
+	// Destruktor
+	~LTSKlient();
+	// nicht constant
+	void lock();
+	void unlock();
+	bool verbinden();
+	bool login( const char *name, const char *passwort );
+	bool logout();
+	int getStatus();
+	bool stop();
+	bool pause();
+	bool fortsetzen();
+	bool start();
+	bool setMaxTasks( int maxC );
+	bool beenden();
+	bool terminieren();
+	bool trenne();
+	void abbruch();
+	// constant
+	bool istVerbunden() const;
+	bool istEingeloggt() const;
+	const char *getLetzterFehler() const;
+	SSLKlient *zKlient() const;
+	// Reference Counting
+	virtual LTSKlient *getThis() = 0;
+	virtual LTSKlient *release() = 0;
+};
+
+#endif

+ 412 - 0
SMP/Netzwerk/Main/MSKlient.cpp

@@ -0,0 +1,412 @@
+#include "MSKlient.h"
+
+// Inhalt der MSKlient Klasse aus MSKlient.h
+// Konstruktor
+MSKlient::MSKlient( const char *ip, int port )
+{
+	k = new SSLKlient();
+	fehler = new Text( "Keine Verbindung zum Server." );
+	this->ip = new Text( ip );
+	this->port = port;
+	verbunden = 0;
+	eingeloggt = 0;
+	InitializeCriticalSection( &cs );
+	ref = 1;
+}
+
+// Destruktor
+MSKlient::~MSKlient()
+{
+	if( verbunden )
+		trenne();
+	k->release();
+	ip->release();
+	fehler->release();
+	DeleteCriticalSection( &cs );
+}
+
+// nicht constant
+void MSKlient::lock()
+{
+	EnterCriticalSection( &cs );
+}
+
+void MSKlient::unlock()
+{
+	LeaveCriticalSection( &cs );
+}
+
+bool MSKlient::verbinden()
+{
+	if( verbunden )
+		return 1;
+	lock();
+	bool b = k->verbinde( port, ip->getText() );
+	if( !b )
+	{
+		fehler->setText( "Fehler während verbinden bei MainServer.\nPort:" );
+		fehler->append( port );
+		fehler->append( " IP:" );
+		fehler->append( ip->getText() );
+	}
+	verbunden = b;
+	eingeloggt = 0;
+	unlock();
+	return b;
+}
+
+bool MSKlient::login( const char *name, const char *passwort )
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\1", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 1 )
+	{
+		unsigned char län = (unsigned char)textLength( name );
+		k->sende( (char*)&län, 1 );
+		if( län )
+			k->sende( name, län );
+		län = (unsigned char)textLength( passwort );
+		k->sende( (char*)&län, 1 );
+		if( län )
+			k->sende( passwort, län );
+		k->getNachricht( (char*)&res, 1 );
+	}
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während einloggen bei MainServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	else
+	{
+		eingeloggt = 1;
+		unlock();
+		return 1;
+	}
+	unlock();
+	return 0;
+}
+
+bool MSKlient::logout()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\2", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während ausloggen bei MainServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+int MSKlient::getStatus()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return -1;
+	lock();
+	k->sende( "\x8", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	int status = 0;
+	if( res == 1 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		if( res == 1 )
+			status = 1;
+	}
+	if( res == 3 )
+	{
+		status = -2;
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Status Request bei MainServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return (int)res;
+}
+
+bool MSKlient::pause()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\5", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Pausieren bei MainServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+bool MSKlient::fortsetzen()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\4", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Fortsetzen bei MainServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	return res == 1;
+}
+
+bool MSKlient::beenden()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\6", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Beenden bei MainServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	if( res == 1 )
+	{
+		eingeloggt = 0;
+		verbunden = 0;
+	}
+	return res == 1;
+}
+
+bool MSKlient::terminieren()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\7", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Terminieren bei MainServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	if( res == 1 )
+	{
+		eingeloggt = 0;
+		verbunden = 0;
+	}
+	return res == 1;
+}
+
+bool MSKlient::getPatchServerListe( Array< ServerData* > *list )
+{
+    if( !verbunden )
+        verbinden();
+    if( !verbunden )
+        return 0;
+    lock();
+    k->sende( "\x9", 1 );
+    unsigned char res = 0;
+    k->getNachricht( (char*)&res, 1 );
+    if( res == 3 )
+    {
+        k->getNachricht( (char*)&res, 1 );
+        char *txt = new char[ res + 1 ];
+        k->getNachricht( txt, res );
+        txt[ res ] = 0;
+        fehler->setText( "Fehler während Terminieren bei MainServer.\nServer Rückgabe:" );
+        fehler->append( txt );
+        delete[] txt;
+        unlock();
+        return 0;
+    }
+    else if( res == 1 )
+    {
+        int anz = 0;
+        k->getNachricht( (char*)&anz, 4 );
+        for( int i = 0; i < anz; i++ )
+        {
+            ServerData *s = new ServerData();
+            k->getNachricht( (char*)&s->id, 4 );
+            k->getNachricht( (char*)&s->port, 2 );
+            k->getNachricht( (char*)&s->adminPort, 2 );
+            unsigned char len = 0;
+            k->getNachricht( (char*)&len, 1 );
+            s->name.fillText( ' ', len );
+            k->getNachricht( s->name, len );
+            k->getNachricht( (char*)&len, 1 );
+            s->ip.fillText( ' ', len );
+            k->sende( s->ip, len );
+            k->getNachricht( (char*)&len, 1 );
+            s->status.fillText( ' ', len );
+            k->sende( s->status, len );
+            list->add( s );
+        }
+    }
+    unlock();
+    return 1;
+}
+
+bool MSKlient::getPatchServerDetails( int id, ServerDetails *details )
+{
+    if( !verbunden )
+        verbinden();
+    if( !verbunden )
+        return 0;
+    lock();
+    k->sende( "\xA", 1 );
+    unsigned char res = 0;
+    k->getNachricht( (char*)&res, 1 );
+    if( res == 1 )
+    {
+        k->sende( (char*)&id, 4 );
+        k->getNachricht( (char*)&res, 1 );
+        if( res == 1 )
+        {
+            unsigned char len = 0;
+            k->getNachricht( (char*)&len, 1 );
+            details->name.fillText( ' ', len );
+            k->getNachricht( details->name, len );
+            k->getNachricht( (char*)&len, 1 );
+            details->ip.fillText( ' ', len );
+            k->sende( details->ip, len );
+            k->getNachricht( (char*)&details->port, 2 );
+            k->getNachricht( (char*)&details->adminPort, 2 );
+            k->getNachricht( (char*)&details->tasks, 4 );
+            k->getNachricht( (char*)&details->maxTasks, 4 );
+        }
+    }
+    if( res == 3 )
+    {
+        k->getNachricht( (char*)&res, 1 );
+        char *txt = new char[ res + 1 ];
+        k->getNachricht( txt, res );
+        txt[ res ] = 0;
+        fehler->setText( "Fehler während Terminieren bei MainServer.\nServer Rückgabe:" );
+        fehler->append( txt );
+        delete[] txt;
+        unlock();
+        return 0;
+    }
+    unlock();
+    return 1;
+}
+
+bool MSKlient::trenne()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\3", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während Trennen bei MainServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+	}
+	unlock();
+	eingeloggt = 0;
+	verbunden = 0;
+	k->trenne();
+	return res == 1;
+}
+
+// constant
+bool MSKlient::istVerbunden() const
+{
+	return verbunden;
+}
+
+bool MSKlient::istEingeloggt() const
+{
+	return eingeloggt;
+}
+
+const char *MSKlient::getLetzterFehler() const
+{
+	return fehler->getText();
+}
+
+// Reference Counting
+MSKlient *MSKlient::getThis()
+{
+	ref++;
+	return this;
+}
+
+MSKlient *MSKlient::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}

+ 71 - 0
SMP/Netzwerk/Main/MSKlient.h

@@ -0,0 +1,71 @@
+#ifndef MSKlient_H
+#define MSKlient_H
+
+#include <Klient.h>
+#include <Text.h>
+#include <Array.h>
+
+using namespace Network;
+using namespace Framework;
+
+struct ServerData
+{
+    int id;
+    Text name;
+    Text ip;
+    unsigned short port;
+    unsigned short adminPort;
+    Text status;
+};
+
+struct ServerDetails
+{
+    Text name;
+    Text ip;
+    unsigned short port;
+    unsigned short adminPort;
+    int tasks;
+    int maxTasks;
+};
+
+class MSKlient
+{
+private:
+	SSLKlient *k;
+	CRITICAL_SECTION cs;
+	Text *fehler;
+	Text *ip;
+	int port;
+	bool verbunden;
+	bool eingeloggt;
+	int ref;
+
+public:
+	// Konstruktor
+	MSKlient( const char *ip, int port );
+	// Destruktor
+	~MSKlient();
+	// nicht constant
+	void lock();
+	void unlock();
+	bool verbinden();
+	bool login( const char *name, const char *passwort );
+	bool logout();
+	int getStatus();
+	bool pause();
+	bool fortsetzen();
+	bool beenden();
+	bool terminieren();
+    bool getPatchServerListe( Array< ServerData* > *list );
+    bool getPatchServerDetails( int id, ServerDetails *details );
+	bool trenne();
+	// constant
+	bool istVerbunden() const;
+	bool istEingeloggt() const;
+	const char *getLetzterFehler() const;
+	// Reference Counting
+	MSKlient *getThis();
+	MSKlient *release();
+};
+
+#endif

+ 400 - 0
SMP/Netzwerk/Patch/PSKlient.cpp

@@ -0,0 +1,400 @@
+#include "PSKlient.h"
+
+// Inhalt der PSKlient Klasse aus PSKlient.h
+// Konstruktor
+PSKlient::PSKlient( const char *ip, int port )
+	: LTSKlient( ip, port )
+{
+}
+
+// Destruktor
+PSKlient::~PSKlient()
+{
+}
+
+// nicht constant
+bool PSKlient::getDateiListe( int *systemAnzahl, Array< int > *dateiAnzahl, RCArray< Text > *systeme, RCArray< RCArray< Text > > *dateien )
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\xB", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während GetDateiListe bei PatchServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+		unlock();
+		return 0;
+	}
+	*systemAnzahl = 0;
+	int län = 0;
+	k->getNachricht( (char*)&län, 4 );
+	while( län )
+	{ // System Sleife
+		char *txt = new char[ län + 1 ];
+		txt[ län ] = 0;
+		k->getNachricht( txt, län );
+		systeme->set( new Text( txt ), *systemAnzahl );
+		delete[] txt;
+		dateien->set( new RCArray< Text >(), *systemAnzahl );
+		int dAnzahl = 0;
+		k->getNachricht( (char*)&län, 4 );
+		while( län )
+		{ // Datei Schleife
+			char *txt = new char[ län + 1 ];
+			txt[ län ] = 0;
+			k->getNachricht( txt, län );
+			dateien->z( *systemAnzahl )->set( new Text( txt ), dAnzahl );
+			delete[] txt;
+			dAnzahl++;
+			k->getNachricht( (char*)&län, 4 );
+		}
+		dateiAnzahl->set( dAnzahl, *systemAnzahl );
+		( *systemAnzahl )++;
+		k->getNachricht( (char*)&län, 4 );
+	}
+	unlock();
+	return 1;
+}
+
+bool PSKlient::updateFertig()
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\xC", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während UpdateFertig bei PatchServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+		unlock();
+		return 0;
+	}
+	unlock();
+	return 1;
+}
+
+bool PSKlient::updateStarten( int dateiGruppeId )
+{
+	if( !verbunden )
+		verbinden();
+	if( !verbunden )
+		return 0;
+	lock();
+	k->sende( "\xD", 1 );
+	unsigned char res = 0;
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während UpdateStarten bei PatchServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+		unlock();
+		return 0;
+	}
+	k->sende( (char*)&dateiGruppeId, 4 );
+	k->getNachricht( (char*)&res, 1 );
+	if( res == 3 )
+	{
+		k->getNachricht( (char*)&res, 1 );
+		char *txt = new char[ res + 1 ];
+		k->getNachricht( txt, res );
+		txt[ res ] = 0;
+		fehler->setText( "Fehler während UpdateStarten bei PatchServer.\nServer Rückgabe:" );
+		fehler->append( txt );
+		delete[] txt;
+		unlock();
+		return 0;
+	}
+	unlock();
+	return 1;
+}
+
+bool PSKlient::getFileGroupInfoList( Array< FileGroupInfo* > *list )
+{
+    if( !verbunden )
+        verbinden();
+    if( !verbunden )
+        return 0;
+    lock();
+    k->sende( "\x10", 1 );
+    unsigned char res = 0;
+    k->getNachricht( (char*)&res, 1 );
+    if( res == 1 )
+    {
+        int anz = 0;
+        k->getNachricht( (char*)&anz, 4 );
+        for( int i = 0; i < anz; i++ )
+        {
+            FileGroupInfo *info = new FileGroupInfo();
+            k->getNachricht( (char*)&info->id, 4 );
+            unsigned char len = 0;
+            k->getNachricht( (char*)&len, 1 );
+            info->name.fillText( ' ', len );
+            k->getNachricht( info->name, len );
+            k->getNachricht( (char*)&len, 1 );
+            info->status.fillText( ' ', len );
+            k->getNachricht( info->status, len );
+            unsigned short l = 0;
+            k->getNachricht( (char*)&l, 2 );
+            info->path.fillText( ' ', l );
+            k->getNachricht( info->path, l );
+            k->getNachricht( (char*)&info->version, 4 );
+            list->add( info );
+        }
+    }
+    if( res == 3 )
+    {
+        k->getNachricht( (char*)&res, 1 );
+        char *txt = new char[ res + 1 ];
+        k->getNachricht( txt, res );
+        txt[ res ] = 0;
+        fehler->setText( "Fehler während getFileGroupInfoList bei PatchServer.\nServer Rückgabe:" );
+        fehler->append( txt );
+        delete[] txt;
+        unlock();
+        return 0;
+    }
+    unlock();
+    return 1;
+}
+
+bool PSKlient::getSystemInfoList( RCArray< ReferenceCounting< std::pair< int, Text > > > *list )
+{
+    if( !verbunden )
+        verbinden();
+    if( !verbunden )
+        return 0;
+    lock();
+    k->sende( "\x11", 1 );
+    unsigned char res = 0;
+    k->getNachricht( (char*)&res, 1 );
+    if( res == 1 )
+    {
+        int anz = 0;
+        k->getNachricht( (char*)&anz, 4 );
+        for( int i = 0; i < anz; i++ )
+        {
+            ReferenceCounting< std::pair< int, Text > > *obj = new ReferenceCounting< std::pair< int, Text > >();
+            k->getNachricht( (char*)&obj->first, 4 );
+            unsigned char len = 0;
+            k->getNachricht( (char*)&len, 1 );
+            obj->second.fillText( ' ', len );
+            k->getNachricht( obj->second, len );
+            list->add( obj );
+        }
+    }
+    if( res == 3 )
+    {
+        k->getNachricht( (char*)&res, 1 );
+        char *txt = new char[ res + 1 ];
+        k->getNachricht( txt, res );
+        txt[ res ] = 0;
+        fehler->setText( "Fehler während getSystemInfoList bei PatchServer.\nServer Rückgabe:" );
+        fehler->append( txt );
+        delete[] txt;
+        unlock();
+        return 0;
+    }
+    unlock();
+    return 1;
+}
+
+bool PSKlient::getFileInfoList( int system, int group, RCArray< ReferenceCounting< FileInfo > > *list )
+{
+    if( !verbunden )
+        verbinden();
+    if( !verbunden )
+        return 0;
+    lock();
+    k->sende( "\x12", 1 );
+    unsigned char res = 0;
+    k->getNachricht( (char*)&res, 1 );
+    if( res == 1 )
+    {
+        k->sende( (char*)&system, 4 );
+        k->sende( (char*)&group, 4 );
+        int anz = 0;
+        k->getNachricht( (char*)&anz, 4 );
+        for( int i = 0; i < anz; i++ )
+        {
+            ReferenceCounting< FileInfo > *obj = new ReferenceCounting< FileInfo >();
+            k->getNachricht( (char*)&obj->id, 4 );
+            unsigned short len = 0;
+            k->getNachricht( (char*)&len, 2 );
+            obj->path.fillText( ' ', len );
+            k->getNachricht( obj->path, len );
+            k->getNachricht( (char*)&obj->version, 4 );
+            unsigned char l = 0;
+            k->getNachricht( (char*)&l, 1 );
+            obj->time.fillText( ' ', l );
+            k->getNachricht( obj->time, l );
+            list->add( obj );
+        }
+    }
+    if( res == 3 )
+    {
+        k->getNachricht( (char*)&res, 1 );
+        char *txt = new char[ res + 1 ];
+        k->getNachricht( txt, res );
+        txt[ res ] = 0;
+        fehler->setText( "Fehler während getSystemInfoList bei PatchServer.\nServer Rückgabe:" );
+        fehler->append( txt );
+        delete[] txt;
+        unlock();
+        return 0;
+    }
+    unlock();
+    return 1;
+}
+
+bool PSKlient::getFileVersion( char *path, int system, int group, int *version )
+{
+    if( !verbunden )
+        verbinden();
+    if( !verbunden )
+        return 0;
+    lock();
+    k->sende( "\x13", 1 );
+    unsigned char res = 0;
+    k->getNachricht( (char*)&res, 1 );
+    if( res == 1 )
+    {
+        unsigned short len = textLength( path );
+        k->sende( (char*)&len, 2 );
+        k->sende( path, len );
+        k->sende( (char*)&group, 4 );
+        k->sende( (char*)&system, 4 );
+        k->getNachricht( (char*)version, 4 );
+    }
+    if( res == 3 )
+    {
+        k->getNachricht( (char*)&res, 1 );
+        char *txt = new char[ res + 1 ];
+        k->getNachricht( txt, res );
+        txt[ res ] = 0;
+        fehler->setText( "Fehler während getSystemInfoList bei PatchServer.\nServer Rückgabe:" );
+        fehler->append( txt );
+        delete[] txt;
+        unlock();
+        return 0;
+    }
+    unlock();
+    return 1;
+}
+
+bool PSKlient::updateFile( const char *pfad, Zeit *zLetzteÄnderung, int system, int gruppe )
+{
+    if( !verbunden )
+        verbinden();
+    if( !verbunden )
+        return 0;
+    lock();
+    k->sende( "\x14", 1 );
+    unsigned char res = 0;
+    k->getNachricht( (char*)&res, 1 );
+    if( res == 1 )
+    {
+        unsigned short len = textLength( pfad );
+        k->sende( (char*)&len, 2 );
+        k->sende( pfad, len );
+        Text *time = zLetzteÄnderung->getZeit( "y-m-d h:i:s" );
+        unsigned char l = (unsigned char)time->getLength();
+        k->sende( (char*)&l, 1 );
+        k->sende( time->getText(), l );
+        k->sende( (char*)&system, 4 );
+        k->sende( (char*)&gruppe, 4 );
+        k->getNachricht( (char*)&res, 1 );
+        time->release();
+    }
+    if( res == 3 )
+    {
+        k->getNachricht( (char*)&res, 1 );
+        char *txt = new char[ res + 1 ];
+        k->getNachricht( txt, res );
+        txt[ res ] = 0;
+        fehler->setText( "Fehler während getSystemInfoList bei PatchServer.\nServer Rückgabe:" );
+        fehler->append( txt );
+        delete[] txt;
+        unlock();
+        return 0;
+    }
+    unlock();
+    return 1;
+}
+
+bool PSKlient::dateiGruppeUpdate( int gruppe )
+{
+    if( !verbunden )
+        verbinden();
+    if( !verbunden )
+        return 0;
+    lock();
+    k->sende( "\x15", 1 );
+    unsigned char res = 0;
+    k->getNachricht( (char*)&res, 1 );
+    if( res == 1 )
+    {
+        k->sende( (char*)&gruppe, 4 );
+        k->getNachricht( (char*)&res, 1 );
+    }
+    if( res == 3 )
+    {
+        k->getNachricht( (char*)&res, 1 );
+        char *txt = new char[ res + 1 ];
+        k->getNachricht( txt, res );
+        txt[ res ] = 0;
+        fehler->setText( "Fehler während getSystemInfoList bei PatchServer.\nServer Rückgabe:" );
+        fehler->append( txt );
+        delete[] txt;
+        unlock();
+        return 0;
+    }
+    unlock();
+    return 1;
+}
+
+void PSKlient::abbruch()
+{
+	if( verbunden )
+		k->trenne();
+	eingeloggt = 0;
+	verbunden = 0;
+}
+
+// Reference Counting
+LTSKlient *PSKlient::getThis()
+{
+	ref++;
+	return this;
+}
+
+LTSKlient *PSKlient::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}

+ 53 - 0
SMP/Netzwerk/Patch/PSKlient.h

@@ -0,0 +1,53 @@
+#ifndef PSKlient_H
+#define PSKlient_H
+
+#include "../LTSKlient.h"
+#include <Array.h>
+#include <Text.h>
+#include <ReferenceCounting.h>
+#include <Zeit.h>
+
+using namespace Network;
+using namespace Framework;
+
+struct FileGroupInfo
+{
+    int id;
+    Text name;
+    Text status;
+    Text path;
+    int version;
+};
+
+struct FileInfo
+{
+    int id;
+    Text path;
+    int version;
+    Text time;
+};
+
+class PSKlient : public LTSKlient
+{
+public:
+    // Konstruktor
+    PSKlient( const char *ip, int port );
+    // Destruktor
+    ~PSKlient();
+    // nicht constant
+    bool getDateiListe( int *systemAnzahl, Array< int > *dateiAnzahl, RCArray< Text > *systeme, RCArray< RCArray< Text > > *dateien );
+    bool updateFertig();
+    bool updateStarten( int dateiGruppeId );
+    bool getFileGroupInfoList( Array< FileGroupInfo* > *list );
+    bool getSystemInfoList( RCArray< ReferenceCounting< std::pair< int, Text > > > *list );
+    bool getFileInfoList( int system, int group, RCArray< ReferenceCounting< FileInfo > > *list );
+    bool getFileVersion( char *path, int system, int group, int *version );
+    bool updateFile( const char *pfad, Zeit *zLetzteÄnderung, int system, int gruppe );
+    bool dateiGruppeUpdate( int gruppe );
+    void abbruch();
+    // Reference Counting
+    virtual LTSKlient *getThis();
+    virtual LTSKlient *release();
+};
+
+#endif

+ 41 - 0
SMP/Programm/Basic/Abschnitt.cpp

@@ -0,0 +1,41 @@
+#include "Abschnitt.h"
+#include <Bildschirm.h>
+
+// Inhalt der Abschnitt Klasse aus Abschnitt.h
+// Konstruktor
+Abschnitt::Abschnitt( Bildschirm *b )
+{
+	this->b = b;
+	sichtbar = 0;
+	ref = 1;
+}
+
+// Destruktor
+Abschnitt::~Abschnitt()
+{
+	if( b )
+		b->release();
+}
+
+int Abschnitt::getColorFromStatus( char *status )
+{
+    if( Text( "Unbekannt" ).istGleich( status ) )
+        return 0xFFFF8800;
+    if( Text( "Unerreichbar" ).istGleich( status ) )
+        return 0xFFFF0000;
+    if( Text( "Offline" ).istGleich( status ) )
+        return 0xFFFFFF00;
+    if( Text( "Pausiert" ).istGleich( status ) )
+        return 0xFF88FF00;
+    if( Text( "Online" ).istGleich( status ) )
+        return 0xFF00FF00;
+    if( Text( "Veraltet" ).istGleich( status ) )
+        return 0xFFB0FF00;
+    return 0xFFFFFFFF;
+}
+
+// constant
+bool Abschnitt::istSichtbar() const
+{
+	return sichtbar;
+}

+ 32 - 0
SMP/Programm/Basic/Abschnitt.h

@@ -0,0 +1,32 @@
+#ifndef Abschnitt_H
+#define Abschnitt_H
+
+#include <Fenster.h>
+
+using namespace Framework;
+
+class Abschnitt
+{
+protected:
+	Bildschirm *b;
+	bool sichtbar;
+	int ref;
+
+    int getColorFromStatus( char *status );
+
+public:
+	// Konstruktor
+	Abschnitt( Bildschirm *b );
+	// Destruktor
+	~Abschnitt();
+	// nicht constant
+	virtual void setFenster( Fenster *f ) = 0;
+	virtual void setSichtbar( bool s ) = 0;
+	// constant
+	bool istSichtbar() const;
+	// Reference Counting
+	virtual Abschnitt *getThis() = 0;
+	virtual Abschnitt *release() = 0;
+};
+
+#endif

+ 111 - 0
SMP/Programm/Beenden/Beenden.cpp

@@ -0,0 +1,111 @@
+#include "Beenden.h"
+#include <TextFeld.h>
+#include <Schrift.h>
+#include <Punkt.h>
+
+// Inhalt der Beenden Klasse aus Beenden.h
+// Konstruktor
+Beenden::Beenden( Schrift *s, Bildschirm *b )
+: Abschnitt( b )
+{
+	f = new Fenster();
+	f->setStyle( Fenster::Style::Sichtbar | Fenster::Style::Erlaubt | Fenster::Style::Titel | Fenster::Style::Rahmen | Fenster::Style::TitelBuffered );
+	f->setRFarbe( 0xFFFFFFFF );
+	f->setRBreite( 1 );
+	f->setTitel( "Beenden" );
+	f->setTAfFarbe( 0x1000FF00 );
+	f->setTAfStrength( -15 );
+	f->setTRBreite( 1 );
+	f->setTRFarbe( 0xFFFFFFFF );
+	f->zTTextFeld()->addStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Center | TextFeld::Style::Rahmen );
+	f->zTTextFeld()->setSize( 0, 20 );
+	f->setTSchriftZ( s->getThis() );
+	f->setTSFarbe( 0xFFFFFFFF );
+	f->setSize( 300, 150 );
+
+	text = new TextFeld();
+	text->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Mehrzeilig );
+	text->setText( "Möchtest du das SMP wirklich beenden?" );
+	text->setPosition( 10, 10 );
+	text->setSize( 280, 70 );
+	text->setSchriftZ( s->getThis() );
+	text->setSchriftSize( 12 );
+	text->setSchriftFarbe( 0xFFFFFFFF );
+	f->addMember( text );
+
+	beenden = new Knopf( );
+	beenden->setStyle( Knopf::Style::Normal );
+	beenden->setText( "Beenden" );
+	beenden->setSchriftZ( s->getThis() );
+	beenden->setSize( 100, 20 );
+	beenden->setPosition( 190, 100 );
+	beenden->setMausEreignisParameter( this );
+	beenden->setMausEreignis( beendenBeendenMausEreignis );
+	f->addMember( beenden );
+
+	fenster = 0;
+	ref = 1;
+	s->release();
+}
+
+// Destruktor
+Beenden::~Beenden()
+{
+	f->release();
+	text->release();
+	beenden->release();
+	if( fenster )
+		fenster->release();
+}
+
+// nicht constant
+void Beenden::setFenster( Fenster *f )
+{
+	if( fenster )
+		fenster->release();
+	this->f->setPosition( f->getBreite() / 2 - 150, f->getHeight() / 2 - 75 );
+	fenster = f;
+}
+
+void Beenden::setSichtbar( bool s )
+{
+	sichtbar = s;
+	if( !fenster )
+		return;
+	if( s )
+		fenster->addMember( f );
+	else
+		fenster->removeMember( f );
+}
+
+bool Beenden::beendenMausEreignis( void *obj, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+		PostQuitMessage( 0 );
+	return 1;
+}
+
+// constant
+
+// Reference Counting
+Abschnitt *Beenden::getThis()
+{
+	ref++;
+	return this;
+}
+
+Abschnitt *Beenden::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}
+
+// Ereignisse
+bool beendenBeendenMausEreignis( void *p, void *obj, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Beenden*)p )->beendenMausEreignis( obj, me );
+}

+ 36 - 0
SMP/Programm/Beenden/Beenden.h

@@ -0,0 +1,36 @@
+#ifndef Beenden_H
+#define Beenden_H
+
+#include <Knopf.h>
+#include <MausEreignis.h>
+#include "..\Basic\Abschnitt.h"
+
+class Beenden : public Abschnitt
+{
+private:
+	Fenster *fenster;
+	Fenster *f;
+	TextFeld *text;
+	Knopf *beenden;
+	int ref;
+
+public:
+	// Konstruktor
+	Beenden( Schrift *s, Bildschirm *b );
+	// Destruktor
+	~Beenden();
+	// nicht constant
+	virtual void setFenster( Fenster *f );
+	virtual void setSichtbar( bool s );
+	bool beendenMausEreignis( void *obj, MausEreignis me );
+	// constant
+
+	// Reference Counting
+	virtual Abschnitt *getThis();
+	virtual Abschnitt *release();
+};
+
+// Ereignisse
+bool beendenBeendenMausEreignis( void *p, void *obj, MausEreignis me );
+
+#endif

+ 372 - 0
SMP/Programm/Login/Login.cpp

@@ -0,0 +1,372 @@
+#include "Login.h"
+#include <Text.h>
+#include <Schrift.h>
+#include <TextFeld.h>
+#include "..\Server\Patch\PatchServer.h"
+#include "..\Version\Version.h"
+
+// Inhalt der AktionThread Klasse aus Login.h
+// Konstruktor
+AktionThread::AktionThread( int ak, Bildschirm *zScreen, Programm *zProg )
+	: Thread()
+{
+	this->ak = ak;
+	zB = zScreen;
+	zP = zProg;
+	ref = 1;
+	start();
+}
+
+// Destruktor
+AktionThread::~AktionThread()
+{
+
+}
+
+// nicht constant
+void AktionThread::thread()
+{
+	zB->lock();
+	switch( ak )
+	{
+	case 0:
+		zP->removeAbschnitt( "Patch Server" );
+		zP->removeAbschnitt( "Version" );
+		break;
+	}
+	zB->unlock();
+	release();
+}
+
+// constant
+
+// Reference Counting
+AktionThread *AktionThread::getThis()
+{
+	ref++;
+	return this;
+}
+
+AktionThread *AktionThread::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}
+
+
+// Inhalt der AdminAccount Klasse aus Login.h
+// Konstruktor
+AdminAccount::AdminAccount( const char *name, const char *passwort )
+{
+	this->name = new Text( name );
+	this->passwort = new Text( passwort );
+	ref = 1;
+}
+
+// Destruktor
+AdminAccount::~AdminAccount()
+{
+	name->release();
+	passwort->release();
+}
+
+// nicht constant
+void AdminAccount::login( const char *name, const char *passwort )
+{
+	this->name = new Text( name );
+	this->passwort = new Text( passwort );
+}
+
+// constant
+Text *AdminAccount::getName() const
+{
+	return name->getThis();
+}
+
+Text *AdminAccount::zName() const
+{
+	return name;
+}
+
+Text *AdminAccount::getPasswort() const
+{
+	return passwort->getThis();
+}
+
+Text *AdminAccount::zPasswort() const
+{
+	return passwort;
+}
+
+// Reference Counting
+AdminAccount *AdminAccount::getThis()
+{
+	ref++;
+	return this;
+}
+
+AdminAccount *AdminAccount::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}
+
+
+// Inhalt der Login Klasse aus Login.h
+// Konstruktor
+Login::Login( Schrift *s, Programm *zP, InitDatei *iDat, RessourceBild *resB, Bildschirm *b )
+	: Abschnitt( b )
+{
+	account = 0;
+	fenster = 0;
+	zProg = zP;
+	iD = iDat;
+	rB = resB;
+	schrift = s;
+
+	f = new Fenster();
+	f->setStyle( Fenster::Style::Sichtbar | Fenster::Style::Erlaubt | Fenster::Style::Rahmen | Fenster::Style::Titel | Fenster::Style::TitelBuffered );
+	f->setRFarbe( 0xFFFFFFFF );
+	f->setRBreite( 1 );
+	f->setTitel( "Login" );
+	f->setTSchriftZ( s->getThis() );
+	f->setTSFarbe( 0xFFFFFFFF );
+	f->setTSSize( 12 );
+	f->setTAfFarbe( 0x1000FF00 );
+	f->setTAfStrength( -15 );
+	f->setTRFarbe( 0xFFFFFFFF );
+	f->setTRBreite( 1 );
+	f->zTTextFeld()->addStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Center | TextFeld::Style::Rahmen );
+	f->zTTextFeld()->setSize( 0, 20 );
+	f->setSize( 300, 120 );
+
+	logout = new TextFeld();
+	logout->setStyle( TextFeld::Style::HCenter );
+	logout->setSchriftZ( s->getThis() );
+	logout->setSchriftFarbe( 0xFFFFFFFF );
+	logout->setSchriftSize( 12 );
+	logout->setText( "Möchtest du dich wirklich ausloggen?" );
+	logout->setSize( 300, 20 );
+	logout->setPosition( 0, 20 );
+	f->addMember( logout );
+
+	name = new TextFeld();
+	name->setStyle( TextFeld::Style::TextFeld );
+	name->setSchriftZ( s->getThis() );
+	name->setSchriftFarbe( 0xFFFFFFFF );
+	name->setSchriftSize( 12 );
+	name->setAlphaFeldFarbe( 0x1000FF00 );
+	name->setAlphaFeldStrength( -5 );
+	name->setTastaturEreignisParameter( this );
+	name->setTastaturEreignis( loginNameTastaturEreignis );
+	name->setSize( 200, 20 );
+	name->setPosition( 50, 10 );
+	name->setText( "Name" );
+	name->setLinienRahmenFarbe( 0xFFFFFFFF );
+	name->setLinienRahmenBreite( 1 );
+	f->addMember( name );
+
+	passwort = new TextFeld();
+	passwort->setStyle( TextFeld::Style::TextFeld );
+	passwort->setSchriftZ( s->getThis() );
+	passwort->setSchriftFarbe( 0xFFFFFFFF );
+	passwort->setSchriftSize( 12 );
+	passwort->setAlphaFeldFarbe( 0x1000FF00 );
+	passwort->setAlphaFeldStrength( -5 );
+	passwort->setTastaturEreignisParameter( this );
+	passwort->setTastaturEreignis( loginPasswortTastaturEreignis );
+	passwort->setSize( 200, 20 );
+	passwort->setPosition( 50, 40 );
+	passwort->setText( "Passwort" );
+	passwort->setLinienRahmenFarbe( 0xFFFFFFFF );
+	passwort->setLinienRahmenBreite( 1 );
+	f->addMember( passwort );
+
+	login = new Knopf();
+	login->setStyle( Knopf::Style::Normal );
+	login->setText( "Login" );
+	login->setSchriftZ( s->getThis() );
+	login->setMausEreignisParameter( this );
+	login->setMausEreignis( loginLoginMausEreignis );
+	login->setSize( 150, 20 );
+	login->setPosition( 75, 70 );
+	f->addMember( login );
+
+	ref = 1;
+}
+
+// Destruktor
+Login::~Login()
+{
+	if( fenster )
+		fenster->release();
+	f->release();
+	name->release();
+	passwort->release();
+	login->release();
+	if( account )
+		account->release();
+	logout->release();
+	iD->release();
+	rB->release();
+	schrift->release();
+}
+
+// nicht constant
+void Login::setFenster( Fenster *f )
+{
+	if( fenster )
+		fenster->release();
+	this->f->setPosition( f->getBreite() / 2 - 150, f->getHeight() / 2 - 60 );
+	fenster = f;
+}
+
+void Login::setSichtbar( bool s )
+{
+	sichtbar = s;
+	if( s )
+	{
+		name->addStyle( TextFeld::Style::Fokus );
+		name->setAuswahl( name->zText()->getLength(), 0 );
+		fenster->addMember( f );
+	}
+	else
+	{
+		fenster->removeMember( f );
+	}
+}
+
+bool Login::nameTastaturEreignis( void *obj, TastaturEreignis te )
+{
+	if( te.id == TE_Release )
+	{
+		if( te.taste == T_Enter || te.taste == T_Unten || te.taste == T_Tab )
+		{
+			name->removeStyle( TextFeld::Style::Fokus );
+			passwort->addStyle( TextFeld::Style::Fokus );
+			passwort->setAuswahl( passwort->zText()->getLength(), 0 );
+		}
+	}
+	return 1;
+}
+
+bool Login::passwortTastaturEreignis( void *obj, TastaturEreignis te )
+{
+	passwort->setSchowChar( '*' );
+	if( te.id == TE_Release )
+	{
+		if( te.taste == T_Enter )
+		{
+			passwort->removeStyle( TextFeld::Style::Fokus );
+			MausEreignis me;
+			me.id = ME_RLinks;
+			me.mx = login->getX() + 1;
+			me.my = login->getY() + 1;
+			me.verarbeitet = 0;
+			b->lock();
+			login->doMausEreignis( me );
+			b->unlock();
+		}
+	}
+	return 1;
+}
+
+bool Login::loginMausEreignis( void *obj, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+	{
+		if( f->zTitel()->istGleich( "Login" ) )
+		{
+            MSKlient *msk = new MSKlient( iD->zWert( "MainServerIP" )->getText(), TextZuInt( iD->zWert( "MainServerPort" )->getText(), 10 ) );
+            if( msk->login( account->zName()->getText(), account->zPasswort()->getText() ) )
+            {
+                if( !account )
+                    account = new AdminAccount( name->zText()->getText(), passwort->zText()->getText() );
+                else
+                    account->login( name->zText()->getText(), passwort->zText()->getText() );
+                f->setTitel( "Logout" );
+                name->removeStyle( TextFeld::Style::Sichtbar );
+                passwort->removeStyle( TextFeld::Style::Sichtbar );
+                logout->addStyle( TextFeld::Style::Sichtbar );
+                login->setText( "Logout" );
+                zProg->renameAbschnitt( "Login", "Logout" );
+                // Abshnitte erstellen
+                PatchServer *psA = new PatchServer( schrift->getThis(), iD->getThis(), msk->getThis(), rB->getThis(), account->getThis(), b->getThis() );
+                zProg->addAbschnitt( "Patch Server", psA );
+                Version *vA = new Version( schrift->getThis(), msk->getThis(), rB->getThis(), account->getThis(), b->getThis() );
+                zProg->addAbschnitt( "Version", vA );
+                zProg->abschnittAuswählen( "Patch Server" );
+            }
+            else
+                WMessageBox( 0, new Text( "Fehler" ), new Text( msk->getLetzterFehler() ), MB_ICONERROR );
+            msk->release();
+		}
+		else
+		{
+			new AktionThread( 0, b, zProg );
+			f->setTitel( "Login" );
+			name->addStyle( TextFeld::Style::Sichtbar );
+			passwort->addStyle( TextFeld::Style::Sichtbar );
+			logout->removeStyle( TextFeld::Style::Sichtbar );
+			login->setText( "Login" );
+			account = account->release();
+			zProg->renameAbschnitt( "Logout", "Login" );
+			name->setText( "Name" );
+			passwort->setText( "Passwort" );
+			passwort->setSchowChar( 0 );
+		}
+	}
+	return 1;
+}
+
+// constant
+AdminAccount *Login::getAccount() const
+{
+	return account ? account->getThis() : 0;
+}
+
+AdminAccount *Login::zAccount() const
+{
+	return account;
+}
+
+// Reference Counting
+Abschnitt *Login::getThis()
+{
+	ref++;
+	return this;
+}
+
+Abschnitt *Login::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}
+
+// Ereignisse
+bool loginNameTastaturEreignis( void *p, void *obj, TastaturEreignis te )
+{
+	if( !p )
+		return 0;
+	return ( (Login*)p )->nameTastaturEreignis( obj, te );
+}
+
+bool loginPasswortTastaturEreignis( void *p, void *obj, TastaturEreignis te )
+{
+	if( !p )
+		return 0;
+	return ( (Login*)p )->passwortTastaturEreignis( obj, te );
+}
+
+bool loginLoginMausEreignis( void *p, void *obj, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Login*)p )->loginMausEreignis( obj, me );
+}

+ 97 - 0
SMP/Programm/Login/Login.h

@@ -0,0 +1,97 @@
+#ifndef Login_H
+#define Login_H
+
+#include <Knopf.h>
+#include <MausEreignis.h>
+#include <TastaturEreignis.h>
+#include <Thread.h>
+#include "..\Basic\Abschnitt.h"
+#include "..\Programm.h"
+
+class AktionThread : public Thread
+{
+private:
+	Bildschirm *zB;
+	Programm *zP;
+	int ak;
+	int ref;
+
+public:
+	// Konstruktor
+	AktionThread( int ak, Bildschirm *zScreen, Programm *zProg );
+	// Destruktor
+	~AktionThread();
+	// nicht constant
+	virtual void thread();
+	// constant
+
+	// Reference Counting
+	AktionThread *getThis();
+	AktionThread *release();
+};
+
+class AdminAccount
+{
+private:
+	Text *name;
+	Text *passwort;
+	int ref;
+
+public:
+	// Konstruktor
+	AdminAccount( const char *name, const char *passwort );
+	// Destruktor
+	~AdminAccount();
+	// nicht constant
+	void login( const char *name, const char *passwort );
+	// constant
+	Text *getName() const;
+	Text *zName() const;
+	Text *getPasswort() const;
+	Text *zPasswort() const;
+	// Reference Counting
+	AdminAccount *getThis();
+	AdminAccount *release();
+};
+
+class Login : public Abschnitt
+{
+private:
+	Fenster *fenster;
+	Fenster *f;
+	TextFeld *logout;
+	TextFeld *name;
+	TextFeld *passwort;
+	Knopf *login;
+	AdminAccount *account;
+	Programm *zProg;
+	Schrift *schrift;
+	InitDatei *iD;
+	RessourceBild *rB;
+	int ref;
+
+public:
+	// Konstruktor
+	Login( Schrift *s, Programm *zP, InitDatei *iDat, RessourceBild *resB, Bildschirm *b );
+	// Destruktor
+	~Login();
+	// nicht constant
+	virtual void setFenster( Fenster *f );
+	virtual void setSichtbar( bool s );
+	bool nameTastaturEreignis( void *obj, TastaturEreignis te );
+	bool passwortTastaturEreignis( void *obj, TastaturEreignis te );
+	bool loginMausEreignis( void *obj, MausEreignis me );
+	// constant
+	AdminAccount *getAccount() const;
+	AdminAccount *zAccount() const;
+	// Reference Counting
+	virtual Abschnitt *getThis();
+	virtual Abschnitt *release();
+};
+
+// Ereignisse
+bool loginNameTastaturEreignis( void *p, void *obj, TastaturEreignis te );
+bool loginPasswortTastaturEreignis( void *p, void *obj, TastaturEreignis te );
+bool loginLoginMausEreignis( void *p, void *obj, MausEreignis me );
+
+#endif

+ 206 - 0
SMP/Programm/Programm.cpp

@@ -0,0 +1,206 @@
+#include "Programm.h"
+#include <Punkt.h>
+#include <Rahmen.h>
+
+// Inhalt der Programm Klasse aus Programm.h
+// Konstruktor
+Programm::Programm( Bildschirm *b, Schrift *s )
+{
+	bildschirm = b;
+	schrift = s;
+
+	Punkt bg = b->getBackBufferSize();
+	kFenster = new Fenster();
+	kFenster->setStyle( Fenster::Style::Sichtbar | Fenster::Style::Erlaubt | Fenster::Style::Rahmen | Fenster::Style::VScroll );
+	kFenster->setRFarbe( 0xFFFFFFFF );
+	kFenster->setRBreite( 1 );
+	kFenster->setPosition( bg.x - 200, 0 );
+	kFenster->setSize( 200, bg.y );
+	kFenster->setVSBMax( 0 );
+	bildschirm->addMember( kFenster );
+
+	mFenster = new Fenster();
+	mFenster->setStyle( Fenster::Style::Erlaubt | Fenster::Style::Sichtbar );
+	mFenster->setSize( bg.x - 200, bg.y );
+	bildschirm->addMember( mFenster );
+
+	auswahlRahmen = new LRahmen();
+	auswahlRahmen->setPosition( 0, -30 );
+	auswahlRahmen->setSize( 182, 30 );
+	auswahlRahmen->setRamenBreite( 1 );
+	auswahlRahmen->setFarbe( 0xFFFFFFFF );
+	kFenster->addMember( auswahlRahmen );
+
+	sichtbar = -1;
+
+	name = new RCArray< Text >();
+	knopf = new RCArray< Knopf >();
+	abschnitte = new RCArray< Abschnitt >();
+
+	abschnittAnzahl = 0;
+
+	ref = 1;
+}
+
+// Destruktor
+Programm::~Programm()
+{
+	bildschirm->removeMember( kFenster );
+	bildschirm->removeMember( mFenster );
+	name->release();
+	knopf->release();
+	abschnitte->release();
+	auswahlRahmen->release();
+	kFenster->release();
+	mFenster->release();
+	bildschirm->release();
+	schrift->release();
+}
+
+// nicht constant
+bool Programm::addAbschnitt( const char *name, Abschnitt *abschnitt )
+{
+	bool hat = 0;
+	for( int i = 0; i < abschnittAnzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+		{
+			hat = 1;
+			break;
+		}
+	}
+	if( hat )
+	{
+		abschnitt->release();
+		return 0;
+	}
+	Knopf *k = new Knopf();
+	k->setStyle( Knopf::Style::Normal );
+	k->setSize( 150, 20 );
+	k->setPosition( 16, abschnittAnzahl * 30 + 5 );
+	k->setSchriftZ( schrift->getThis() );
+	k->setText( name );
+	k->setMausEreignisParameter( this );
+	k->setMausEreignis( programmAbschnittME );
+	kFenster->addMember( k );
+
+	this->name->add( new Text( name ), abschnittAnzahl );
+	knopf->add( k, abschnittAnzahl );
+	abschnitte->add( abschnitt, abschnittAnzahl );
+	abschnittAnzahl++;
+
+	abschnitt->setFenster( mFenster->getThis() );
+
+	if( sichtbar < 0 )
+	{
+		sichtbar = 0;
+		auswahlRahmen->setPosition( 0, 0 );
+		abschnitt->setSichtbar( 1 );
+	}
+	kFenster->setVSBMax( abschnittAnzahl * 30 );
+	return 1;
+}
+
+bool Programm::removeAbschnitt( const char *name )
+{
+	for( int i = 0; i < abschnittAnzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+		{
+			if( sichtbar == i )
+				abschnitte->z( i )->setSichtbar( 0 );
+			this->name->remove( i );
+			kFenster->removeMember( knopf->z( i ) );
+			knopf->remove( i );
+			abschnitte->remove( i );
+			abschnittAnzahl--;
+			if( sichtbar >= abschnittAnzahl )
+				sichtbar = abschnittAnzahl - 1;
+			if( sichtbar > i )
+				sichtbar--;
+			if( sichtbar >= 0 && !abschnitte->z( sichtbar )->istSichtbar() )
+				abschnitte->z( i )->setSichtbar( 1 );
+			auswahlRahmen->setPosition( auswahlRahmen->getX(), sichtbar * 30 );
+			kFenster->setVSBMax( abschnittAnzahl * 30 );
+			return 1;
+		}
+	}
+	return 0;
+}
+
+bool Programm::renameAbschnitt( const char *name, const char *newName )
+{
+	for( int i = 0; i < abschnittAnzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+		{
+			this->name->z( i )->setText( newName );
+			knopf->z( i )->setText( newName );
+			return 1;
+		}
+	}
+	return 0;
+}
+
+bool Programm::abschnittAuswählen( const char *name )
+{
+	for( int i = 0; i < abschnittAnzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+		{
+			if( sichtbar == i )
+				break;
+			abschnitte->z( sichtbar )->setSichtbar( 0 );
+			sichtbar = i;
+			abschnitte->z( i )->setSichtbar( 1 );
+			auswahlRahmen->setPosition( auswahlRahmen->getX(), sichtbar * 30 );
+			return 1;
+		}
+	}
+	return 0;
+}
+
+bool Programm::abschnittMausEreignis( void *obj, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+		abschnittAuswählen( ( (Knopf*)obj )->zText()->getText() );
+	return 1;
+}
+
+// constant
+Text *Programm::getSichtbarAbschnittName() const
+{
+	if( sichtbar >= abschnittAnzahl )
+		return 0;
+	return name->get( sichtbar );
+}
+
+Text *Programm::zSichtbarAbschnittName() const
+{
+	if( sichtbar >= abschnittAnzahl )
+		return 0;
+	return name->z( sichtbar );
+}
+
+// Reference Counting
+Programm *Programm::getThis()
+{
+	ref++;
+	return this;
+}
+
+Programm *Programm::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}
+
+// Ereignis
+bool programmAbschnittME( void *p, void *obj, MausEreignis me )
+{
+	if( p )
+		return ( (Programm*)p )->abschnittMausEreignis( obj, me );
+	return 0;
+}

+ 52 - 0
SMP/Programm/Programm.h

@@ -0,0 +1,52 @@
+#ifndef Programm_H
+#define Programm_H
+
+#include <Bildschirm.h>
+#include <InitDatei.h>
+#include <Fenster.h>
+#include <Array.h>
+#include <Knopf.h>
+#include "..\Ressourcen\Ressourcen.h"
+#include "Basic\Abschnitt.h"
+#include <MausEreignis.h>
+
+using namespace Framework;
+
+class Programm
+{
+private:
+	Bildschirm *bildschirm;
+	Schrift *schrift;
+	Fenster *kFenster;
+	Fenster *mFenster;
+	LRahmen *auswahlRahmen;
+	RCArray< Text > *name;
+	RCArray< Knopf > *knopf;
+	RCArray< Abschnitt > *abschnitte;
+	int abschnittAnzahl;
+	int sichtbar;
+	int ref;
+
+public:
+	// Konstruktor
+	Programm( Bildschirm *b, Schrift *s );
+	// Destruktor
+	~Programm();
+	// nicht constant
+	bool addAbschnitt( const char *name, Abschnitt *abschnitt );
+	bool removeAbschnitt( const char *name );
+	bool renameAbschnitt( const char *name, const char *newName );
+	bool abschnittAuswählen( const char *name );
+	bool abschnittMausEreignis( void *obj, MausEreignis me );
+	// constant
+	Text *getSichtbarAbschnittName() const;
+	Text *zSichtbarAbschnittName() const;
+	// Reference Counting
+	Programm *getThis();
+	Programm *release();
+};
+
+// Ereignis
+bool programmAbschnittME( void *p, void *obj, MausEreignis me );
+
+#endif

+ 1688 - 0
SMP/Programm/Server/Patch/PatchServer.cpp

@@ -0,0 +1,1688 @@
+#include "PatchServer.h"
+#include <TextFeld.h>
+#include <MausEreignis.h>
+#include "..\..\Login\Login.h"
+#include <Datei.h>
+#include <iostream>
+
+// Inhalt der PSUpdate Klasse aus PatchServer.h
+// Kontruktor
+PSUpdate::PSUpdate( PatchServer *zPSA, AdminAccount *account )
+{
+    this->account = account;
+    this->zPSA = zPSA;
+    gruppeAnzahl = 0;
+    gruppeId = 0;
+    this->psc = 0;
+    id = 0;
+    ref = 1;
+}
+
+// Destruktor
+PSUpdate::~PSUpdate()
+{
+    ende();
+    if( psc )
+    {
+        psc->abbruch();
+        psc->release();
+    }
+    account->release();
+    delete[] gruppeId;
+}
+
+// nicht constant
+void PSUpdate::setServer( const char *ip, unsigned short port )
+{
+    if( psc )
+    {
+        psc->abbruch();
+        psc->release();
+    }
+    psc = new PSKlient( ip, port );
+}
+
+void PSUpdate::setUpdateListe( int gAnzahl, Array< int > *gId )
+{
+    gruppeAnzahl = gAnzahl;
+    delete[] gruppeId;
+    gruppeId = 0;
+    if( gAnzahl )
+    {
+        gruppeId = new int[ gAnzahl ];
+        for( int i = 0; i < gAnzahl; i++ )
+            gruppeId[ i ] = gId->get( i );
+    }
+}
+
+void PSUpdate::thread()
+{
+    if( !psc )
+    {
+        for( int g = 0; g < gruppeAnzahl; g++ )
+            zPSA->setUpdateFertig( 1, gruppeId[ g ] );
+        return;
+    }
+    if( !psc->login( account->zName()->getText(), account->zPasswort()->getText() ) )
+    {
+        for( int g = 0; g < gruppeAnzahl; g++ )
+            zPSA->setUpdateFertig( 1, gruppeId[ g ] );
+        return;
+    }
+    Array< FileGroupInfo* > fileGroupList;
+    psc->getFileGroupInfoList( &fileGroupList );
+    RCArray< ReferenceCounting< std::pair< int, Text > > > systemT;
+    psc->getSystemInfoList( &systemT );
+    int gAnz = fileGroupList.getEintragAnzahl();
+    for( int g = 0; g < gruppeAnzahl; g++ )
+    {
+        Text *initPfad = new Text( "data/" );
+        for( int i = 0; i < gAnz; i++ )
+        {
+            if( gruppeId[ g ] == fileGroupList.get( i )->id )
+            {
+                initPfad->append( (char*)fileGroupList.get( i )->name );
+                break;
+            }
+        }
+        initPfad->append( ".ini" );
+        InitDatei *systemInit = new InitDatei( initPfad );
+        systemInit->laden();
+        bool cont = 0;
+        int sAnz = systemT.getEintragAnzahl();
+        for( int i = 0; i < sAnz; i++ ) // Prüfen, ob Lokale Version aktuell ist
+        {
+            if( !systemInit->wertExistiert( systemT.z( i )->second ) )
+            {
+                systemInit->release();
+                zPSA->setUpdateFertig( 1, gruppeId[ g ] );
+                cont = 1;
+                break;
+            }
+            Text *pfad = new Text( systemInit->zWert( (char*)systemT.z( i )->second )->getText() );
+            pfad->append( "/" );
+            RCArray< ReferenceCounting< FileInfo > > dateiT;
+            psc->getFileInfoList( systemT.z( i )->first, gruppeId[ g ], &dateiT );
+            int dAnz = dateiT.getEintragAnzahl();
+            bool br = 0;
+            for( int j = 0; j < dAnz; j++ )
+            {
+                Text *pf = new Text( pfad->getText() );
+                pf->append( dateiT.z( j )->path.getText() );
+                if( !DateiExistiert( pf->getThis() ) )
+                {
+                    pfad->release();
+                    pf->release();
+                    systemInit->release();
+                    zPSA->setUpdateFertig( 1, gruppeId[ g ] );
+                    cont = 1;
+                    br = 1;
+                    break;
+                }
+                if( !DateiIstVerzeichnis( pf->getThis() ) )
+                {
+                    Datei *d = new Datei();
+                    d->setDatei( pf->getText() );
+                    Zeit *zeit = d->getLastChange();
+                    d->release();
+                    if( !zeit->istGleich( "y-m-d h:i:s", dateiT.z( j )->time.getText() ) )
+                    {
+                        zeit->release();
+                        pfad->release();
+                        pf->release();
+                        systemInit->release();
+                        zPSA->setUpdateFertig( 1, gruppeId[ g ] );
+                        cont = 1;
+                        br = 1;
+                        break;
+                    }
+                    zeit->release();
+                }
+                pf->release();
+            }
+            if( br )
+                break;
+            pfad->release();
+        }
+        if( cont )
+            continue;
+        if( psc->updateStarten( gruppeId[ g ] ) )
+        {
+            RCArray< Text > *systemA = new RCArray< Text >();
+            RCArray< RCArray< Text > > *dateiA = new RCArray< RCArray< Text > >();
+            Array< int > *dateiAnzahlA = new Array< int >();
+            int systemAnzahl = 0;
+            bool ok = psc->getDateiListe( &systemAnzahl, dateiAnzahlA, systemA, dateiA );
+            if( !ok )
+            {
+                systemA->release();
+                dateiA->release();
+                dateiAnzahlA->release();
+                psc->abbruch();
+                psc = (PSKlient*)psc->release();
+                systemInit->release();
+                zPSA->setUpdateFertig( 1, gruppeId[ g ] );
+                continue;
+            }
+            __int64 maxAktionen = 0;
+            for( int i = 0; i < systemAnzahl; i++ )
+            {
+                for( int j = 0; j < dateiAnzahlA->get( i ); j++ )
+                {
+                    Text *pfad = new Text( systemInit->zWert( systemA->z( i )->getText() )->getText() );
+                    pfad->append( "/" );
+                    pfad->append( dateiA->z( i )->z( j )->getText() );
+                    Datei *d = new Datei();
+                    d->setDatei( pfad );
+                    if( !d->istOrdner() )
+                        maxAktionen += d->getSize();
+                    d->release();
+                }
+            }
+            __int64 aktionen = 0;
+            int prozent = 0;
+            bool br = 0;
+            for( int i = 0; i < systemAnzahl; i++ )
+            {
+                for( int j = 0; j < dateiAnzahlA->get( i ); j++ )
+                {
+                    Text *pfad = new Text( systemInit->zWert( systemA->z( i )->getText() )->getText() );
+                    pfad->append( "/" );
+                    pfad->append( dateiA->z( i )->z( j )->getText() );
+                    Datei *d = new Datei();
+                    d->setDatei( pfad );
+                    if( d->istOrdner() )
+                    {
+                        d->release();
+                        continue;
+                    }
+                    __int64 gr = d->getSize();
+                    d->open( Datei::Style::lesen );
+                    psc->lock();
+                    psc->zKlient()->sende( "\xE", 1 );
+                    char ret = 0;
+                    psc->zKlient()->getNachricht( &ret, 1 );
+                    if( ret == 1 )
+                    {
+                        int system = 0;
+                        for( int s = 0; s < sAnz; s++ )
+                        {
+                            if( systemT.z( s )->second.istGleich( systemA->z( i )->getText() ) )
+                                system = systemT.z( s )->first;
+                        }
+                        psc->zKlient()->sende( (char*)&system, 4 );
+                        int version;
+                        psc->getFileVersion( dateiA->z( i )->z( j )->getText(), system, gruppeId[ g ], &version );
+                        psc->zKlient()->sende( (char*)&version, 4 );
+                        short län = dateiA->z( i )->z( j )->getLength();
+                        psc->zKlient()->sende( (char*)&län, 2 );
+                        psc->zKlient()->sende( dateiA->z( i )->z( j )->getText(), län );
+                        psc->zKlient()->getNachricht( &ret, 1 );
+                        if( ret == 1 )
+                        {
+                            while( gr )
+                            {
+                                if( gr >= 2048 )
+                                {
+                                    gr -= 2048;
+                                    län = 2048;
+                                }
+                                else
+                                {
+                                    län = (int)gr;
+                                    gr = 0;
+                                }
+                                if( län < 0 )
+                                    break;
+                                psc->zKlient()->sende( (char*)&län, 2 );
+                                char *buff = new char[ län ];
+                                d->lese( buff, län );
+                                psc->zKlient()->sende( buff, län );
+                                delete[] buff;
+                                aktionen += län;
+                                if( prozent != 100 / ( maxAktionen / (long double)aktionen ) )
+                                {
+                                    prozent = (int)( 100 / ( maxAktionen / (long double)aktionen ) );
+                                    zPSA->setUpdateProzent( prozent, gruppeId[ g ] );
+                                }
+                            }
+                            psc->zKlient()->sende( "\0\0", 2 );
+                            psc->zKlient()->getNachricht( &ret, 1 );
+                        }
+                    }
+                    if( prozent != 100 / ( maxAktionen / (long double)aktionen ) )
+                    {
+                        prozent = (int)( 100 / ( maxAktionen / (long double)aktionen ) );
+                        zPSA->setUpdateProzent( prozent, gruppeId[ g ] );
+                    }
+                    if( ret == 3 )
+                    {
+                        d->close();
+                        d->release();
+                        systemA->release();
+                        dateiA->release();
+                        dateiAnzahlA->release();
+                        char l = 0;
+                        psc->zKlient()->getNachricht( &l, 1 );
+                        char *txt = new char[ l + 1 ];
+                        txt[ l ] = 0;
+                        if( l )
+                            psc->zKlient()->getNachricht( txt, l );
+                        std::cout << "Error: " << txt << "\n";
+                        delete[] txt;
+                        psc->unlock();
+                        psc->trenne();
+                        psc = (PSKlient*)psc->release();
+                        zPSA->setUpdateProzent( 0, gruppeId[ g ] );
+                        zPSA->setUpdateFertig( 1, gruppeId[ g ] );
+                        br = 1;
+                        break;
+                    }
+                    psc->unlock();
+                    d->close();
+                    d->release();
+                }
+                if( br )
+                    break;
+            }
+            if( br )
+                continue;
+            psc->updateFertig();
+            systemA->release();
+            dateiA->release();
+            dateiAnzahlA->release();
+        }
+        else
+        {
+            psc = (PSKlient*)psc->release();
+            systemInit->release();
+            zPSA->setUpdateProzent( 0, gruppeId[ g ] );
+            zPSA->setUpdateFertig( 1, gruppeId[ g ] );
+            continue;
+        }
+        psc = (PSKlient*)psc->release();
+        zPSA->setUpdateProzent( 0, gruppeId[ g ] );
+        zPSA->setUpdateFertig( 0, gruppeId[ g ] );
+        systemInit->release();
+    }
+    for( int i = 0; i < gAnz; i++ )
+        delete fileGroupList.get( i );
+    zPSA->setUpdateFertig( 0, 0 );
+    run = 0;
+}
+
+// constant
+
+// Reference Counting
+PSUpdate *PSUpdate::getThis()
+{
+    ref++;
+    return this;
+}
+
+PSUpdate *PSUpdate::release()
+{
+    ref--;
+    if( !ref )
+        delete this;
+    return 0;
+}
+
+
+// Inhalt der PSDetails Klasse aus PatchServer.h
+// Konstruktor
+PSDetails::PSDetails( PatchServer *zPSA, MSKlient *mk )
+{
+    this->zPSA = zPSA;
+    this->mk = mk;
+    id = 0;
+    ref = 1;
+}
+
+// Destruktor
+PSDetails::~PSDetails()
+{
+    ende();
+    mk->release();
+}
+
+// nicht constant
+void PSDetails::setServerId( int id )
+{
+    this->id = id;
+}
+
+void PSDetails::thread()
+{
+    ServerDetails detail;
+    mk->getPatchServerDetails( id, &detail );
+    if( !mk->getPatchServerDetails( id, &detail ) )
+    {
+        Text *err = new Text( "Fehler: Server Rückgabe: " );
+        err->append( mk->getLetzterFehler() );
+        zPSA->setServerDetails( id, "", "", 0, 0, 0, 0, -2, err );
+    }
+    else
+    {
+        PSKlient *psc = new PSKlient( detail.ip, detail.port );
+        int st = psc->getStatus();
+        if( st >= 0 )
+            psc->trenne();
+        psc->release();
+        zPSA->setServerDetails( id,
+                                detail.name,
+                                detail.ip,
+                                detail.port,
+                                detail.adminPort,
+                                detail.tasks,
+                                detail.maxTasks,
+                                st,
+                                0 );
+    }
+    run = 0;
+}
+
+// constant
+
+// Reference Counting
+PSDetails *PSDetails::getThis()
+{
+    ref++;
+    return this;
+}
+
+PSDetails *PSDetails::release()
+{
+    ref--;
+    if( !ref )
+        delete this;
+    return 0;
+}
+
+
+// Inhalt der PSSuche Klasse aus PatchServer.h
+// Konstruktor
+PSSuche::PSSuche( PatchServer *zPSA, MSKlient *mk )
+{
+    this->zPSA = zPSA;
+    this->mk = mk;
+    ref = 1;
+}
+
+// Destruktor
+PSSuche::~PSSuche()
+{
+    ende();
+    mk->release();
+}
+
+// nicht constant
+void PSSuche::thread()
+{
+    Array< ServerData* > list;
+    if( mk->getPatchServerListe( &list ) )
+    {
+        int anz = list.getEintragAnzahl();
+        for( int i = 0; i < anz; i++ )
+        {
+            int st = -1;
+            ServerData *s = list.get( i );
+            if( !s->status.istGleich( "Unerreichbar" ) )
+            {
+                PSKlient *psc = new PSKlient( s->ip.getText(), s->port );
+                st = psc->getStatus();
+                switch( st )
+                {
+                case -2:
+                    s->status = "Unbekannt";
+                    break;
+                case -1:
+                    s->status = "Unerreichbar";
+                    break;
+                case 0:
+                    s->status = "Offline";
+                    break;
+                case 1:
+                    s->status = "Pausiert";
+                    break;
+                case 2:
+                    s->status = "Online";
+                    break;
+                case 3:
+                    s->status = "Veraltet";
+                    break;
+                }
+                if( st >= 0 )
+                    psc->trenne();
+                psc->release();
+            }
+            zPSA->addServer( s->id,
+                             s->name,
+                             s->ip,
+                             s->port,
+                             s->adminPort,
+                             s->status );
+            delete s;
+        }
+    }
+    zPSA->sucheAbgeschlossen();
+    run = 0;
+}
+
+// constant
+
+// Reference Counting
+PSSuche *PSSuche::getThis()
+{
+    ref++;
+    return this;
+}
+
+PSSuche *PSSuche::release()
+{
+    ref--;
+    if( !ref )
+        delete this;
+    return 0;
+}
+
+
+TextFeld *getTabellenEintrag( const char *txt, Schrift *s, int farbe )
+{
+    TextFeld *tmp = new TextFeld();
+    tmp->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Center );
+    tmp->setSchriftZ( s );
+    tmp->setText( txt );
+    tmp->setSchriftFarbe( farbe );
+    return tmp;
+}
+
+
+// Inhalt der PatchServer Klasse aus PatchServer.h
+// Konstruktor
+PatchServer::PatchServer( Schrift *s, InitDatei *d, MSKlient *msk, RessourceBild *rb, AdminAccount *acc, Bildschirm *b )
+    : Abschnitt( b )
+{
+    fenster = 0;
+    this->msk = msk;
+    iD = d;
+    account = acc;
+    schrift = s;
+    psc = 0;
+
+    f = new Fenster();
+    f->setStyle( Fenster::Style::Sichtbar | Fenster::Style::Erlaubt | Fenster::Style::Rahmen | Fenster::Style::Titel | Fenster::Style::TitelBuffered );
+    f->setRFarbe( 0xFFFFFFFF );
+    f->setRBreite( 1 );
+    f->setTitel( "Patch Server" );
+    f->setTSchriftZ( s->getThis() );
+    f->setTSFarbe( 0xFFFFFFFF );
+    f->setTSSize( 12 );
+    f->setTAfFarbe( 0x1000FF00 );
+    f->setTAfStrength( -15 );
+    f->setTRFarbe( 0xFFFFFFFF );
+    f->setTRBreite( 1 );
+    f->zTTextFeld()->addStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Center | TextFeld::Style::Rahmen );
+    f->zTTextFeld()->setSize( 0, 20 );
+    f->setSize( 492, 277 );
+
+    liste = new Fenster();
+    liste->setStyle( Fenster::Style::Sichtbar | Fenster::Style::Erlaubt );
+    liste->setSize( 490, 255 );
+    f->addMember( liste );
+
+    details = new Fenster();
+    details->setStyle( Fenster::Style::Erlaubt );
+    details->setSize( 490, 255 );
+    f->addMember( details );
+
+    updateF = new Fenster();
+    updateF->setStyle( Fenster::Style::Erlaubt );
+    updateF->setSize( 490, 255 );
+    f->addMember( updateF );
+
+    tabelle = new ObjTabelle();
+    tabelle->setStyle( ObjTabelle::Style::Sichtbar | ObjTabelle::Style::VScroll | ObjTabelle::Style::Rahmen | ObjTabelle::Style::Raster | ObjTabelle::Style::Erlaubt );
+    tabelle->setMausEreignis( _ret1ME );
+    tabelle->setLinienRahmenFarbe( 0xFFFFFFFF );
+    tabelle->setRasterFarbe( 0xFFA0A0A0 );
+    tabelle->setRasterBreite( 1 );
+    tabelle->setPosition( 5, 5 );
+    tabelle->setSize( 480, 220 );
+    tabelle->setVertikalKlickScroll( 5 );
+    tabelle->addSpalte( "id" );
+    tabelle->setSpaltenBreite( 0, 40 );
+    tabelle->addSpalte( "name" );
+    tabelle->setSpaltenBreite( 1, 105 );
+    tabelle->addSpalte( "ip" );
+    tabelle->setSpaltenBreite( 2, 90 );
+    tabelle->addSpalte( "port" );
+    tabelle->setSpaltenBreite( 3, 50 );
+    tabelle->addSpalte( "aport" );
+    tabelle->setSpaltenBreite( 4, 50 );
+    tabelle->addSpalte( "status" );
+    tabelle->setSpaltenBreite( 5, 100 );
+    tabelle->addSpalte( "auswahl" );
+    tabelle->setSpaltenBreite( 6, 20 );
+    tabelle->addZeile( "Überschrifft" );
+    tabelle->setZeilenHeight( 0, 20 );
+    tabelle->setZeichnungZ( 0, 0, getTabellenEintrag( "Id", s->getThis(), 0xFFFFFFFF ) );
+    tabelle->setZeichnungZ( 1, 0, getTabellenEintrag( "Name", s->getThis(), 0xFFFFFFFF ) );
+    tabelle->setZeichnungZ( 2, 0, getTabellenEintrag( "Ip", s->getThis(), 0xFFFFFFFF ) );
+    tabelle->setZeichnungZ( 3, 0, getTabellenEintrag( "Port", s->getThis(), 0xFFFFFFFF ) );
+    tabelle->setZeichnungZ( 4, 0, getTabellenEintrag( "APort", s->getThis(), 0xFFFFFFFF ) );
+    tabelle->setZeichnungZ( 5, 0, getTabellenEintrag( "Status", s->getThis(), 0xFFFFFFFF ) );
+    tabelle->setZeichnungZ( 6, 0, 0 );
+    liste->addMember( tabelle );
+
+    aktualisieren = new Knopf();
+    aktualisieren->setText( "" );
+    aktualisieren->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Erlaubt | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+    aktualisieren->setHintergrundBildZ( rb->get( "neuladen.png" ) );
+    aktualisieren->setPosition( 236, 230 );
+    aktualisieren->setSize( 20, 20 );
+    aktualisieren->setMausEreignisParameter( this );
+    aktualisieren->setMausEreignis( patchServerAktualisierenMausEreignis );
+    f->addMember( aktualisieren );
+
+    weiter = new Knopf();
+    weiter->setText( "" );
+    weiter->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+    weiter->setHintergrundBildZ( rb->get( "weiter.png" ) );
+    weiter->setPosition( 261, 230 );
+    weiter->setSize( 20, 20 );
+    weiter->setMausEreignisParameter( this );
+    weiter->setMausEreignis( patchServerWeiterMausEreignis );
+    f->addMember( weiter );
+
+    zurück = new Knopf();
+    zurück->setText( "" );
+    zurück->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+    zurück->setHintergrundBildZ( rb->get( "zurück.png" ) );
+    zurück->setPosition( 211, 230 );
+    zurück->setSize( 20, 20 );
+    zurück->setMausEreignisParameter( this );
+    zurück->setMausEreignis( patchServerZurückMausEreignis );
+    f->addMember( zurück );
+
+    serverId = new TextFeld();
+    serverId->setStyle( TextFeld::Style::Sichtbar );
+    serverId->setSchriftZ( s->getThis() );
+    serverId->setSchriftFarbe( 0xFFFFFFFF );
+    serverId->setSchriftSize( 12 );
+    serverId->setText( "ID: " );
+    serverId->setSize( 100, 20 );
+    serverId->setPosition( 10, 10 );
+    details->addMember( serverId );
+
+    serverName = new TextFeld();
+    serverName->setStyle( TextFeld::Style::Sichtbar );
+    serverName->setSchriftZ( s->getThis() );
+    serverName->setSchriftFarbe( 0xFFFFFFFF );
+    serverName->setSchriftSize( 12 );
+    serverName->setText( "Name: " );
+    serverName->setSize( 150, 20 );
+    serverName->setPosition( 120, 10 );
+    details->addMember( serverName );
+
+    serverIp = new TextFeld();
+    serverIp->setStyle( TextFeld::Style::Sichtbar );
+    serverIp->setSchriftZ( s->getThis() );
+    serverIp->setSchriftFarbe( 0xFFFFFFFF );
+    serverIp->setSchriftSize( 12 );
+    serverIp->setText( "IP: " );
+    serverIp->setSize( 120, 20 );
+    serverIp->setPosition( 280, 10 );
+    details->addMember( serverIp );
+
+    serverPort = new TextFeld();
+    serverPort->setStyle( TextFeld::Style::Sichtbar );
+    serverPort->setSchriftZ( s->getThis() );
+    serverPort->setSchriftFarbe( 0xFFFFFFFF );
+    serverPort->setSchriftSize( 12 );
+    serverPort->setText( "Port: " );
+    serverPort->setSize( 100, 20 );
+    serverPort->setPosition( 10, 40 );
+    details->addMember( serverPort );
+
+    serverAPort = new TextFeld();
+    serverAPort->setStyle( TextFeld::Style::Sichtbar );
+    serverAPort->setSchriftZ( s->getThis() );
+    serverAPort->setSchriftFarbe( 0xFFFFFFFF );
+    serverAPort->setSchriftSize( 12 );
+    serverAPort->setText( "Admin Port: " );
+    serverAPort->setSize( 200, 20 );
+    serverAPort->setPosition( 120, 40 );
+    details->addMember( serverAPort );
+
+    serverClients = new TextFeld();
+    serverClients->setStyle( TextFeld::Style::Sichtbar );
+    serverClients->setSchriftZ( s->getThis() );
+    serverClients->setSchriftFarbe( 0xFFFFFFFF );
+    serverClients->setSchriftSize( 12 );
+    serverClients->setText( "Clients: " );
+    serverClients->setSize( 100, 20 );
+    serverClients->setPosition( 10, 70 );
+    details->addMember( serverClients );
+
+    serverMaxClients = new TextFeld();
+    serverMaxClients->setStyle( TextFeld::Style::Sichtbar );
+    serverMaxClients->setSchriftZ( s->getThis() );
+    serverMaxClients->setSchriftFarbe( 0xFFFFFFFF );
+    serverMaxClients->setSchriftSize( 12 );
+    serverMaxClients->setText( "Max Clients: " );
+    serverMaxClients->setSize( 80, 20 );
+    serverMaxClients->setPosition( 120, 70 );
+    details->addMember( serverMaxClients );
+
+    maxClients = new TextFeld();
+    maxClients->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Erlaubt | TextFeld::Style::Rahmen | TextFeld::Style::Buffered | TextFeld::Style::VCenter );
+    maxClients->setSchriftZ( s->getThis() );
+    maxClients->setSchriftFarbe( 0xFFFFFFFF );
+    maxClients->setSchriftSize( 12 );
+    maxClients->setLinienRahmenBreite( 1 );
+    maxClients->setLinienRahmenFarbe( 0xFFFFFFFF );
+    maxClients->setAlphaFeldFarbe( 0x1000FF00 );
+    maxClients->setAlphaFeldStrength( -5 );
+    maxClients->setText( "" );
+    maxClients->setSize( 100, 20 );
+    maxClients->setPosition( 200, 68 );
+    maxClients->setMausEreignis( _ret1ME );
+    maxClients->setTastaturEreignisParameter( this );
+    maxClients->setTastaturEreignis( patchServerMaxClientsTastaturEreignis );
+    details->addMember( maxClients );
+
+    serverStatus = new TextFeld();
+    serverStatus->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Mehrfarbig );
+    serverStatus->setSchriftZ( s->getThis() );
+    serverStatus->setSchriftFarbe( 0xFFFFFFFF );
+    serverStatus->setSchriftSize( 12 );
+    serverStatus->setText( "Status: " );
+    serverStatus->setSize( 150, 20 );
+    serverStatus->setPosition( 10, 100 );
+    details->addMember( serverStatus );
+
+    serverFehler = new TextFeld();
+    serverFehler->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Mehrzeilig );
+    serverFehler->setSchriftZ( s->getThis() );
+    serverFehler->setSchriftFarbe( 0xFFFFFFFF );
+    serverFehler->setSchriftSize( 12 );
+    serverFehler->setText( "" );
+    serverFehler->setSize( 470, 60 );
+    serverFehler->setPosition( 10, 130 );
+    details->addMember( serverFehler );
+
+    update = new Knopf();
+    update->setStyle( Knopf::Style::Normal & ~Knopf::Style::Erlaubt );
+    update->setText( "Update" );
+    update->setSchriftZ( s->getThis() );
+    update->setMausEreignisParameter( this );
+    update->setMausEreignis( patchServerUpdateMausEreignis );
+    update->setSize( 80, 20 );
+    update->setPosition( 400, 100 );
+    details->addMember( update );
+
+    pausieren = new Knopf();
+    pausieren->setStyle( Knopf::Style::Normal & ~Knopf::Style::Erlaubt );
+    pausieren->setText( "Pausieren" );
+    pausieren->setSchriftZ( s->getThis() );
+    pausieren->setMausEreignisParameter( this );
+    pausieren->setMausEreignis( patchServerPausierenMausEreignis );
+    pausieren->setSize( 80, 20 );
+    pausieren->setPosition( 10, 200 );
+    details->addMember( pausieren );
+
+    stoppen = new Knopf();
+    stoppen->setStyle( Knopf::Style::Normal & ~Knopf::Style::Erlaubt );
+    stoppen->setText( "Stoppen" );
+    stoppen->setSchriftZ( s->getThis() );
+    stoppen->setMausEreignisParameter( this );
+    stoppen->setMausEreignis( patchServerStoppenMausEreignis );
+    stoppen->setSize( 80, 20 );
+    stoppen->setPosition( 100, 200 );
+    details->addMember( stoppen );
+
+    beenden = new Knopf();
+    beenden->setStyle( Knopf::Style::Normal & ~Knopf::Style::Erlaubt );
+    beenden->setText( "Beenden" );
+    beenden->setSchriftZ( s->getThis() );
+    beenden->setMausEreignisParameter( this );
+    beenden->setMausEreignis( patchServerBeendenMausEreignis );
+    beenden->setSize( 80, 20 );
+    beenden->setPosition( 190, 200 );
+    details->addMember( beenden );
+
+    terminieren = new Knopf();
+    terminieren->setStyle( Knopf::Style::Normal & ~Knopf::Style::Erlaubt );
+    terminieren->setText( "Terminieren" );
+    terminieren->setSchriftZ( s->getThis() );
+    terminieren->setMausEreignisParameter( this );
+    terminieren->setMausEreignis( patchServerTerminierenMausEreignis );
+    terminieren->setSize( 80, 20 );
+    terminieren->setPosition( 280, 200 );
+    details->addMember( terminieren );
+
+    setMaxClients = new Knopf();
+    setMaxClients->setStyle( Knopf::Style::Normal & ~Knopf::Style::Erlaubt );
+    setMaxClients->setText( "set Max Clients" );
+    setMaxClients->setSchriftZ( s->getThis() );
+    setMaxClients->setMausEreignisParameter( this );
+    setMaxClients->setMausEreignis( patchServerSetMaxClientsMausEreignis );
+    setMaxClients->setSize( 110, 20 );
+    setMaxClients->setPosition( 370, 200 );
+    details->addMember( setMaxClients );
+
+    updateT = new ObjTabelle();
+    updateT->setStyle( ObjTabelle::Style::Sichtbar | ObjTabelle::Style::Erlaubt | ObjTabelle::Style::Rahmen | ObjTabelle::Style::VScroll );
+    updateT->setVertikalKlickScroll( 10 );
+    updateT->setMausEreignis( _ret1ME );
+    updateT->setLinienRahmenFarbe( 0xFFFFFFFF );
+    updateT->setPosition( 5, 5 );
+    updateT->setSize( 480, 190 );
+    updateT->addSpalte( "Name" );
+    updateT->addSpalte( "Status" );
+    updateT->addSpalte( "Auswahl" );
+    updateT->addSpalte( "Update" );
+    updateT->setSpaltenBreite( 0, 340 );
+    updateT->setSpaltenBreite( 1, 100 );
+    updateT->setSpaltenBreite( 2, 22 );
+    updateT->setSpaltenBreite( 3, 0 );
+    updateT->addZeile( "Titel" );
+    updateT->setZeilenHeight( 0, 20 );
+    TextFeld *uTN = new TextFeld();
+    uTN->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+    uTN->setSchriftZ( s->getThis() );
+    uTN->setSchriftFarbe( 0xFFFFFFFF );
+    uTN->setSchriftSize( 12 );
+    uTN->setLinienRahmenFarbe( 0xFFFFFFFF );
+    uTN->setText( "Name" );
+    updateT->setZeichnungZ( 0, 0, uTN );
+    TextFeld *uTS = new TextFeld();
+    uTS->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+    uTS->setSchriftZ( s->getThis() );
+    uTS->setSchriftFarbe( 0xFFFFFFFF );
+    uTS->setSchriftSize( 12 );
+    uTS->setLinienRahmenFarbe( 0xFFFFFFFF );
+    uTS->setText( "Status" );
+    updateT->setZeichnungZ( 1, 0, uTS );
+    updateT->setMausEreignis( _ret1ME );
+    updateT->setTastaturEreignis( _ret1TE );
+    updateF->addMember( updateT );
+
+    updateStarten = new Knopf();
+    updateStarten->setStyle( Knopf::Style::Normal );
+    updateStarten->setText( "Start" );
+    updateStarten->setSchriftZ( s->getThis() );
+    updateStarten->setMausEreignisParameter( this );
+    updateStarten->setMausEreignis( patchServerUpdateStartenMausEreignis );
+    updateStarten->setSize( 80, 20 );
+    updateStarten->setPosition( 205, 200 );
+    updateF->addMember( updateStarten );
+
+    obj = new Zeichnung();
+
+    suchen = new PSSuche( this, msk->getThis() );
+    getDetails = new PSDetails( this, msk->getThis() );
+    updateTh = new PSUpdate( this, account->getThis() );
+    rb->release();
+    ref = 1;
+}
+
+// Destruktor
+PatchServer::~PatchServer()
+{
+    for( int i = 0; i < updateT->getZeilenAnzahl(); i++ )
+    {
+        ( (TextFeld*)updateT->zZeichnung( 0, i ) )->release();
+        if( updateT->zZeichnung( 3, i ) == obj )
+            ( (FBalken*)updateT->zZeichnung( 1, i ) )->release();
+        else
+            ( (TextFeld*)updateT->zZeichnung( 1, i ) )->release();
+        if( updateT->zZeichnung( 2, i ) )
+            ( (KontrollKnopf*)updateT->zZeichnung( 2, i ) )->release();
+    }
+    delete obj;
+    if( psc )
+    {
+        psc->trenne();
+        psc->release();
+    }
+    if( fenster )
+    {
+        fenster->removeMember( f );
+        fenster->release();
+    }
+    account->release();
+    msk->release();
+    iD->release();
+    f->release();
+    liste->release();
+    details->release();
+    updateF->release();
+    updateStarten->release();
+    updateT->release();
+    aktualisieren->release();
+    weiter->release();
+    zurück->release();
+    update->release();
+    pausieren->release();
+    stoppen->release();
+    beenden->release();
+    terminieren->release();
+    setMaxClients->release();
+    serverId->release();
+    serverName->release();
+    serverIp->release();
+    serverPort->release();
+    serverAPort->release();
+    serverClients->release();
+    serverMaxClients->release();
+    serverStatus->release();
+    serverFehler->release();
+    maxClients->release();
+    suchen->release();
+    getDetails->release();
+    updateTh->release();
+    for( int x = 0; x < tabelle->getSpaltenAnzahl(); x++ )
+    {
+        for( int y = 0; y < tabelle->getZeilenAnzahl(); y++ )
+        {
+            Zeichnung *obj = tabelle->zZeichnung( x, y );
+            if( obj )
+            {
+                if( x == tabelle->getSpaltenNummer( "auswahl" ) )
+                    ( (KontrollKnopf*)obj )->release();
+                else
+                    ( (TextFeld*)obj )->release();
+            }
+            tabelle->setZeichnungZ( x, y, 0 );
+        }
+    }
+    tabelle->release();
+    schrift->release();
+}
+
+// nicht constant
+void PatchServer::setFenster( Fenster *f )
+{
+    if( fenster )
+        fenster->release();
+    this->f->setPosition( f->getBreite() / 2 - this->f->getBreite() / 2, f->getHeight() / 2 - this->f->getHeight() / 2 );
+    fenster = f;
+}
+
+void PatchServer::setSichtbar( bool s )
+{
+    sichtbar = s;
+    if( s )
+    {
+        if( !suchen->isRunning() && liste->hatStyle( Fenster::Style::Sichtbar ) )
+        {
+            for( int x = 0; x < tabelle->getSpaltenAnzahl(); x++ )
+            {
+                for( int y = 1; y < tabelle->getZeilenAnzahl(); y++ )
+                {
+                    Zeichnung *obj = tabelle->zZeichnung( x, y );
+                    if( obj )
+                    {
+                        if( x == tabelle->getSpaltenNummer( "auswahl" ) )
+                            ( (KontrollKnopf*)obj )->release();
+                        else
+                            ( (TextFeld*)obj )->release();
+                    }
+                    tabelle->setZeichnungZ( x, y, 0 );
+                }
+            }
+            for( int y = 1; y < tabelle->getZeilenAnzahl(); y++ )
+                tabelle->removeZeile( 1 );
+            weiter->removeStyle( Knopf::Style::Erlaubt );
+            aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+            tabelle->removeStyle( ObjTabelle::Style::Erlaubt );
+            suchen->start();
+        }
+        fenster->addMember( f );
+    }
+    else
+        fenster->removeMember( f );
+}
+
+void PatchServer::addServer( int id, char *name, char *ip, int port, int adminPort, char *status )
+{
+    Text *txt = new Text();
+    txt->append( id );
+    tabelle->addZeile( txt->getText() );
+    int y = tabelle->getZeilenNummer( txt->getText() );
+    tabelle->setZeilenHeight( y, 20 );
+    tabelle->setZeichnungZ( 0, y, getTabellenEintrag( txt->getText(), schrift->getThis(), 0xFFFFFFFF ) );
+    tabelle->setZeichnungZ( 1, y, getTabellenEintrag( name, schrift->getThis(), 0xFFFFFFFF ) );
+    tabelle->setZeichnungZ( 2, y, getTabellenEintrag( ip, schrift->getThis(), 0xFFFFFFFF ) );
+    txt->setText( "" );
+    txt->append( port );
+    tabelle->setZeichnungZ( 3, y, getTabellenEintrag( txt->getText(), schrift->getThis(), 0xFFFFFFFF ) );
+    txt->setText( "" );
+    txt->append( adminPort );
+    tabelle->setZeichnungZ( 4, y, getTabellenEintrag( txt->getText(), schrift->getThis(), 0xFFFFFFFF ) );
+    txt->release();
+    tabelle->setZeichnungZ( 5, y, getTabellenEintrag( status, schrift->getThis(), 0xFFFF8800 ) );
+    tabelle->setZeichnungZ( 5, y, getTabellenEintrag( status, schrift->getThis(), getColorFromStatus( status ) ) );
+    KontrollKnopf *knopf = new KontrollKnopf();
+    knopf->setStyle( KontrollKnopf::Style::Sichtbar | KontrollKnopf::Style::Erlaubt | KontrollKnopf::Style::KlickBuffer );
+    knopf->loadData( "data/bilder/icons.ltdb" );
+    knopf->setMausEreignisParameter( this );
+    knopf->setMausEreignis( patchServerAuswahlKnopfMausEreignis );
+    tabelle->setZeichnungZ( 6, y, knopf );
+}
+
+void PatchServer::setServerDetails( int id, char *name, char *ip, int port, int adminPort, int clients, int maxClients, int status, Text *error )
+{
+    if( !psc )
+    {
+        psc = new PSKlient( ip, adminPort );
+        psc->verbinden();
+        psc->login( account->zName()->getText(), account->zPasswort()->getText() );
+        updateTh->setServer( ip, port );
+    }
+    if( !error )
+    {
+        serverId->setText( "ID: " );
+        serverId->zText()->append( id );
+        serverName->setText( "Name: " );
+        serverName->zText()->append( name );
+        serverIp->setText( "IP: " );
+        serverIp->zText()->append( ip );
+        serverPort->setText( "Port: " );
+        serverPort->zText()->append( port );
+        serverAPort->setText( "Admin Port: " );
+        serverAPort->zText()->append( adminPort );
+        serverClients->setText( "Clients: " );
+        serverClients->zText()->append( clients );
+        this->maxClients->setText( "" );
+        this->maxClients->zText()->append( maxClients );
+        serverFehler->setText( "" );
+        switch( status )
+        {
+        case -2: // Unbekannt
+            serverStatus->setText( "\r0xFFFFFFFFStatus: \r0xFFFF8800Unbekannt" );
+            break;
+        case -1: // Unerreichbar
+            serverStatus->setText( "\r0xFFFFFFFFStatus: \r0xFFFF0000Unerreichbar" );
+            break;
+        case 0: // Offline
+            serverStatus->setText( "\r0xFFFFFFFFStatus: \r0xFFFFFF00Offline" );
+            stoppen->setText( "Starten" );
+            stoppen->addStyle( Knopf::Style::Erlaubt );
+            beenden->addStyle( Knopf::Style::Erlaubt );
+            terminieren->addStyle( Knopf::Style::Erlaubt );
+            this->maxClients->addStyle( TextFeld::Style::Erlaubt );
+            break;
+        case 1: // Pausiert
+            serverStatus->setText( "\r0xFFFFFFFFStatus: \r0xFF88FF00Pausiert" );
+            pausieren->setText( "Fortsetzen" );
+            pausieren->addStyle( Knopf::Style::Erlaubt );
+            stoppen->setText( "Stoppen" );
+            stoppen->addStyle( Knopf::Style::Erlaubt );
+            beenden->addStyle( Knopf::Style::Erlaubt );
+            terminieren->addStyle( Knopf::Style::Erlaubt );
+            this->maxClients->addStyle( TextFeld::Style::Erlaubt );
+            break;
+        case 2: // Online
+            serverStatus->setText( "\r0xFFFFFFFFStatus: \r0xFF00FF00Online" );
+            pausieren->setText( "Pausieren" );
+            pausieren->addStyle( Knopf::Style::Erlaubt );
+            terminieren->addStyle( Knopf::Style::Erlaubt );
+            this->maxClients->addStyle( TextFeld::Style::Erlaubt );
+            break;
+        case 3: // Veraltet
+            serverStatus->setText( "\r0xFFFFFFFFStatus: \r0xFFB0FF00Veraltet" );
+            pausieren->setText( "Pausieren" );
+            pausieren->addStyle( Knopf::Style::Erlaubt );
+            update->addStyle( Knopf::Style::Erlaubt );
+            beenden->addStyle( Knopf::Style::Erlaubt );
+            terminieren->addStyle( Knopf::Style::Erlaubt );
+            this->maxClients->addStyle( TextFeld::Style::Erlaubt );
+            break;
+        }
+        aktualisieren->addStyle( Knopf::Style::Erlaubt );
+        zurück->addStyle( Knopf::Style::Erlaubt );
+        update->addStyle( Knopf::Style::Erlaubt );
+    }
+    else
+    {
+        serverId->setText( "ID: " );
+        serverName->setText( "Name: " );
+        serverIp->setText( "IP: " );
+        serverPort->setText( "Port: " );
+        serverAPort->setText( "APort: " );
+        serverClients->setText( "Clients: " );
+        this->maxClients->setText( "" );
+        this->serverStatus->setText( "Status: " );
+        aktualisieren->addStyle( Knopf::Style::Erlaubt );
+        zurück->addStyle( Knopf::Style::Erlaubt );
+        serverFehler->setText( error );
+    }
+}
+
+void PatchServer::sucheAbgeschlossen()
+{
+    aktualisieren->addStyle( Knopf::Style::Erlaubt );
+    tabelle->addStyle( ObjTabelle::Style::Erlaubt );
+}
+
+void PatchServer::setUpdateProzent( int prozent, int gruppe )
+{
+    for( int i = 0; i < updateT->getZeilenAnzahl(); i++ )
+    {
+        if( gruppe == TextZuInt( updateT->zZeilenName( i )->getText(), 10 ) )
+        {
+            if( updateT->zZeichnung( 3, i ) != obj )
+            {
+                updateT->lockZeichnung();
+                ( (TextFeld*)updateT->zZeichnung( 1, i ) )->release();
+                FBalken *fb = new FBalken();
+                fb->setStyle( FBalken::Style::Sichtbar | FBalken::Style::L_R | FBalken::Style::FFarbe | FBalken::Style::Hintergrund | FBalken::Style::Prozent | FBalken::Style::Rahmen | FBalken::Style::FRahmen );
+                fb->setFBgFarbe( 0xFF00FF00 );
+                fb->setHintergrundFarbe( 0xFFFFFFFF );
+                fb->setSFarbe( 0xFF000000 );
+                fb->setSchriftZ( schrift->getThis() );
+                fb->setSSize( 12 );
+                fb->setLinienRahmenBreite( 1 );
+                fb->setLinienRahmenFarbe( 0xFF55FF55 );
+                fb->setFRFarbe( 0xFF55FF55 );
+                fb->reset();
+                fb->setAktionAnzahl( 100 );
+                updateT->setZeichnungZ( 1, i, fb );
+                updateT->setZeichnungZ( 3, i, obj );
+                updateT->unlockZeichnung();
+            }
+            ( (FBalken*)updateT->zZeichnung( 1, i ) )->reset();
+            ( (FBalken*)updateT->zZeichnung( 1, i ) )->aktionPlus( prozent );
+            return;
+        }
+    }
+}
+
+void PatchServer::setUpdateFertig( bool error, int gruppe )
+{
+    if( !gruppe )
+    { // gesamter Vorgang abgeschlossen
+        aktualisieren->addStyle( Knopf::Style::Erlaubt );
+        zurück->addStyle( Knopf::Style::Erlaubt );
+        updateStarten->addStyle( Knopf::Style::Erlaubt );
+        updateT->addStyle( ObjTabelle::Style::Erlaubt );
+        MausEreignis me;
+        me.id = ME_RLinks;
+        b->lock();
+        aktualisierenMausEreignis( 0, me );
+        b->unlock();
+    }
+    else
+    { // einzelner Schritt abgeschlossen
+        for( int i = 0; i < updateT->getZeilenAnzahl(); i++ )
+        {
+            if( gruppe == TextZuInt( updateT->zZeilenName( i )->getText(), 10 ) )
+            {
+                updateT->lockZeichnung();
+                ( (FBalken*)updateT->zZeichnung( 1, i ) )->release();
+                TextFeld *uTS = new TextFeld();
+                uTS->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+                uTS->setSchriftZ( schrift->getThis() );
+                uTS->setSchriftSize( 12 );
+                uTS->setLinienRahmenFarbe( 0xFFFFFFFF );
+                if( error )
+                {
+                    uTS->setText( "Fehler" );
+                    uTS->setSchriftFarbe( 0xFFFF0000 );
+                }
+                else
+                {
+                    uTS->setText( "Aktuell" );
+                    uTS->setSchriftFarbe( 0xFF00FF00 );
+                }
+                updateT->setZeichnungZ( 1, i, uTS );
+                updateT->setZeichnungZ( 3, i, 0 );
+                updateT->unlockZeichnung();
+                return;
+            }
+        }
+    }
+}
+
+bool PatchServer::aktualisierenMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        if( liste->hatStyle( Fenster::Style::Sichtbar ) )
+        {
+            if( !suchen->isRunning() )
+            {
+                for( int x = 0; x < tabelle->getSpaltenAnzahl(); x++ )
+                {
+                    for( int y = 1; y < tabelle->getZeilenAnzahl(); y++ )
+                    {
+                        Zeichnung *obj = tabelle->zZeichnung( x, y );
+                        if( obj )
+                        {
+                            if( x == tabelle->getSpaltenNummer( "auswahl" ) )
+                                ( (KontrollKnopf*)obj )->release();
+                            else
+                                ( (TextFeld*)obj )->release();
+                        }
+                        tabelle->setZeichnungZ( x, y, 0 );
+                    }
+                }
+                for( int y = 1; y < tabelle->getZeilenAnzahl(); y++ )
+                    tabelle->removeZeile( 1 );
+                weiter->removeStyle( Knopf::Style::Erlaubt );
+                aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                tabelle->removeStyle( ObjTabelle::Style::Erlaubt );
+                suchen->start();
+            }
+        }
+        else if( details->hatStyle( Fenster::Style::Sichtbar ) )
+        {
+            aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+            zurück->removeStyle( Knopf::Style::Erlaubt );
+            update->removeStyle( Knopf::Style::Erlaubt );
+            pausieren->removeStyle( Knopf::Style::Erlaubt );
+            stoppen->removeStyle( Knopf::Style::Erlaubt );
+            beenden->removeStyle( Knopf::Style::Erlaubt );
+            terminieren->removeStyle( Knopf::Style::Erlaubt );
+            setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+            maxClients->removeStyle( TextFeld::Style::Erlaubt );
+            getDetails->start();
+        }
+        else if( updateF->hatStyle( Fenster::Style::Sichtbar ) )
+        {
+            int id = -1;
+            for( int i = 1; i < tabelle->getZeilenAnzahl(); i++ )
+            {
+                if( ( (KontrollKnopf*)tabelle->zZeichnung( 6, i ) )->hatStyle( KontrollKnopf::Style::Selected ) )
+                {
+                    id = TextZuInt( tabelle->zZeilenName( i )->getText(), 10 );
+                    break;
+                }
+            }
+            Array< FileGroupInfo* > list;
+            if( psc->getFileGroupInfoList( &list ) )
+            {
+                for( int i = 1; i < updateT->getZeilenAnzahl(); )
+                {
+                    ( (TextFeld*)updateT->zZeichnung( 0, i ) )->release();
+                    if( updateT->zZeichnung( 3, i ) == obj )
+                        ( (FBalken*)updateT->zZeichnung( 1, i ) )->release();
+                    else
+                        ( (TextFeld*)updateT->zZeichnung( 1, i ) )->release();
+                    if( updateT->zZeichnung( 2, i ) )
+                        ( (KontrollKnopf*)updateT->zZeichnung( 2, i ) )->release();
+                    updateT->removeZeile( i );
+                }
+                int anz = list.getEintragAnzahl();
+                for( int i = 0; i < anz; i++ )
+                {
+                    FileGroupInfo *info = list.get( i );
+                    updateT->addZeile( new Text( info->id ) );
+                    TextFeld *uTN = new TextFeld();
+                    uTN->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::VCenter );
+                    uTN->setSchriftZ( schrift->getThis() );
+                    uTN->setSchriftFarbe( 0xFFFFFFFF );
+                    uTN->setSchriftSize( 12 );
+                    uTN->setLinienRahmenFarbe( 0xFFFFFFFF );
+                    uTN->setText( info->name );
+                    updateT->setZeichnungZ( 0, i + 1, uTN );
+                    TextFeld *uTS = new TextFeld();
+                    uTS->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+                    uTS->setLinienRahmenFarbe( 0xFFFFFFFF );
+                    uTS->setSchriftZ( schrift->getThis() );
+                    uTS->setSchriftSize( 12 );
+                    if( info->status.istGleich( "Fehlt" ) )
+                        uTS->setSchriftFarbe( 0xFFFF0000 );
+                    if( info->status.istGleich( "Aktuell" ) )
+                        uTS->setSchriftFarbe( 0xFF00FF00 );
+                    if( info->status.istGleich( "Veraltet" ) )
+                        uTS->setSchriftFarbe( 0xFFFFFF00 );
+                    if( info->status.istGleich( "Update" ) )
+                        uTS->setSchriftFarbe( 0xFFFFFFFF );
+                    uTS->setText( info->status.getText() );
+                    updateT->setZeichnungZ( 1, i + 1, uTS );
+                    if( info->status.istGleich( "Veraltet" ) || info->status.istGleich( "Fehlt" ) )
+                    {
+                        KontrollKnopf *auswahl = new KontrollKnopf();
+                        auswahl->setStyle( KontrollKnopf::Style::Sichtbar | KontrollKnopf::Style::Erlaubt | KontrollKnopf::Style::KlickBuffer | KontrollKnopf::Style::Rahmen );
+                        auswahl->loadData( "data/bilder/icons.ltdb" );
+                        auswahl->setMausEreignisParameter( this );
+                        auswahl->setMausEreignis( patchServerAuswahlKnopfMausEreignis );
+                        auswahl->setLinienRahmenFarbe( 0xFFFFFFFF );
+                        updateT->setZeichnungZ( 2, i + 1, auswahl );
+                    }
+                    delete info;
+                }
+            }
+            else
+                WMessageBox( 0, new Text( "Fehler" ), new Text( psc->getLetzterFehler() ), MB_ICONERROR );
+        }
+    }
+    return 1;
+}
+
+bool PatchServer::auswahlKnopfMausEreignis( void *o, MausEreignis me )
+{
+    if( !o )
+        return 0;
+    if( me.id == ME_RLinks )
+    {
+        if( liste->hatStyle( Fenster::Style::Sichtbar ) )
+        {
+            for( int i = 1; i < tabelle->getZeilenAnzahl(); i++ )
+                ( (KontrollKnopf*)tabelle->zZeichnung( 6, i ) )->removeStyle( KontrollKnopf::Style::Selected );
+            weiter->addStyle( Knopf::Style::Erlaubt );
+        }
+    }
+    return 1;
+}
+
+bool PatchServer::weiterMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        liste->removeStyle( Fenster::Style::Sichtbar );
+        details->addStyle( Fenster::Style::Sichtbar );
+        aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+        zurück->removeStyle( Knopf::Style::Erlaubt );
+        update->removeStyle( Knopf::Style::Erlaubt );
+        pausieren->removeStyle( Knopf::Style::Erlaubt );
+        stoppen->removeStyle( Knopf::Style::Erlaubt );
+        beenden->removeStyle( Knopf::Style::Erlaubt );
+        terminieren->removeStyle( Knopf::Style::Erlaubt );
+        setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+        maxClients->removeStyle( TextFeld::Style::Erlaubt );
+        int id = -1;
+        for( int i = 1; i < tabelle->getZeilenAnzahl(); i++ )
+        {
+            if( ( (KontrollKnopf*)tabelle->zZeichnung( 6, i ) )->hatStyle( KontrollKnopf::Style::Selected ) )
+            {
+                id = TextZuInt( tabelle->zZeilenName( i )->getText(), 10 );
+                break;
+            }
+        }
+        getDetails->setServerId( id );
+        getDetails->start();
+    }
+    return 1;
+}
+
+bool PatchServer::zurückMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        if( details->hatStyle( Fenster::Style::Sichtbar ) )
+        {
+            details->removeStyle( Fenster::Style::Sichtbar );
+            liste->addStyle( Fenster::Style::Sichtbar );
+            if( !suchen->isRunning() )
+            {
+                for( int x = 0; x < tabelle->getSpaltenAnzahl(); x++ )
+                {
+                    for( int y = 1; y < tabelle->getZeilenAnzahl(); y++ )
+                    {
+                        Zeichnung *obj = tabelle->zZeichnung( x, y );
+                        if( obj )
+                        {
+                            if( x == tabelle->getSpaltenNummer( "auswahl" ) )
+                                ( (KontrollKnopf*)obj )->release();
+                            else
+                                ( (TextFeld*)obj )->release();
+                        }
+                        tabelle->setZeichnungZ( x, y, 0 );
+                    }
+                }
+                for( int y = 1; y < tabelle->getZeilenAnzahl(); y++ )
+                    tabelle->removeZeile( 1 );
+                weiter->removeStyle( Knopf::Style::Erlaubt );
+                zurück->removeStyle( Knopf::Style::Erlaubt );
+                aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                suchen->start();
+            }
+            if( psc )
+            {
+                psc->trenne();
+                psc = (PSKlient*)psc->release();
+            }
+        }
+        else if( updateF->hatStyle( Fenster::Style::Sichtbar ) )
+        {
+            updateF->removeStyle( Fenster::Style::Sichtbar );
+            details->addStyle( Fenster::Style::Sichtbar );
+            aktualisierenMausEreignis( 0, me );
+        }
+    }
+    return 1;
+}
+
+bool PatchServer::updateMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        zurück->addStyle( Knopf::Style::Erlaubt );
+        weiter->removeStyle( Knopf::Style::Erlaubt );
+        details->removeStyle( Fenster::Style::Sichtbar );
+        updateF->addStyle( Fenster::Style::Sichtbar );
+        aktualisieren->addStyle( Knopf::Style::Erlaubt );
+        aktualisierenMausEreignis( 0, me );
+    }
+    return 1;
+}
+
+bool PatchServer::pausierenMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        if( pausieren->zText()->istGleich( "Pausieren" ) )
+        {
+            if( psc->pause() )
+            {
+                aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                zurück->removeStyle( Knopf::Style::Erlaubt );
+                update->removeStyle( Knopf::Style::Erlaubt );
+                pausieren->removeStyle( Knopf::Style::Erlaubt );
+                stoppen->removeStyle( Knopf::Style::Erlaubt );
+                beenden->removeStyle( Knopf::Style::Erlaubt );
+                terminieren->removeStyle( Knopf::Style::Erlaubt );
+                setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+                maxClients->removeStyle( TextFeld::Style::Erlaubt );
+                getDetails->start();
+            }
+            else
+                serverFehler->setText( psc->getLetzterFehler() );
+        }
+        else
+        {
+            if( psc->fortsetzen() )
+            {
+                aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                zurück->removeStyle( Knopf::Style::Erlaubt );
+                update->removeStyle( Knopf::Style::Erlaubt );
+                pausieren->removeStyle( Knopf::Style::Erlaubt );
+                stoppen->removeStyle( Knopf::Style::Erlaubt );
+                beenden->removeStyle( Knopf::Style::Erlaubt );
+                terminieren->removeStyle( Knopf::Style::Erlaubt );
+                setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+                maxClients->removeStyle( TextFeld::Style::Erlaubt );
+                getDetails->start();
+            }
+            else
+                serverFehler->setText( psc->getLetzterFehler() );
+        }
+    }
+    return 1;
+}
+
+bool PatchServer::stoppenMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        if( stoppen->zText()->istGleich( "Stoppen" ) )
+        {
+            if( psc->stop() )
+            {
+                aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                zurück->removeStyle( Knopf::Style::Erlaubt );
+                update->removeStyle( Knopf::Style::Erlaubt );
+                pausieren->removeStyle( Knopf::Style::Erlaubt );
+                stoppen->removeStyle( Knopf::Style::Erlaubt );
+                beenden->removeStyle( Knopf::Style::Erlaubt );
+                terminieren->removeStyle( Knopf::Style::Erlaubt );
+                setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+                maxClients->removeStyle( TextFeld::Style::Erlaubt );
+                getDetails->start();
+            }
+            else
+                serverFehler->setText( psc->getLetzterFehler() );
+        }
+        else
+        {
+            if( psc->start() )
+            {
+                aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                zurück->removeStyle( Knopf::Style::Erlaubt );
+                update->removeStyle( Knopf::Style::Erlaubt );
+                pausieren->removeStyle( Knopf::Style::Erlaubt );
+                stoppen->removeStyle( Knopf::Style::Erlaubt );
+                beenden->removeStyle( Knopf::Style::Erlaubt );
+                terminieren->removeStyle( Knopf::Style::Erlaubt );
+                setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+                maxClients->removeStyle( TextFeld::Style::Erlaubt );
+                getDetails->start();
+            }
+            else
+                serverFehler->setText( psc->getLetzterFehler() );
+        }
+    }
+    return 1;
+}
+
+bool PatchServer::beendenMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        if( psc->beenden() )
+        {
+            aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+            zurück->removeStyle( Knopf::Style::Erlaubt );
+            update->removeStyle( Knopf::Style::Erlaubt );
+            pausieren->removeStyle( Knopf::Style::Erlaubt );
+            stoppen->removeStyle( Knopf::Style::Erlaubt );
+            beenden->removeStyle( Knopf::Style::Erlaubt );
+            terminieren->removeStyle( Knopf::Style::Erlaubt );
+            setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+            maxClients->removeStyle( TextFeld::Style::Erlaubt );
+            zurückMausEreignis( 0, me );
+        }
+        else
+            serverFehler->setText( psc->getLetzterFehler() );
+    }
+    return 1;
+}
+
+bool PatchServer::terminierenMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        if( psc->terminieren() )
+        {
+            aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+            zurück->removeStyle( Knopf::Style::Erlaubt );
+            update->removeStyle( Knopf::Style::Erlaubt );
+            pausieren->removeStyle( Knopf::Style::Erlaubt );
+            stoppen->removeStyle( Knopf::Style::Erlaubt );
+            beenden->removeStyle( Knopf::Style::Erlaubt );
+            terminieren->removeStyle( Knopf::Style::Erlaubt );
+            setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+            maxClients->removeStyle( TextFeld::Style::Erlaubt );
+            zurückMausEreignis( 0, me );
+        }
+        else
+            serverFehler->setText( psc->getLetzterFehler() );
+    }
+    return 1;
+}
+
+bool PatchServer::setMaxClientsMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        if( psc->setMaxTasks( TextZuInt( maxClients->zText()->getText(), 10 ) ) )
+        {
+            aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+            zurück->removeStyle( Knopf::Style::Erlaubt );
+            update->removeStyle( Knopf::Style::Erlaubt );
+            pausieren->removeStyle( Knopf::Style::Erlaubt );
+            stoppen->removeStyle( Knopf::Style::Erlaubt );
+            beenden->removeStyle( Knopf::Style::Erlaubt );
+            terminieren->removeStyle( Knopf::Style::Erlaubt );
+            setMaxClients->removeStyle( Knopf::Style::Erlaubt );
+            maxClients->removeStyle( TextFeld::Style::Erlaubt );
+            getDetails->start();
+        }
+        else
+            serverFehler->setText( psc->getLetzterFehler() );
+    }
+    return 1;
+}
+
+bool PatchServer::updateStartenMausEreignis( void *o, MausEreignis me )
+{
+    if( me.id == ME_RLinks )
+    {
+        int id = -1;
+        for( int i = 1; i < tabelle->getZeilenAnzahl(); i++ )
+        {
+            if( ( (KontrollKnopf*)tabelle->zZeichnung( 6, i ) )->hatStyle( KontrollKnopf::Style::Selected ) )
+            {
+                id = TextZuInt( tabelle->zZeilenName( i )->getText(), 10 );
+                break;
+            }
+        }
+        if( id > 0 )
+        {
+            int anzahl = 0;
+            Array< int > *gruppen = new Array< int >();
+            for( int i = 1; i < updateT->getZeilenAnzahl(); i++ )
+            {
+                if( updateT->zZeichnung( 2, i ) && ( (KontrollKnopf*)updateT->zZeichnung( 2, i ) )->hatStyle( KontrollKnopf::Style::Selected ) )
+                {
+                    int gId = TextZuInt( updateT->zZeilenName( i )->getText(), 10 );
+                    gruppen->set( gId, anzahl );
+                    anzahl++;
+                }
+            }
+            if( anzahl )
+            {
+                updateStarten->removeStyle( Knopf::Style::Erlaubt );
+                zurück->removeStyle( Knopf::Style::Erlaubt );
+                aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                updateT->removeStyle( ObjTabelle::Style::Erlaubt );
+                updateTh->setUpdateListe( anzahl, gruppen );
+                updateTh->start();
+            }
+            gruppen->release();
+        }
+    }
+    return 1;
+}
+
+bool PatchServer::maxClientsTastaturEreignis( void *o, TastaturEreignis te )
+{
+    bool ret = 0;
+    if( te.taste >= '0' && te.taste <= '9' )
+        ret = 1;
+    if( te.taste == T_Entf || te.taste == T_BackSpace )
+        ret = 1;
+    if( te.taste == T_Links || te.taste == T_Rechts )
+        ret = 1;
+    if( ret )
+        setMaxClients->addStyle( Knopf::Style::Erlaubt );
+    return ret;
+}
+
+// constant
+
+// Reference Counting
+Abschnitt *PatchServer::getThis()
+{
+    ref++;
+    return this;
+}
+
+Abschnitt *PatchServer::release()
+{
+    ref--;
+    if( !ref )
+        delete this;
+    return 0;
+}
+
+
+// Ereignisse
+bool patchServerAktualisierenMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->aktualisierenMausEreignis( o, me );
+}
+
+bool patchServerAuswahlKnopfMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->auswahlKnopfMausEreignis( o, me );
+}
+
+bool patchServerWeiterMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->weiterMausEreignis( o, me );
+}
+
+bool patchServerZurückMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->zurückMausEreignis( o, me );
+}
+
+bool patchServerUpdateMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->updateMausEreignis( o, me );
+}
+
+bool patchServerPausierenMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->pausierenMausEreignis( o, me );
+}
+
+bool patchServerStoppenMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->stoppenMausEreignis( o, me );
+}
+
+bool patchServerBeendenMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->beendenMausEreignis( o, me );
+}
+
+bool patchServerTerminierenMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->terminierenMausEreignis( o, me );
+}
+
+bool patchServerSetMaxClientsMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->setMaxClientsMausEreignis( o, me );
+}
+
+bool patchServerUpdateStartenMausEreignis( void *p, void *o, MausEreignis me )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->updateStartenMausEreignis( o, me );
+}
+
+bool patchServerMaxClientsTastaturEreignis( void *p, void *o, TastaturEreignis te )
+{
+    if( !p )
+        return 0;
+    return ( (PatchServer*)p )->maxClientsTastaturEreignis( o, te );
+}

+ 175 - 0
SMP/Programm/Server/Patch/PatchServer.h

@@ -0,0 +1,175 @@
+#ifndef PatchServer_H
+#define PatchServer_H
+
+#include "..\..\Basic\Abschnitt.h"
+#include "..\..\..\Netzwerk\Main\MSKlient.h"
+#include "..\..\..\Netzwerk\Patch\PSKlient.h"
+#include "..\..\..\Ressourcen\Ressourcen.h"
+#include <InitDatei.h>
+#include <Knopf.h>
+#include <Tabelle.h>
+#include <Thread.h>
+#include <Fortschritt.h>
+
+class AdminAccount; // Login.h
+class PatchServer; // PatchServer.h
+
+class PSUpdate : public Thread
+{
+private:
+	PatchServer *zPSA;
+	AdminAccount *account;
+	PSKlient *psc;
+	int gruppeAnzahl;
+	int *gruppeId;
+	int id;
+	int ref;
+
+public:
+	// Kontruktor
+	PSUpdate( PatchServer *zPSA, AdminAccount *account );
+	// Destruktor
+	~PSUpdate();
+	// nicht constant
+	void setServer( const char *ip, unsigned short port );
+	void setUpdateListe( int gAnzahl, Array< int > *gId );
+	virtual void thread();
+	// constant
+
+	// Reference Counting
+	PSUpdate *getThis();
+	PSUpdate *release();
+};
+
+class PSDetails : public Thread
+{
+private:
+	PatchServer *zPSA;
+    MSKlient *mk;
+	int id;
+	int ref;
+
+public:
+	// Konstruktor
+	PSDetails( PatchServer *zPSA, MSKlient *mk );
+	// Destruktor
+	~PSDetails();
+	// nicht constant
+	void setServerId( int id );
+	virtual void thread();
+	// constant
+
+	// Reference Counting
+	PSDetails *getThis();
+	PSDetails *release();
+};
+
+class PSSuche : public Thread
+{
+private:
+	PatchServer *zPSA;
+	MSKlient *mk;
+	int ref;
+
+public:
+	// Konstruktor
+	PSSuche( PatchServer *zPSA, MSKlient *mk );
+	// Destruktor
+	~PSSuche();
+	// nicht constant
+	virtual void thread();
+	// constant
+
+	// Reference Counting
+	PSSuche *getThis();
+	PSSuche *release();
+};
+
+class PatchServer : public Abschnitt
+{
+private:
+	Fenster *fenster;
+	Fenster *liste;
+	Fenster *details;
+	Fenster *updateF;
+	MSKlient *msk;
+	InitDatei *iD;
+	Fenster *f;
+	AdminAccount *account;
+	Knopf *aktualisieren;
+	Knopf *weiter;
+	Knopf *zurück;
+	ObjTabelle *tabelle;
+	ObjTabelle *updateT;
+	PSSuche *suchen;
+	PSDetails *getDetails;
+	PSUpdate *updateTh;
+	Schrift *schrift;
+	PSKlient *psc;
+	TextFeld *serverId;
+	TextFeld *serverName;
+	TextFeld *serverIp;
+	TextFeld *serverPort;
+	TextFeld *serverAPort;
+	TextFeld *serverClients;
+	TextFeld *serverMaxClients;
+	TextFeld *maxClients;
+	TextFeld *serverStatus;
+	TextFeld *serverFehler;
+	Knopf *updateStarten;
+	Knopf *update;
+	Knopf *pausieren;
+	Knopf *stoppen;
+	Knopf *beenden;
+	Knopf *terminieren;
+	Knopf *setMaxClients;
+	Zeichnung *obj;
+	int ref;
+
+public:
+	// Konstruktor
+	PatchServer( Schrift *s, InitDatei *d, MSKlient *msk, RessourceBild *rb, AdminAccount *acc, Bildschirm *b );
+	// Destruktor
+	~PatchServer();
+	// nicht constant
+	virtual void setFenster( Fenster *f );
+	virtual void setSichtbar( bool s );
+	void addServer( int id, char *name, char *ip, int port, int adminPort, char *status );
+	void sucheAbgeschlossen();
+	void setServerDetails( int id, char *name, char *ip, int port, int adminPort, int clients, int maxClients, int status, Text *error );
+	void setUpdateProzent( int prozent, int gruppe );
+	void setUpdateFertig( bool error, int gruppe );
+	bool aktualisierenMausEreignis( void *o, MausEreignis me );
+	bool auswahlKnopfMausEreignis( void *o, MausEreignis me );
+	bool weiterMausEreignis( void *o, MausEreignis me );
+	bool zurückMausEreignis( void *o, MausEreignis me );
+	bool updateMausEreignis( void *o, MausEreignis me );
+	bool pausierenMausEreignis( void *o, MausEreignis me );
+	bool stoppenMausEreignis( void *o, MausEreignis me );
+	bool beendenMausEreignis( void *o, MausEreignis me );
+	bool terminierenMausEreignis( void *o, MausEreignis me );
+	bool setMaxClientsMausEreignis( void *o, MausEreignis me );
+	bool updateStartenMausEreignis( void *o, MausEreignis me );
+	bool maxClientsTastaturEreignis( void *o, TastaturEreignis te );
+	// constant
+
+	// Reference Counting
+	virtual Abschnitt *getThis();
+	virtual Abschnitt *release();
+};
+
+// Ereignisse
+bool patchServerAktualisierenMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerAuswahlKnopfMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerWeiterMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerZurückMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerUpdateMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerPausierenMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerStoppenMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerBeendenMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerTerminierenMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerSetMaxClientsMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerUpdateStartenMausEreignis( void *p, void *o, MausEreignis me );
+bool patchServerMaxClientsTastaturEreignis( void *p, void *o, TastaturEreignis te );
+
+#endif

+ 1044 - 0
SMP/Programm/Version/Version.cpp

@@ -0,0 +1,1044 @@
+#include "Version.h"
+#include <Datei.h>
+#include <Zeit.h>
+
+// Inhalt der Version Klasse aus Version.h
+// Konstruktor
+Version::Version( Schrift *s, MSKlient *msc, RessourceBild *rb, AdminAccount *acc, Bildschirm *b )
+	: Abschnitt( b )
+{
+	fenster = 0;
+	this->msc = msc;
+	account = acc;
+	schrift = s;
+    psc = 0;
+
+    Array< ServerData* > list;
+    if( msc->getPatchServerListe( &list ) )
+    {
+        int anz = list.getEintragAnzahl();
+        for( int i = 0; i < anz; i++ )
+        {
+            ServerData *server = list.get( i );
+            psc = new PSKlient( server->ip, server->adminPort );
+            if( psc->verbinden() )
+                break;
+            psc = (PSKlient*)psc->release();
+        }
+    }
+    if( !psc )
+        WMessageBox( 0, new Text( "Warnung" ), new Text( "Es wurde kein erreichbarer Patch Server gefunden. Es kann keine neue Version des Clients veröffentlicht werden." ), MB_ICONERROR );
+    else
+        psc->login( acc->zName()->getText(), acc->zPasswort()->getText() );
+	f = new Fenster();
+	f->setStyle( Fenster::Style::Sichtbar | Fenster::Style::Erlaubt | Fenster::Style::Rahmen | Fenster::Style::Titel | Fenster::Style::TitelBuffered );
+	f->setRFarbe( 0xFFFFFFFF );
+	f->setRBreite( 1 );
+	f->setTitel( "Version" );
+	f->setTSchriftZ( s->getThis() );
+	f->setTSFarbe( 0xFFFFFFFF );
+	f->setTSSize( 12 );
+	f->setTAfFarbe( 0x1000FF00 );
+	f->setTAfStrength( -15 );
+	f->setTRFarbe( 0xFFFFFFFF );
+	f->setTRBreite( 1 );
+	f->zTTextFeld()->addStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Center | TextFeld::Style::Rahmen );
+	f->zTTextFeld()->setSize( 0, 20 );
+	f->setSize( 700, 700 );
+
+	gruppeF = new Fenster();
+	gruppeF->setStyle( Fenster::Style::Sichtbar | Fenster::Style::Erlaubt );
+	gruppeF->setSize( 680, 640 );
+	gruppeF->setPosition( 10, 10 );
+	f->addMember( gruppeF );
+
+	gruppeT = new ObjTabelle();
+	gruppeT->setStyle( ObjTabelle::Style::Sichtbar | ObjTabelle::Style::Erlaubt | ObjTabelle::Style::Rahmen | ObjTabelle::Style::VScroll );
+	gruppeT->setVertikalKlickScroll( 10 );
+	gruppeT->setMausEreignis( _ret1ME );
+	gruppeT->setLinienRahmenFarbe( 0xFFFFFFFF );
+	gruppeT->setSize( 680, 600 );
+	gruppeT->addSpalte( "Name" );
+	gruppeT->addSpalte( "Pfad" );
+	gruppeT->addSpalte( "Version" );
+	gruppeT->addSpalte( "Auswahl" );
+	gruppeT->setSpaltenBreite( 0, 285 );
+	gruppeT->setSpaltenBreite( 1, 285 );
+	gruppeT->setSpaltenBreite( 2, 68 );
+	gruppeT->setSpaltenBreite( 3, 22 );
+	gruppeT->addZeile( "Titel" );
+	gruppeT->setZeilenHeight( 0, 20 );
+	TextFeld *gTN = new TextFeld();
+	gTN->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+	gTN->setSchriftZ( s->getThis() );
+	gTN->setSchriftFarbe( 0xFFFFFFFF );
+	gTN->setSchriftSize( 12 );
+	gTN->setLinienRahmenFarbe( 0xFFFFFFFF );
+	gTN->setText( "Name" );
+	gruppeT->setZeichnungZ( 0, 0, gTN );
+	TextFeld *gTP = new TextFeld();
+	gTP->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+	gTP->setSchriftZ( s->getThis() );
+	gTP->setSchriftFarbe( 0xFFFFFFFF );
+	gTP->setSchriftSize( 12 );
+	gTP->setLinienRahmenFarbe( 0xFFFFFFFF );
+	gTP->setText( "Pfad" );
+	gruppeT->setZeichnungZ( 1, 0, gTP );
+	TextFeld *gTV = new TextFeld();
+	gTV->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+	gTV->setSchriftZ( s->getThis() );
+	gTV->setSchriftFarbe( 0xFFFFFFFF );
+	gTV->setSchriftSize( 12 );
+	gTV->setLinienRahmenFarbe( 0xFFFFFFFF );
+	gTV->setText( "Version" );
+	gruppeT->setZeichnungZ( 2, 0, gTV );
+	gruppeT->setMausEreignis( _ret1ME );
+	gruppeT->setTastaturEreignis( _ret1TE );
+	gruppeF->addMember( gruppeT );
+
+	neuGruppeName = new TextFeld();
+	neuGruppeName->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Erlaubt | TextFeld::Style::Rahmen | TextFeld::Style::Buffered | TextFeld::Style::VCenter );
+	neuGruppeName->setSchriftZ( s->getThis() );
+	neuGruppeName->setSchriftFarbe( 0xFFFFFFFF );
+	neuGruppeName->setSchriftSize( 12 );
+	neuGruppeName->setLinienRahmenBreite( 1 );
+	neuGruppeName->setLinienRahmenFarbe( 0xFFFFFFFF );
+	neuGruppeName->setAlphaFeldFarbe( 0x1000FF00 );
+	neuGruppeName->setAlphaFeldStrength( -5 );
+	neuGruppeName->setSize( 285, 20 );
+	neuGruppeName->setPosition( 40, 610 );
+	neuGruppeName->setMausEreignis( _ret1ME );
+	neuGruppeName->setTastaturEreignis( _ret1TE );
+	neuGruppeName->setText( "" );
+	gruppeF->addMember( neuGruppeName );
+
+	neuGruppePfad = new TextFeld();
+	neuGruppePfad->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Erlaubt | TextFeld::Style::Rahmen | TextFeld::Style::Buffered | TextFeld::Style::VCenter );
+	neuGruppePfad->setSchriftZ( s->getThis() );
+	neuGruppePfad->setSchriftFarbe( 0xFFFFFFFF );
+	neuGruppePfad->setSchriftSize( 12 );
+	neuGruppePfad->setLinienRahmenBreite( 1 );
+	neuGruppePfad->setLinienRahmenFarbe( 0xFFFFFFFF );
+	neuGruppePfad->setAlphaFeldFarbe( 0x1000FF00 );
+	neuGruppePfad->setAlphaFeldStrength( -5 );
+	neuGruppePfad->setSize( 285, 20 );
+	neuGruppePfad->setPosition( 330, 610 );
+	neuGruppePfad->setMausEreignis( _ret1ME );
+	neuGruppePfad->setTastaturEreignis( _ret1TE );
+	neuGruppePfad->setText( "" );
+	gruppeF->addMember( neuGruppePfad );
+
+	neuGruppeK = new Knopf();
+	neuGruppeK->setText( "" );
+	neuGruppeK->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Erlaubt | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+	neuGruppeK->setHintergrundBildZ( rb->get( "neu.png" ) );
+	neuGruppeK->setPosition( 625, 610 );
+	neuGruppeK->setSize( 20, 20 );
+	neuGruppeK->setMausEreignisParameter( this );
+	neuGruppeK->setMausEreignis( versionNeuGruppeKMausEreignis );
+	gruppeF->addMember( neuGruppeK );
+
+	systemF = new Fenster();
+	systemF->setStyle( Fenster::Style::Erlaubt );
+	systemF->setSize( 680, 640 );
+	systemF->setPosition( 10, 10 );
+	f->addMember( systemF );
+
+	systemInit = new InitDatei();
+
+	systemT = new ObjTabelle();
+	systemT->setStyle( ObjTabelle::Style::Sichtbar | ObjTabelle::Style::Erlaubt | ObjTabelle::Style::Rahmen | ObjTabelle::Style::VScroll );
+	systemT->setVertikalKlickScroll( 10 );
+	systemT->setMausEreignis( _ret1ME );
+	systemT->setLinienRahmenFarbe( 0xFFFFFFFF );
+	systemT->setSize( 680, 600 );
+	systemT->addSpalte( "Name" );
+	systemT->addSpalte( "Pfad" );
+	systemT->addSpalte( "Auswahl" );
+	systemT->setSpaltenBreite( 0, 150 );
+	systemT->setSpaltenBreite( 1, 490 );
+	systemT->setSpaltenBreite( 2, 22 );
+	systemT->addZeile( "Titel" );
+	systemT->setZeilenHeight( 0, 20 );
+	TextFeld *sTN = new TextFeld();
+	sTN->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+	sTN->setSchriftZ( s->getThis() );
+	sTN->setSchriftFarbe( 0xFFFFFFFF );
+	sTN->setSchriftSize( 12 );
+	sTN->setLinienRahmenFarbe( 0xFFFFFFFF );
+	sTN->setText( "Name" );
+	systemT->setZeichnungZ( 0, 0, sTN );
+	TextFeld *sTP = new TextFeld();
+	sTP->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+	sTP->setSchriftZ( s->getThis() );
+	sTP->setSchriftFarbe( 0xFFFFFFFF );
+	sTP->setSchriftSize( 12 );
+	sTP->setLinienRahmenFarbe( 0xFFFFFFFF );
+	sTP->setText( "Pfad" );
+	systemT->setZeichnungZ( 1, 0, sTP );
+	systemT->setMausEreignis( _ret1ME );
+	systemT->setTastaturEreignis( _ret1TE );
+	systemF->addMember( systemT );
+
+	neuSystemName = new TextFeld();
+	neuSystemName->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Erlaubt | TextFeld::Style::Rahmen | TextFeld::Style::Buffered | TextFeld::Style::VCenter );
+	neuSystemName->setSchriftZ( s->getThis() );
+	neuSystemName->setSchriftFarbe( 0xFFFFFFFF );
+	neuSystemName->setSchriftSize( 12 );
+	neuSystemName->setLinienRahmenBreite( 1 );
+	neuSystemName->setLinienRahmenFarbe( 0xFFFFFFFF );
+	neuSystemName->setAlphaFeldFarbe( 0x1000FF00 );
+	neuSystemName->setAlphaFeldStrength( -5 );
+	neuSystemName->setSize( 490, 20 );
+	neuSystemName->setPosition( 80, 610 );
+	neuSystemName->setMausEreignis( _ret1ME );
+	neuSystemName->setTastaturEreignis( _ret1TE );
+	neuSystemName->setText( "" );
+	systemF->addMember( neuSystemName );
+
+	neuSystemK = new Knopf();
+	neuSystemK->setText( "" );
+	neuSystemK->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Erlaubt | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+	neuSystemK->setHintergrundBildZ( rb->get( "neu.png" ) );
+	neuSystemK->setPosition( 580, 610 );
+	neuSystemK->setSize( 20, 20 );
+	neuSystemK->setMausEreignisParameter( this );
+	neuSystemK->setMausEreignis( versionNeuSystemKMausEreignis );
+	systemF->addMember( neuSystemK );
+
+	dateiF = new Fenster();
+	dateiF->setStyle( Fenster::Style::Erlaubt );
+	dateiF->setSize( 680, 640 );
+	dateiF->setPosition( 10, 10 );
+	f->addMember( dateiF );
+
+	dateiT = new ObjTabelle();
+	dateiT->setStyle( ObjTabelle::Style::Sichtbar | ObjTabelle::Style::Erlaubt | ObjTabelle::Style::Rahmen | ObjTabelle::Style::VScroll );
+	dateiT->setVertikalKlickScroll( 10 );
+	dateiT->setMausEreignis( _ret1ME );
+	dateiT->setLinienRahmenFarbe( 0xFFFFFFFF );
+	dateiT->setSize( 680, 600 );
+	dateiT->addSpalte( "Pfad" );
+	dateiT->addSpalte( "Version" );
+	dateiT->addSpalte( "Status" );
+	dateiT->setSpaltenBreite( 0, 510 );
+	dateiT->setSpaltenBreite( 1, 50 );
+	dateiT->setSpaltenBreite( 2, 100 );
+	dateiT->addZeile( "Titel" );
+	dateiT->setZeilenHeight( 0, 20 );
+	TextFeld *dTP = new TextFeld();
+	dTP->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+	dTP->setSchriftZ( s->getThis() );
+	dTP->setSchriftFarbe( 0xFFFFFFFF );
+	dTP->setSchriftSize( 12 );
+	dTP->setLinienRahmenFarbe( 0xFFFFFFFF );
+	dTP->setText( "Pfad" );
+	dateiT->setZeichnungZ( 0, 0, dTP );
+	TextFeld *dTV = new TextFeld();
+	dTV->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+	dTV->setSchriftZ( s->getThis() );
+	dTV->setSchriftFarbe( 0xFFFFFFFF );
+	dTV->setSchriftSize( 12 );
+	dTV->setLinienRahmenFarbe( 0xFFFFFFFF );
+	dTV->setText( "Version" );
+	dateiT->setZeichnungZ( 1, 0, dTV );
+	TextFeld *dTS = new TextFeld();
+	dTS->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+	dTS->setSchriftZ( s->getThis() );
+	dTS->setSchriftFarbe( 0xFFFFFFFF );
+	dTS->setSchriftSize( 12 );
+	dTS->setLinienRahmenFarbe( 0xFFFFFFFF );
+	dTS->setText( "Status" );
+	dateiT->setZeichnungZ( 2, 0, dTS );
+	dateiF->addMember( dateiT );
+
+	commit = new Knopf();
+	commit->setStyle( Knopf::Style::Normal );
+	commit->setText( "Veröffentlichen" );
+	commit->setSchriftZ( s->getThis() );
+	commit->setMausEreignisParameter( this );
+	commit->setMausEreignis( versionCommitMausEreignis );
+	commit->setSize( 100, 20 );
+	commit->setPosition( 290, 610 );
+	dateiF->addMember( commit );
+
+	fehlerF = new Fenster();
+	fehlerF->setStyle( Fenster::Style::Erlaubt );
+	fehlerF->setSize( 680, 640 );
+	fehlerF->setPosition( 10, 10 );
+	f->addMember( fehlerF );
+
+	fehlerText = new TextFeld();
+	fehlerText->setStyle( TextFeld::Style::Text );
+	fehlerText->setSchriftZ( s->getThis() );
+	fehlerText->setSchriftFarbe( 0xFFFFFFFF );
+	fehlerText->setSchriftSize( 12 );
+	fehlerText->setText( "" );
+	fehlerText->setSize( 680, 650 );
+	fehlerF->addMember( fehlerText );
+
+	zurück = new Knopf();
+	zurück->setText( "" );
+	zurück->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+	zurück->setHintergrundBildZ( rb->get( "zurück.png" ) );
+	zurück->setPosition( 295, 650 );
+	zurück->setSize( 20, 20 );
+	zurück->setMausEreignisParameter( this );
+	zurück->setMausEreignis( versionZurückMausEreignis );
+	f->addMember( zurück );
+
+	aktualisieren = new Knopf();
+	aktualisieren->setText( "" );
+	aktualisieren->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Erlaubt | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+	aktualisieren->setHintergrundBildZ( rb->get( "neuladen.png" ) );
+	aktualisieren->setPosition( 325, 650 );
+	aktualisieren->setSize( 20, 20 );
+	aktualisieren->setMausEreignisParameter( this );
+	aktualisieren->setMausEreignis( versionAktualisierenMausEreignis );
+	f->addMember( aktualisieren );
+
+	speichern = new Knopf();
+	speichern->setText( "" );
+	speichern->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+	speichern->setHintergrundBildZ( rb->get( "speichern.png" ) );
+	speichern->setPosition( 355, 650 );
+	speichern->setSize( 20, 20 );
+	speichern->setMausEreignisParameter( this );
+	speichern->setMausEreignis( versionSpeichernMausEreignis );
+	f->addMember( speichern );
+
+	weiter = new Knopf();
+	weiter->setText( "" );
+	weiter->setStyle( Knopf::Style::Sichtbar | Knopf::Style::Hintergrund | Knopf::Style::HBild | Knopf::Style::HAlpha | Knopf::Style::KlickBuffer );
+	weiter->setHintergrundBildZ( rb->get( "weiter.png" ) );
+	weiter->setPosition( 385, 650 );
+	weiter->setSize( 20, 20 );
+	weiter->setMausEreignisParameter( this );
+	weiter->setMausEreignis( versionWeiterMausEreignis );
+	f->addMember( weiter );
+
+	sName = new Text( "" );
+	system = 0;
+
+	rb->release();
+	ref = 1;
+}
+
+// Destruktor
+Version::~Version()
+{
+	for( int i = 1; i < gruppeT->getZeilenAnzahl(); i++ )
+	{
+		( (TextFeld*)gruppeT->zZeichnung( 0, i ) )->release();
+		( (TextFeld*)gruppeT->zZeichnung( 1, i ) )->release();
+		( (TextFeld*)gruppeT->zZeichnung( 2, i ) )->release();
+		( (KontrollKnopf*)gruppeT->zZeichnung( 3, i ) )->release();
+	}
+	if( gruppeT->getZeilenAnzahl() )
+	{
+		( (TextFeld*)gruppeT->zZeichnung( 0, 0 ) )->release();
+		( (TextFeld*)gruppeT->zZeichnung( 1, 0 ) )->release();
+		( (TextFeld*)gruppeT->zZeichnung( 2, 0 ) )->release();
+	}
+	for( int i = 1; i < systemT->getZeilenAnzahl(); i++ )
+	{
+		( (TextFeld*)systemT->zZeichnung( 0, i ) )->release();
+		( (TextFeld*)systemT->zZeichnung( 1, i ) )->release();
+		( (KontrollKnopf*)systemT->zZeichnung( 2, i ) )->release();
+	}
+	if( systemT->getZeilenAnzahl() )
+	{
+		( (TextFeld*)systemT->zZeichnung( 0, 0 ) )->release();
+		( (TextFeld*)systemT->zZeichnung( 1, 0 ) )->release();
+	}
+	for( int i = 0; i < dateiT->getZeilenAnzahl(); i++ )
+	{
+		( (TextFeld*)dateiT->zZeichnung( 0, i ) )->release();
+		( (TextFeld*)dateiT->zZeichnung( 1, i ) )->release();
+		( (TextFeld*)dateiT->zZeichnung( 2, i ) )->release();
+	}
+	if( fenster )
+	{
+		fenster->removeMember( f );
+		fenster->release();
+	}
+	account->release();
+	msc->release();
+    if( psc )
+        psc->release();
+	f->release();
+	gruppeF->release();
+	gruppeT->release();
+	neuGruppeName->release();
+	neuGruppePfad->release();
+	neuGruppeK->release();
+	systemF->release();
+	systemInit->release();
+	systemT->release();
+	neuSystemName->release();
+	neuSystemK->release();
+	speichern->release();
+	weiter->release();
+	dateiF->release();
+	dateiT->release();
+	commit->release();
+	aktualisieren->release();
+	fehlerF->release();
+	fehlerText->release();
+	zurück->release();
+	schrift->release();
+	sName->release();
+}
+
+// privat
+void Version::sucheDateien( const char *pfad, RCArray< ReferenceCounting< FileInfo > > &list )
+{
+	Datei *d = new Datei();
+	d->setDatei( pfad );
+	if( d->istOrdner() )
+	{
+		RCArray< Text > *liste = d->getDateiListe();
+		int anzahl = d->getUnterdateiAnzahl();
+		for( int i = 0; i < anzahl; i++ )
+		{
+			Text *p = new Text( pfad );
+			p->append( "/" );
+			p->append( liste->z( i )->getText() );
+			sucheDateien( p->getText(), list );
+			p->release();
+		}
+		liste->release();
+	}
+	d->release();
+	Text *pf = new Text( pfad );
+	pf->remove( systemInit->zWert( sName->getText() )->getText() );
+	pf->remove( 0, 1 );
+	if( !pf->getLength() )
+	{
+		pf->release();
+		return;
+	}
+	bool gefunden = 0;
+    int anz = list.getEintragAnzahl();
+	for( int i = 0; i < anz; i++ )
+	{
+		if( pf->istGleich( list.z( i )->path ) )
+		{
+			gefunden = 1;
+			break;
+		}
+	}
+	if( !gefunden )
+	{
+		dateiT->addZeile( "0" );
+		TextFeld *pfad = new TextFeld();
+		pfad->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::VCenter );
+		pfad->setSchriftZ( schrift->getThis() );
+		pfad->setSchriftFarbe( 0xFFFFFFFF );
+		pfad->setSchriftSize( 12 );
+		pfad->setLinienRahmenFarbe( 0xFFFFFFFF );
+		pfad->setText( pf->getText() );
+		dateiT->setZeichnungZ( 0, dateiT->getZeilenAnzahl() - 1, pfad );
+		TextFeld *version = new TextFeld();
+		version->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+		version->setSchriftZ( schrift->getThis() );
+		version->setSchriftFarbe( 0xFFFFFFFF );
+		version->setSchriftSize( 12 );
+		version->setLinienRahmenFarbe( 0xFFFFFFFF );
+		version->setText( "0" );
+		dateiT->setZeichnungZ( 1, dateiT->getZeilenAnzahl() - 1, version );
+		TextFeld *status = new TextFeld();
+		status->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+		status->setSchriftZ( schrift->getThis() );
+		status->setSchriftFarbe( 0xFFFFFFFF );
+		status->setSchriftSize( 12 );
+		status->setLinienRahmenFarbe( 0xFFFFFFFF );
+		status->setText( "Neu" );
+		dateiT->setZeichnungZ( 2, dateiT->getZeilenAnzahl() - 1, status );
+	}
+	pf->release();
+}
+
+// nicht constant
+void Version::setFenster( Fenster *f )
+{
+	if( fenster )
+		fenster->release();
+	this->f->setPosition( f->getBreite() / 2 - this->f->getBreite() / 2, f->getHeight() / 2 - this->f->getHeight() / 2 );
+	fenster = f;
+}
+
+void Version::setSichtbar( bool s )
+{
+	sichtbar = s;
+	if( s )
+		fenster->addMember( f );
+	else
+		fenster->removeMember( f );
+}
+
+bool Version::neuGruppeKMausEreignis( void *o, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+	{
+		if( neuGruppeName->zText()->getLength() )
+		{
+			/*if( !pgDb->neueDateiGruppeErstellen( neuGruppeName->zText()->getText(), neuGruppePfad->zText()->getText() ) )
+			{
+				fehlerText->setText( "Es ist ein Fehler aufgetreten. Siehe in den Logdateien nach für nähere\nInformationen." );
+				gruppeF->removeStyle( Fenster::Style::Sichtbar );
+				weiter->removeStyle( Knopf::Style::Erlaubt );
+				zurück->addStyle( Knopf::Style::Erlaubt );
+				aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+				speichern->removeStyle( Knopf::Style::Erlaubt );
+				fehlerF->addStyle( Fenster::Style::Sichtbar );
+			}
+			else
+			{
+				neuGruppeName->setText( "" );
+				neuGruppeName->setAuswahl( 0, 0 );
+				neuGruppePfad->setText( "" );
+				neuGruppePfad->setAuswahl( 0, 0 );
+				aktualisierenMausEreignis( 0, me );
+			}*/
+            WMessageBox( 0, new Text( "Warnung" ), new Text( "Diese Funktion ist momentan nicht implementiert. Nehmen sie die Änderungen manuell in der Datenbank vor." ), MB_ICONERROR );
+		}
+	}
+	return 1;
+}
+
+bool Version::auswahlKnopfMausEreignis( void *o, MausEreignis me )
+{
+	if( !o )
+		return 0;
+	if( me.id == ME_RLinks )
+	{
+		if( gruppeF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			for( int i = 1; i < gruppeT->getZeilenAnzahl(); i++ )
+				( (KontrollKnopf*)gruppeT->zZeichnung( 3, i ) )->removeStyle( KontrollKnopf::Style::Selected );
+			weiter->addStyle( Knopf::Style::Erlaubt );
+		}
+		else if( systemF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			for( int i = 1; i < systemT->getZeilenAnzahl(); i++ )
+				( (KontrollKnopf*)systemT->zZeichnung( 2, i ) )->removeStyle( KontrollKnopf::Style::Selected );
+			weiter->addStyle( Knopf::Style::Erlaubt );
+		}
+	}
+	return 1;
+}
+
+bool Version::neuSystemKMausEreignis( void *o, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+	{
+		if( neuSystemName->zText()->getLength() )
+		{
+			/*if( !pgDb->neuesSystemErstellen( neuSystemName->zText()->getText() ) )
+			{
+				fehlerText->setText( "Es ist ein Fehler aufgetreten. Siehe in den Logdateien nach für nähere\nInformationen." );
+				systemF->removeStyle( Fenster::Style::Sichtbar );
+				weiter->removeStyle( Knopf::Style::Erlaubt );
+				zurück->addStyle( Knopf::Style::Erlaubt );
+				aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+				speichern->removeStyle( Knopf::Style::Erlaubt );
+				fehlerF->addStyle( Fenster::Style::Sichtbar );
+			}
+			else
+			{
+				neuSystemName->setText( "" );
+				neuSystemName->setAuswahl( 0, 0 );
+				aktualisierenMausEreignis( 0, me );
+			}*/
+            WMessageBox( 0, new Text( "Warnung" ), new Text( "Diese Funktion ist momentan nicht implementiert. Nehmen sie die Änderungen manuell in der Datenbank vor." ), MB_ICONERROR );
+		}
+	}
+	return 1;
+}
+
+bool Version::speichernMausEreignis( void *o, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+	{
+		systemInit->removeAlle();
+		for( int i = 1; i < systemT->getZeilenAnzahl(); i++ )
+		{
+			systemInit->addWert( ( (TextFeld*)systemT->zZeichnung( 0, i ) )->zText()->getText(),
+								 ( (TextFeld*)systemT->zZeichnung( 1, i ) )->zText()->getText() );
+			systemInit->speichern();
+		}
+	}
+	return 1;
+}
+
+bool Version::weiterMausEreignis( void *o, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+	{
+		if( gruppeF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			for( int i = 1; i < gruppeT->getZeilenAnzahl(); i++ )
+			{
+				if( ( (KontrollKnopf*)gruppeT->zZeichnung( 3, i ) )->hatStyle( KontrollKnopf::Style::Selected ) )
+				{
+					gruppe = TextZuInt( gruppeT->zZeilenName( i )->getText(), 10 );
+					Text *pfad = new Text( "data/" );
+					pfad->append( ( (TextFeld*)gruppeT->zZeichnung( 0, i ) )->getText() );
+					pfad->append( ".ini" );
+					systemInit->setPfad( pfad );
+					systemInit->removeAlle();
+					systemInit->laden();
+					gruppeF->removeStyle( Fenster::Style::Sichtbar );
+					systemF->addStyle( Fenster::Style::Sichtbar );
+					speichern->addStyle( Knopf::Style::Erlaubt );
+					aktualisieren->addStyle( Knopf::Style::Erlaubt );
+					weiter->removeStyle( Knopf::Style::Erlaubt );
+					zurück->addStyle( Knopf::Style::Erlaubt );
+					aktualisierenMausEreignis( 0, me );
+					return 1;
+				}
+			}
+		}
+		else if( systemF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			for( int i = 1; i < systemT->getZeilenAnzahl(); i++ )
+			{
+				if( ( (KontrollKnopf*)systemT->zZeichnung( 2, i ) )->hatStyle( KontrollKnopf::Style::Selected ) )
+				{
+					sName->setText( ( (TextFeld*)systemT->zZeichnung( 0, i ) )->zText()->getText() );
+					system = TextZuInt( systemT->zZeilenName( i )->getText(), 10 );
+					systemF->removeStyle( Fenster::Style::Sichtbar );
+					speichern->removeStyle( Knopf::Style::Erlaubt );
+					aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+					weiter->removeStyle( Knopf::Style::Erlaubt );
+					zurück->addStyle( Knopf::Style::Erlaubt );
+					if( !systemInit->wertExistiert( sName->getText() ) )
+					{
+						fehlerText->setText( "Der Pfad wurde für dieses System noch nicht gesetzt." );
+						fehlerF->addStyle( Fenster::Style::Sichtbar );
+						return 1;
+					}
+					if( !DateiExistiert( systemInit->getWert( sName->getText() ) ) || !DateiIstVerzeichnis( systemInit->getWert( sName->getText() ) ) )
+					{
+						fehlerText->setText( "Unter dem angegebenem Pfad wurde keine Datei gefunden." );
+						fehlerF->addStyle( Fenster::Style::Sichtbar );
+						return 1;
+					}
+					aktualisieren->addStyle( Knopf::Style::Erlaubt );
+					dateiF->addStyle( Fenster::Style::Sichtbar );
+					aktualisierenMausEreignis( 0, me );
+					return 1;
+				}
+			}
+		}
+	}
+	return 1;
+}
+
+bool Version::commitMausEreignis( void *o, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+	{
+		/*if( !pgDb->adminHatRecht( account->getId(), Admin_Recht::LTCUpdate ) )
+		{
+			dateiF->removeStyle( Fenster::Style::Sichtbar );
+			aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+			fehlerText->setText( "Du hast keine Berechtigung für diesen Vorgang." );
+			fehlerF->addStyle( Fenster::Style::Sichtbar );
+			zurück->addStyle( Knopf::Style::Erlaubt );
+			return 1;
+		}
+		if( pgDb->sindPatchServerOnline() )
+		{
+			dateiF->removeStyle( Fenster::Style::Sichtbar );
+			aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+			fehlerText->setText( "Es müssen zunächst alle Patchserver herunterfahren." );
+			fehlerF->addStyle( Fenster::Style::Sichtbar );
+			zurück->addStyle( Knopf::Style::Erlaubt );
+			return 1;
+		}*/
+		aktualisierenMausEreignis( 0, me );
+		bool gU = 0;
+		for( int i = 1; i < dateiT->getZeilenAnzahl(); i++ )
+		{
+			if( ( (TextFeld*)dateiT->zZeichnung( 2, i ) )->zText()->istGleich( "Veraltet" ) )
+			{ // datei ist Veraltet
+				Text *pfad = new Text( systemInit->zWert( sName->getText() )->getText() );
+				pfad->append( "/" );
+				pfad->append( ( (TextFeld*)dateiT->zZeichnung( 0, i ) )->zText()->getText() );
+				Datei *d = new Datei();
+				d->setDatei( pfad );
+				Zeit *zeit = d->getLastChange();
+                if( !psc->updateFile( ( (TextFeld*)dateiT->zZeichnung( 0, i ) )->zText()->getText(), zeit, system, gruppe ) )
+                {
+                    dateiF->removeStyle( Fenster::Style::Sichtbar );
+                    aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                    fehlerText->setText( psc->getLetzterFehler() );
+                    fehlerF->addStyle( Fenster::Style::Sichtbar );
+                    zurück->addStyle( Knopf::Style::Erlaubt );
+                    if( zeit )
+                        zeit->release();
+                    d->release();
+                    return 1;
+                }
+				if( zeit )
+					zeit->release();
+				d->release();
+				gU = 1;
+			}
+			else if( ( (TextFeld*)dateiT->zZeichnung( 2, i ) )->zText()->istGleich( "Gelöscht" ) )
+			{ // datei ist Gelöscht
+                if( !psc->updateFile( ( (TextFeld*)dateiT->zZeichnung( 0, i ) )->zText()->getText(), 0, system, gruppe ) )
+                {
+                    dateiF->removeStyle( Fenster::Style::Sichtbar );
+                    aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                    fehlerText->setText( psc->getLetzterFehler() );
+                    fehlerF->addStyle( Fenster::Style::Sichtbar );
+                    zurück->addStyle( Knopf::Style::Erlaubt );
+                    return 1;
+                }
+				gU = 1;
+			}
+			else if( ( (TextFeld*)dateiT->zZeichnung( 2, i ) )->zText()->istGleich( "Neu" ) )
+			{ // datei ist Neu
+				Text *pfad = new Text( systemInit->zWert( sName->getText() )->getText() );
+				pfad->append( "/" );
+				pfad->append( ( (TextFeld*)dateiT->zZeichnung( 0, i ) )->zText()->getText() );
+				Datei *d = new Datei();
+				d->setDatei( pfad );
+				Zeit *zeit = d->getLastChange();
+                if( !psc->updateFile( ( (TextFeld*)dateiT->zZeichnung( 0, i ) )->zText()->getText(), zeit, system, gruppe ) )
+                {
+                    dateiF->removeStyle( Fenster::Style::Sichtbar );
+                    aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                    fehlerText->setText( psc->getLetzterFehler() );
+                    fehlerF->addStyle( Fenster::Style::Sichtbar );
+                    zurück->addStyle( Knopf::Style::Erlaubt );
+                    if( zeit )
+                        zeit->release();
+                    d->release();
+                    return 1;
+                }
+				if( zeit )
+					zeit->release();
+				d->release();
+				gU = 1;
+			}
+		}
+        if( gU )
+        {
+            if( !psc->dateiGruppeUpdate( gruppe ) )
+            {
+                dateiF->removeStyle( Fenster::Style::Sichtbar );
+                aktualisieren->removeStyle( Knopf::Style::Erlaubt );
+                fehlerText->setText( psc->getLetzterFehler() );
+                fehlerF->addStyle( Fenster::Style::Sichtbar );
+                zurück->addStyle( Knopf::Style::Erlaubt );
+                return 1;
+            }
+        }
+		aktualisierenMausEreignis( 0, me );
+	}
+	return 1;
+}
+
+bool Version::aktualisierenMausEreignis( void *o, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+	{
+		if( gruppeF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			for( int i = 1; i < gruppeT->getZeilenAnzahl(); )
+			{
+				( (TextFeld*)gruppeT->zZeichnung( 0, i ) )->release();
+				( (TextFeld*)gruppeT->zZeichnung( 1, i ) )->release();
+				( (TextFeld*)gruppeT->zZeichnung( 2, i ) )->release();
+				( (KontrollKnopf*)gruppeT->zZeichnung( 3, i ) )->release();
+				gruppeT->removeZeile( i );
+			}
+            Array< FileGroupInfo* > list;
+            psc->getFileGroupInfoList( &list );
+            int anz = list.getEintragAnzahl();
+			for( int i = 0; i < anz; i++ )
+			{
+                FileGroupInfo *fileGroup = list.get( i );
+				Text *zeile = new Text( "" );
+				zeile->append( fileGroup->id );
+				gruppeT->addZeile( i + 1, zeile );
+				TextFeld *name = new TextFeld();
+				name->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::VCenter );
+				name->setSchriftZ( schrift->getThis() );
+				name->setSchriftFarbe( 0xFFFFFFFF );
+				name->setSchriftSize( 12 );
+				name->setLinienRahmenFarbe( 0xFFFFFFFF );
+				name->setText( fileGroup->name );
+				gruppeT->setZeichnungZ( 0, i + 1, name );
+				TextFeld *pfad = new TextFeld();
+				pfad->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Erlaubt | TextFeld::Style::Rahmen | TextFeld::Style::VCenter );
+				pfad->setSchriftZ( schrift->getThis() );
+				pfad->setSchriftFarbe( 0xFFFFFFFF );
+				pfad->setSchriftSize( 12 );
+				pfad->setLinienRahmenFarbe( 0xFFFFFFFF );
+				pfad->setText( fileGroup->path );
+				gruppeT->setZeichnungZ( 1, i + 1, pfad );
+				TextFeld *version = new TextFeld();
+				version->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Erlaubt | TextFeld::Style::Rahmen | TextFeld::Style::VCenter );
+				version->setSchriftZ( schrift->getThis() );
+				version->setSchriftFarbe( 0xFFFFFFFF );
+				version->setSchriftSize( 12 );
+				version->setLinienRahmenFarbe( 0xFFFFFFFF );
+				version->setText( Text( fileGroup->version ) );
+				gruppeT->setZeichnungZ( 2, i + 1, version );
+				KontrollKnopf *auswahl = new KontrollKnopf();
+				auswahl->setStyle( KontrollKnopf::Style::Sichtbar | KontrollKnopf::Style::Erlaubt | KontrollKnopf::Style::KlickBuffer | KontrollKnopf::Style::Rahmen );
+				auswahl->loadData( "data/bilder/icons.ltdb" );
+				auswahl->setMausEreignisParameter( this );
+				auswahl->setMausEreignis( versionAuswahlKnopfMausEreignis );
+				auswahl->setLinienRahmenFarbe( 0xFFFFFFFF );
+				gruppeT->setZeichnungZ( 3, i + 1, auswahl );
+                delete fileGroup;
+			}
+		}
+		else if( systemF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			for( int i = 1; i < systemT->getZeilenAnzahl(); )
+			{
+				( (TextFeld*)systemT->zZeichnung( 0, i ) )->release();
+				( (TextFeld*)systemT->zZeichnung( 1, i ) )->release();
+				( (KontrollKnopf*)systemT->zZeichnung( 2, i ) )->release();
+				systemT->removeZeile( i );
+			}
+            RCArray< ReferenceCounting< std::pair< int, Text > > > list;
+			psc->getSystemInfoList( &list );
+            int anz = list.getEintragAnzahl();
+			for( int i = 0; i < anz; i++ )
+			{
+                ReferenceCounting< std::pair< int, Text > > *system = list.z( i );
+				Text *zeile = new Text( "" );
+				zeile->append( system->first );
+				systemT->addZeile( i + 1, zeile );
+				TextFeld *name = new TextFeld();
+				name->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::VCenter );
+				name->setSchriftZ( schrift->getThis() );
+				name->setSchriftFarbe( 0xFFFFFFFF );
+				name->setSchriftSize( 12 );
+				name->setLinienRahmenFarbe( 0xFFFFFFFF );
+				name->setText( system->second );
+				systemT->setZeichnungZ( 0, i + 1, name );
+				TextFeld *pfad = new TextFeld();
+				pfad->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Erlaubt | TextFeld::Style::Rahmen | TextFeld::Style::VCenter );
+				pfad->setSchriftZ( schrift->getThis() );
+				pfad->setText( "" );
+				if( systemInit->wertExistiert( system->second ) )
+					pfad->setText( systemInit->zWert( (char*)system->second )->getText() );
+				pfad->setSchriftFarbe( 0xFFFFFFFF );
+				pfad->setSchriftSize( 12 );
+				pfad->setLinienRahmenFarbe( 0xFFFFFFFF );
+				systemT->setZeichnungZ( 1, i + 1, pfad );
+				KontrollKnopf *auswahl = new KontrollKnopf();
+				auswahl->setStyle( KontrollKnopf::Style::Sichtbar | KontrollKnopf::Style::Erlaubt | KontrollKnopf::Style::KlickBuffer | KontrollKnopf::Style::Rahmen );
+				auswahl->loadData( "data/bilder/icons.ltdb" );
+				auswahl->setMausEreignisParameter( this );
+				auswahl->setMausEreignis( versionAuswahlKnopfMausEreignis );
+				auswahl->setLinienRahmenFarbe( 0xFFFFFFFF );
+				systemT->setZeichnungZ( 2, i + 1, auswahl );
+			}
+		}
+		else if( dateiF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			for( int i = 1; i < dateiT->getZeilenAnzahl(); )
+			{
+				( (TextFeld*)dateiT->zZeichnung( 0, i ) )->release();
+				( (TextFeld*)dateiT->zZeichnung( 1, i ) )->release();
+				( (TextFeld*)dateiT->zZeichnung( 2, i ) )->release();
+				dateiT->removeZeile( i );
+			}
+            RCArray< ReferenceCounting< FileInfo > > list;
+            psc->getFileInfoList( system, gruppe, &list );
+            int anz = list.getEintragAnzahl();
+			for( int i = 0; i < anz; i++ )
+			{
+                ReferenceCounting< FileInfo > *info = list.z( i );
+				Text *zeile = new Text( "" );
+				zeile->append( info->id );
+				dateiT->addZeile( i + 1, zeile );
+				TextFeld *pfad = new TextFeld();
+				pfad->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::VCenter );
+				pfad->setSchriftZ( schrift->getThis() );
+				pfad->setSchriftFarbe( 0xFFFFFFFF );
+				pfad->setSchriftSize( 12 );
+				pfad->setLinienRahmenFarbe( 0xFFFFFFFF );
+				pfad->setText( info->path );
+				dateiT->setZeichnungZ( 0, i + 1, pfad );
+				TextFeld *version = new TextFeld();
+				version->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+				version->setSchriftZ( schrift->getThis() );
+				version->setSchriftFarbe( 0xFFFFFFFF );
+				version->setSchriftSize( 12 );
+				version->setLinienRahmenFarbe( 0xFFFFFFFF );
+				version->setText( Text( info->version ) );
+				dateiT->setZeichnungZ( 1, i + 1, version );
+				TextFeld *status = new TextFeld();
+				status->setStyle( TextFeld::Style::Sichtbar | TextFeld::Style::Rahmen | TextFeld::Style::Center );
+				status->setSchriftZ( schrift->getThis() );
+				status->setSchriftSize( 12 );
+				status->setLinienRahmenFarbe( 0xFFFFFFFF );
+				status->setText( "Aktuell" );
+				status->setSchriftFarbe( 0xFF00FF00 );
+				Text *pf = new Text( systemInit->zWert( sName->getText() )->getText() );
+				if( pf->getText()[ pf->getLength() - 1 ] != '/' )
+					pf->append( "/" );
+				pf->append( (char*)info->path );
+				if( !DateiExistiert( pf->getThis() ) )
+				{
+					status->setText( "Gelöscht" );
+					status->setSchriftFarbe( 0xFFFF0000 );
+				}
+				else
+				{
+					Datei *d = new Datei();
+					d->setDatei( pf->getText() );
+					if( !d->istOrdner() )
+					{
+						Zeit *lä = d->getLastChange();
+						if( !lä->istGleich( "y-m-d h:i:s", info->time ) )
+						{
+							status->setText( "Veraltet" );
+							status->setSchriftFarbe( 0xFFFFFF00 );
+						}
+						lä->release();
+					}
+					d->release();
+				}
+				pf->release();
+				dateiT->setZeichnungZ( 2, i + 1, status );
+			}
+			sucheDateien( systemInit->zWert( sName->getText() )->getText(), list );
+		}
+	}
+	return 1;
+}
+
+bool Version::zurückMausEreignis( void *o, MausEreignis me )
+{
+	if( me.id == ME_RLinks )
+	{
+		if( fehlerF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			fehlerF->removeStyle( Fenster::Style::Sichtbar );
+			dateiF->removeStyle( Fenster::Style::Sichtbar );
+			systemF->removeStyle( Fenster::Style::Sichtbar );
+			zurück->removeStyle( Knopf::Style::Erlaubt );
+			speichern->removeStyle( Knopf::Style::Erlaubt );
+			weiter->removeStyle( Knopf::Style::Erlaubt );
+			aktualisieren->addStyle( Knopf::Style::Erlaubt );
+			gruppeF->addStyle( Fenster::Style::Sichtbar );
+			aktualisierenMausEreignis( 0, me );
+		}
+		else if( dateiF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			fehlerF->removeStyle( Fenster::Style::Sichtbar );
+			dateiF->removeStyle( Fenster::Style::Sichtbar );
+			gruppeF->removeStyle( Fenster::Style::Sichtbar );
+			weiter->removeStyle( Knopf::Style::Erlaubt );
+			zurück->addStyle( Knopf::Style::Erlaubt );
+			speichern->addStyle( Knopf::Style::Erlaubt );
+			aktualisieren->addStyle( Knopf::Style::Erlaubt );
+			systemF->addStyle( Fenster::Style::Sichtbar );
+			aktualisierenMausEreignis( 0, me );
+		}
+		else if( systemF->hatStyle( Fenster::Style::Sichtbar ) )
+		{
+			fehlerF->removeStyle( Fenster::Style::Sichtbar );
+			dateiF->removeStyle( Fenster::Style::Sichtbar );
+			systemF->removeStyle( Fenster::Style::Sichtbar );
+			zurück->removeStyle( Knopf::Style::Erlaubt );
+			speichern->removeStyle( Knopf::Style::Erlaubt );
+			weiter->removeStyle( Knopf::Style::Erlaubt );
+			aktualisieren->addStyle( Knopf::Style::Erlaubt );
+			gruppeF->addStyle( Fenster::Style::Sichtbar );
+			aktualisierenMausEreignis( 0, me );
+		}
+	}
+	return 1;
+}
+
+// constant
+InitDatei *Version::getSystemInit() const
+{
+	return systemInit->getThis();
+}
+
+// Reference Counting
+Abschnitt *Version::getThis()
+{
+	ref++;
+	return this;
+}
+
+Abschnitt *Version::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}
+
+
+// Ereignisse
+bool versionNeuGruppeKMausEreignis( void *p, void *o, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Version*)p )->neuGruppeKMausEreignis( o, me );
+}
+
+bool versionAuswahlKnopfMausEreignis( void *p, void *o, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Version*)p )->auswahlKnopfMausEreignis( o, me );
+}
+
+bool versionNeuSystemKMausEreignis( void *p, void *o, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Version*)p )->neuSystemKMausEreignis( o, me );
+}
+
+bool versionSpeichernMausEreignis( void *p, void *o, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Version*)p )->speichernMausEreignis( o, me );
+}
+
+bool versionWeiterMausEreignis( void *p, void *o, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Version*)p )->weiterMausEreignis( o, me );
+}
+
+bool versionCommitMausEreignis( void *p, void *o, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Version*)p )->commitMausEreignis( o, me );
+}
+
+bool versionAktualisierenMausEreignis( void *p, void *o, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Version*)p )->aktualisierenMausEreignis( o, me );
+}
+
+bool versionZurückMausEreignis( void *p, void *o, MausEreignis me )
+{
+	if( !p )
+		return 0;
+	return ( (Version*)p )->zurückMausEreignis( o, me );
+}

+ 81 - 0
SMP/Programm/Version/Version.h

@@ -0,0 +1,81 @@
+#ifndef Version_H
+#define Version_H
+
+#include "..\Basic\Abschnitt.h"
+#include "..\..\Netzwerk\Main\MSKlient.h"
+#include "..\..\Netzwerk\Patch\PSKlient.h"
+#include "..\..\Ressourcen\Ressourcen.h"
+#include "..\Login\Login.h"
+#include <TextFeld.h>
+#include <AuswahlBox.h>
+#include <Tabelle.h>
+
+class Version : public Abschnitt
+{
+private:
+	Fenster *fenster;
+	Fenster *f;
+	AdminAccount *account;
+    MSKlient *msc;
+    PSKlient *psc;
+	Fenster *gruppeF; // Gruppen Fenster
+	ObjTabelle *gruppeT; // Tabelle mit Gruppen
+	TextFeld *neuGruppeName; // Neue Gruppe erstellen Name Textfeld
+	TextFeld *neuGruppePfad; // Neue Gruppe erstellen Pfad Textfeld
+	Knopf *neuGruppeK; // neue Gruppe erstellen Knopf
+	Fenster *systemF; // System Fenster
+	InitDatei *systemInit; // Pfad zu den Systemen
+	ObjTabelle *systemT; // Tabelle mit Systemen
+	TextFeld *neuSystemName; // Neues System erstellen Name Textfeld
+	Knopf *neuSystemK; // neues System erstellen Knopf
+	Knopf *speichern; // Pfade zu den Systemen speichern
+	Knopf *weiter;
+	Fenster *dateiF; // Datei Fenster
+	ObjTabelle *dateiT; // Tabelle mit Dateien
+	Knopf *commit; // update Knopf
+	Knopf *aktualisieren;
+	Fenster *fehlerF;
+	TextFeld *fehlerText;
+	Knopf *zurück;
+	Schrift *schrift;
+	Text *sName;
+	int system;
+	int gruppe;
+	int ref;
+
+	void sucheDateien( const char *pfad, RCArray< ReferenceCounting< FileInfo > > &list );
+
+public:
+	// Konstruktor
+	Version( Schrift *s, MSKlient *msc, RessourceBild *rb, AdminAccount *acc, Bildschirm *b );
+	// Destruktor
+	~Version();
+	// nicht constant
+	virtual void setFenster( Fenster *f );
+	virtual void setSichtbar( bool s );
+	bool neuGruppeKMausEreignis( void *o, MausEreignis me );
+	bool auswahlKnopfMausEreignis( void *o, MausEreignis me );
+	bool neuSystemKMausEreignis( void *o, MausEreignis me );
+	bool speichernMausEreignis( void *o, MausEreignis me );
+	bool weiterMausEreignis( void *o, MausEreignis me );
+	bool commitMausEreignis( void *o, MausEreignis me );
+	bool aktualisierenMausEreignis( void *o, MausEreignis me );
+	bool zurückMausEreignis( void *o, MausEreignis me );
+	// constant
+	InitDatei *getSystemInit() const;
+	// Reference Counting
+	virtual Abschnitt *getThis();
+	virtual Abschnitt *release();
+};
+
+// Ereignisse
+bool versionNeuGruppeKMausEreignis( void *p, void *o, MausEreignis me );
+bool versionAuswahlKnopfMausEreignis( void *p, void *o, MausEreignis me );
+bool versionNeuSystemKMausEreignis( void *p, void *o, MausEreignis me );
+bool versionSpeichernMausEreignis( void *p, void *o, MausEreignis me );
+bool versionWeiterMausEreignis( void *p, void *o, MausEreignis me );
+bool versionCommitMausEreignis( void *p, void *o, MausEreignis me );
+bool versionAktualisierenMausEreignis( void *p, void *o, MausEreignis me );
+bool versionZurückMausEreignis( void *p, void *o, MausEreignis me );
+
+#endif

+ 60 - 0
SMP/Render/Render.cpp

@@ -0,0 +1,60 @@
+#include "Render.h"
+#include <Zeit.h>
+
+// Inhalt der Render Klasse aus Render.h
+// Konstruktor
+Render::Render( Bildschirm *b )
+{
+	bildschirm = b;
+	beendet = 0;
+	ref = 1;
+}
+
+// Destruktor
+Render::~Render()
+{
+	beenden( );
+	bildschirm->release();
+}
+
+// nicht constant
+void Render::thread()
+{
+	ZeitMesser *timer = new ZeitMesser();
+	while( !beendet )
+	{
+		double tickVal = timer->getSekunden();
+		timer->messungStart();
+		bildschirm->tick( tickVal );
+		bildschirm->render();
+		if( tickVal < 1.0 / 30.0 )
+			Sleep( (int)( ( 1.0 / 30.0 - tickVal ) * 1000 ) );
+		timer->messungEnde();
+	}
+	timer->release();
+	beendet = 0;
+	run = 0;
+}
+
+void Render::beenden()
+{
+	beendet = 1;
+	warteAufThread( 1000 );
+}
+
+// constant
+
+// Reference Counting
+Render *Render::getThis()
+{
+	ref++;
+	return this;
+}
+
+Render *Render::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}

+ 31 - 0
SMP/Render/Render.h

@@ -0,0 +1,31 @@
+#ifndef Render_H
+#define Render_H
+
+#include <Thread.h>
+#include <Bildschirm.h>
+
+using namespace Framework;
+
+class Render : public Thread
+{
+private:
+	Bildschirm *bildschirm;
+	bool beendet;
+	int ref;
+
+public:
+	// Konstruktor
+	Render( Bildschirm *b );
+	// Destruktor
+	~Render();
+	// nicht constant
+	virtual void thread();
+	void beenden();
+	// constant
+
+	// Reference Counting
+	Render *getThis();
+	Render *release();
+};
+
+#endif

+ 276 - 0
SMP/Ressourcen/Ressourcen.cpp

@@ -0,0 +1,276 @@
+#include "Ressourcen.h"
+
+// Inhalt der RessourceBild Klasse aus Ressource.h
+// Konstruktor
+RessourceBild::RessourceBild()
+{
+	name = new RCArray< Text >();
+	bild = new RCArray< Bild >();
+	anzahl = 0;
+	ref = 1;
+}
+
+// Destruktor
+RessourceBild::~RessourceBild()
+{
+	name->release();
+	bild->release();
+}
+
+// nicht constant
+bool RessourceBild::add( Text *name, Bild *bild )
+{
+	bool ret = add( name->getText(), bild );
+	name->release();
+	return ret;
+}
+
+bool RessourceBild::add( const char *name, Bild *bild )
+{
+	if( hat( name ) )
+	{
+		bild->release();
+		return 0;
+	}
+	this->name->add( new Text( name ), anzahl );
+	this->bild->add( bild, anzahl );
+	anzahl++;
+	return 1;
+}
+
+bool RessourceBild::remove( Text *name )
+{
+	bool ret = remove( name->getText() );
+	name->release();
+	return ret;
+}
+
+bool RessourceBild::remove( const char *name )
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+		{
+			this->name->remove( i );
+			bild->remove( i );
+			anzahl--;
+			return 1;
+		}
+	}
+	return 0;
+}
+
+void RessourceBild::reset()
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		name->remove( 0 );
+		bild->remove( 0 );
+	}
+	anzahl = 0;
+}
+
+// constant
+bool RessourceBild::hat( Text *name )
+{
+	bool ret = hat( name->getText() );
+	name->release();
+	return ret;
+}
+
+bool RessourceBild::hat( const char *name )
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+			return 1;
+	}
+	return 0;
+}
+
+Bild *RessourceBild::get( Text *name )
+{
+	Bild *ret = get( name->getText() );
+	name->release();
+	return ret;
+}
+
+Bild *RessourceBild::get( const char *name )
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+			return this->bild->get( i );
+	}
+	return 0;
+}
+
+Bild *RessourceBild::z( Text *name )
+{
+	Bild *ret = z( name->getText() );
+	name->release();
+	return ret;
+}
+
+Bild *RessourceBild::z( const char *name )
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+			return this->bild->z( i );
+	}
+	return 0;
+}
+
+// Reference Counting
+RessourceBild *RessourceBild::getThis()
+{
+	ref++;
+	return this;
+}
+
+RessourceBild *RessourceBild::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}
+
+
+// Inhalt der RessourceSchrift Klasse aus Ressource.h
+// Konstruktor
+RessourceSchrift::RessourceSchrift()
+{
+	name = new RCArray< Text >();
+	schrift = new RCArray< Schrift >();
+	anzahl = 0;
+	ref = 1;
+}
+
+// Destruktor
+RessourceSchrift::~RessourceSchrift()
+{
+	name->release();
+	schrift->release();
+}
+
+// nicht constant
+bool RessourceSchrift::add( Text *name, Schrift *schrift )
+{
+	bool ret = add( name->getText(), schrift );
+	name->release();
+	return ret;
+}
+
+bool RessourceSchrift::add( const char *name, Schrift *schrift )
+{
+	if( hat( name ) )
+	{
+		schrift->release();
+		return 0;
+	}
+	this->name->add( new Text( name ), anzahl );
+	this->schrift->add( schrift, anzahl );
+	anzahl++;
+	return 1;
+}
+
+bool RessourceSchrift::remove( Text *name )
+{
+	bool ret = remove( name->getText() );
+	name->release();
+	return ret;
+}
+
+bool RessourceSchrift::remove( const char *name )
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+		{
+			this->name->remove( i );
+			schrift->remove( i );
+			anzahl--;
+			return 1;
+		}
+	}
+	return 0;
+}
+
+void RessourceSchrift::reset()
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		name->remove( 0 );
+		schrift->remove( 0 );
+	}
+	anzahl = 0;
+}
+
+// constant
+bool RessourceSchrift::hat( Text *name )
+{
+	bool ret = hat( name->getText() );
+	name->release();
+	return ret;
+}
+
+bool RessourceSchrift::hat( const char *name )
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+			return 1;
+	}
+	return 0;
+}
+
+Schrift *RessourceSchrift::get( Text *name )
+{
+	Schrift *ret = get( name->getText() );
+	name->release();
+	return ret;
+}
+
+Schrift *RessourceSchrift::get( const char *name )
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+			return this->schrift->get( i );
+	}
+	return 0;
+}
+
+Schrift *RessourceSchrift::z( Text *name )
+{
+	Schrift *ret = z( name->getText() );
+	name->release();
+	return ret;
+}
+
+Schrift *RessourceSchrift::z( const char *name )
+{
+	for( int i = 0; i < anzahl; i++ )
+	{
+		if( this->name->z( i )->istGleich( name ) )
+			return this->schrift->z( i );
+	}
+	return 0;
+}
+
+// Reference Counting
+RessourceSchrift *RessourceSchrift::getThis()
+{
+	ref++;
+	return this;
+}
+
+RessourceSchrift *RessourceSchrift::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}

+ 73 - 0
SMP/Ressourcen/Ressourcen.h

@@ -0,0 +1,73 @@
+#ifndef Ressourcen_H
+#define Ressourcen_H
+
+#include <Array.h>
+#include <Bild.h>
+#include <Schrift.h>
+#include <Text.h>
+
+using namespace Framework;
+
+class RessourceBild
+{
+private:
+	RCArray< Text > *name;
+	RCArray< Bild > *bild;
+	int anzahl;
+	int ref;
+
+public:
+	// Konstruktor
+	RessourceBild();
+	// Destruktor
+	~RessourceBild();
+	// nicht constant
+	bool add( Text *name, Bild *bild );
+	bool add( const char *name, Bild *bild );
+	bool remove( Text *name );
+	bool remove( const char *name );
+	void reset();
+	// constant
+	bool hat( Text *name );
+	bool hat( const char *name );
+	Bild *get( Text *name );
+	Bild *get( const char *name );
+	Bild *z( Text *name );
+	Bild *z( const char *name );
+	// Reference Counting
+	RessourceBild *getThis();
+	RessourceBild *release();
+};
+
+class RessourceSchrift
+{
+private:
+	RCArray< Text > *name;
+	RCArray< Schrift > *schrift;
+	int anzahl;
+	int ref;
+
+public:
+	// Konstruktor
+	RessourceSchrift();
+	// Destruktor
+	~RessourceSchrift();
+	// nicht constant
+	bool add( Text *name, Schrift *schrift );
+	bool add( const char *name, Schrift *schrift );
+	bool remove( Text *name );
+	bool remove( const char *name );
+	void reset();
+	// constant
+	bool hat( Text *name );
+	bool hat( const char *name );
+	Schrift *get( Text *name );
+	Schrift *get( const char *name );
+	Schrift *z( Text *name );
+	Schrift *z( const char *name );
+	// Reference Counting
+	RessourceSchrift *getThis();
+	RessourceSchrift *release();
+};
+
+#endif

+ 197 - 0
SMP/SMP.vcxproj

@@ -0,0 +1,197 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{F008ED76-C8D3-4D0E-9032-ACB9FF9FB701}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>SMP</RootNamespace>
+    <ProjectName>SMP</ProjectName>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <PlatformToolset>v141</PlatformToolset>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <PlatformToolset>v141</PlatformToolset>
+    <CharacterSet>MultiByte</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <PlatformToolset>v141</PlatformToolset>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>MultiByte</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <PlatformToolset>v141</PlatformToolset>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>MultiByte</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <IncludePath>..\..\..\Allgemein\Framework;..\..\..\Allgemein\Network\Network;$(IncludePath)</IncludePath>
+    <LibraryPath>..\..\..\Allgemein\Framework\x64\Debug;..\..\..\Allgemein\Network\x64\Debug;$(LibraryPath)</LibraryPath>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+    <IncludePath>..\..\..\Allgemein\Framework;..\..\..\Allgemein\Network\Network;..\..\..\Allgemein\sql\sql;$(IncludePath)</IncludePath>
+    <LibraryPath>..\..\..\Allgemein\Framework\Release;..\..\..\Allgemein\Network\Release;..\..\..\Allgemein\sql\Release;$(LibraryPath)</LibraryPath>
+    <CustomBuildBeforeTargets>Build</CustomBuildBeforeTargets>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+    <IncludePath>..\..\..\Allgemein\Framework;..\..\..\Allgemein\Network\Network;..\..\..\Allgemein\sql\sql;$(IncludePath)</IncludePath>
+    <LibraryPath>..\..\..\Allgemein\Framework\x64\Release;..\..\..\Allgemein\Network\x64\Release;..\..\..\Allgemein\sql\x64\Release;$(LibraryPath)</LibraryPath>
+    <CustomBuildBeforeTargets>Build</CustomBuildBeforeTargets>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+    </ClCompile>
+    <Link>
+      <SubSystem>Windows</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Windows</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <AdditionalDependencies>framework.lib;network.lib;%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+    </ClCompile>
+    <Link>
+      <SubSystem>Windows</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+      <AdditionalDependencies>framework.lib;network.lib;sql.lib;%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+    <CustomBuildStep>
+      <Command>copy "..\Release\SMP.exe" "..\Fertig\x32\smp.exe"</Command>
+    </CustomBuildStep>
+    <CustomBuildStep>
+      <Outputs>Kopieren...;%(Outputs)</Outputs>
+    </CustomBuildStep>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+    </ClCompile>
+    <Link>
+      <SubSystem>Windows</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+      <AdditionalDependencies>framework.lib;network.lib;sql.lib;%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+    <CustomBuildStep>
+      <Command>copy "..\x64\Release\SMP.exe" "..\Fertig\x64\smp.exe"</Command>
+    </CustomBuildStep>
+    <CustomBuildStep>
+      <Outputs>Kopieren...;%(Outputs)</Outputs>
+    </CustomBuildStep>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="Netzwerk\LTSKlient.cpp" />
+    <ClCompile Include="Netzwerk\Main\MSKlient.cpp" />
+    <ClCompile Include="Netzwerk\Patch\PSKlient.cpp" />
+    <ClCompile Include="Programm\Basic\Abschnitt.cpp" />
+    <ClCompile Include="Programm\Beenden\Beenden.cpp" />
+    <ClCompile Include="Programm\Login\Login.cpp" />
+    <ClCompile Include="Programm\Programm.cpp" />
+    <ClCompile Include="Programm\Server\Patch\PatchServer.cpp" />
+    <ClCompile Include="Programm\Version\Version.cpp" />
+    <ClCompile Include="Render\Render.cpp" />
+    <ClCompile Include="Ressourcen\Ressourcen.cpp" />
+    <ClCompile Include="Start\Start.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="Netzwerk\Main\MSKlient.h" />
+    <ClInclude Include="Netzwerk\Patch\PSKlient.h" />
+    <ClInclude Include="Netzwerk\LTSKlient.h" />
+    <ClInclude Include="Programm\Basic\Abschnitt.h" />
+    <ClInclude Include="Programm\Beenden\Beenden.h" />
+    <ClInclude Include="Programm\Login\Login.h" />
+    <ClInclude Include="Programm\Programm.h" />
+    <ClInclude Include="Programm\Server\Patch\PatchServer.h" />
+    <ClInclude Include="Programm\Version\Version.h" />
+    <ClInclude Include="Render\Render.h" />
+    <ClInclude Include="Ressourcen\Ressourcen.h" />
+    <ClInclude Include="Start\Start.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>

+ 93 - 0
SMP/SMP.vcxproj.filters

@@ -0,0 +1,93 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Quelldateien">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Headerdateien">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hh;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Ressourcendateien">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="Start\Start.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Ressourcen\Ressourcen.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Render\Render.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Programm\Programm.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Programm\Basic\Abschnitt.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Programm\Beenden\Beenden.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Programm\Login\Login.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Programm\Server\Patch\PatchServer.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Programm\Version\Version.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Netzwerk\Main\MSKlient.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Netzwerk\Patch\PSKlient.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+    <ClCompile Include="Netzwerk\LTSKlient.cpp">
+      <Filter>Quelldateien</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="Start\Start.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Ressourcen\Ressourcen.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Render\Render.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Programm\Programm.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Programm\Basic\Abschnitt.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Programm\Beenden\Beenden.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Programm\Login\Login.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Programm\Server\Patch\PatchServer.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Programm\Version\Version.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Netzwerk\LTSKlient.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Netzwerk\Main\MSKlient.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+    <ClInclude Include="Netzwerk\Patch\PSKlient.h">
+      <Filter>Headerdateien</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>

+ 268 - 0
SMP/Start/Start.cpp

@@ -0,0 +1,268 @@
+#include <Network.h>
+#include <main.h>
+#include "Start.h"
+#include <Punkt.h>
+#include <MausEreignis.h>
+#include <Bildschirm.h>
+#include <DateiSystem.h>
+#include <Text.h>
+#include <TextFeld.h>
+#include <Bild.h>
+#include <InitDatei.h>
+#include <Datei.h>
+#include "..\Render\Render.h"
+#include "..\Programm\Programm.h"
+#include "..\Programm\Beenden\Beenden.h"
+#include "..\Programm\Login\Login.h"
+
+// Laden Fenster Ereignis
+bool lFMausEreignis( void *p, void *f, MausEreignis me )
+{
+	return 1;
+}
+
+void lFVorSchließEreignis( void *p, void *f )
+{
+	// Fenster nicht close
+}
+
+// Haupt Fenster Maus Ereignis
+bool hFMausEreignis( void *p, void *f, MausEreignis me )
+{
+	return 1;
+}
+
+bool hFTastaturEreignis( void *p, void *f, TastaturEreignis me )
+{
+	return 1;
+}
+
+void hFVorSchließEreignis( void *p, void *f )
+{
+	// Programm beenden
+	PostQuitMessage( 0 );
+}
+
+// Inhalt der LedeBildschirm Klasse aus Start.h
+// Konstruktor
+LadeBildschirm::LadeBildschirm( Schrift *s, InitDatei *d, WFenster *f )
+: Thread()
+{
+	bilder = new RessourceBild();
+	schriften = new RessourceSchrift();
+	schrift = s;
+	iD = d;
+	lF = f;
+	ref = 1;
+	start();
+}
+
+// Destruktor
+LadeBildschirm::~LadeBildschirm()
+{
+	schrift->release();
+	iD->release();
+	lF->release();
+	bilder->release();
+	schriften->release();
+}
+
+// nicht constant
+void LadeBildschirm::thread()
+{
+	// Fenster ertellen;
+	lF->setVerschiebbar( 1 );
+	lF->setSize( 300, 150 );
+	lF->setPosition( Bildschirmmitte( lF->getThis() ) );
+	lF->setMausAktion( lFMausEreignis );
+	lF->setVSchließAktion( lFVorSchließEreignis );
+	Bildschirm *lB = new Bildschirm3D( lF->getThis() );
+	lF->setBildschirm( lB->getThis() );
+	lB->setdeckFarbe( 0x00000000 );
+	lB->setRenderZeichnungen( 1 );
+	lB->update();
+	lF->setAnzeigeModus( 1 );
+	lB->render();
+	lB->tick( 0 );
+	// Tetfeld erstellen
+	TextFeld *lTF = new TextFeld();
+	lTF->setStyle( TextFeld::Style::Hintergrund | TextFeld::Style::HAlpha | TextFeld::Style::Sichtbar || TextFeld::Style::VCenter || TextFeld::Style::Rahmen );
+	lTF->setSchriftZ( schrift->getThis() );
+	lTF->setText( "Initialisierung..." );
+	lTF->setSize( 300, 20 );
+	lTF->setPosition( 0, 130 );
+	lTF->setHintergrundFarbe( 0x88000000 );
+	lTF->setSchriftFarbe( 0xFFFFFFFF );
+	lTF->setLinienRahmenFarbe( 0xFF808080 );
+	lB->addMember( lTF );
+	lB->render();
+	lB->tick( 0 );
+	// Hintergrund laden
+	LTDBDatei *bD = new LTDBDatei();
+	bD->setDatei( iD->getWert( "LadenHintergrundDatei" ) );
+	bD->leseDaten( 0 );
+	BildZ *lBgB = new BildZ();
+	lBgB->setStyle( BildZ::Style::Sichtbar );
+	lBgB->setBildZ( bD->laden( 0, iD->getWert( "LadenHintergrundBild" ) ) );
+	lBgB->setSize( 300, 150 );
+	bD->release();
+	// rendern
+	lB->removeMember( lTF );
+	lB->addMember( lBgB );
+	lB->addMember( lTF );
+	lB->render();
+	lB->tick( 0 );
+	// laden
+	InitDatei *lBD = new InitDatei( iD->zWert( "LadeBilder" )->getText() );
+	lBD->laden();
+	int anz = lBD->getWertAnzahl();
+	for( int i = 0; i < anz; i++ )
+	{
+		lTF->setText( lBD->zWert( i )->getText() );
+		lB->render();
+		lB->tick( 0 );
+		Text *w = lBD->zWert( i );
+		LTDBDatei *ltdb = new LTDBDatei();
+		ltdb->setDatei( w->getTeilText( 0, w->positionVon( '/', w->anzahlVon( '/' ) - 1 ) ) );
+		ltdb->leseDaten( 0 );
+		bilder->add( lBD->zName( i )->getText(), ltdb->laden( 0, w->getTeilText( w->positionVon( '/', w->anzahlVon( '/' ) - 1 ) + 1 ) ) );
+		ltdb->release();
+	}
+	lBD->release();
+	InitDatei *lSD = new InitDatei( iD->zWert( "LadeSchriften" )->getText() );
+	lSD->laden();
+	anz = lSD->getWertAnzahl();
+	for( int i = 0; i < anz; i++ )
+	{
+		lTF->setText( lSD->zWert( i )->getText() );
+		lB->render();
+		lB->tick( 0 );
+		Text *w = lSD->zWert( i );
+		LTDSDatei *ltds = new LTDSDatei();
+		ltds->setPfad( lSD->getWert( i ) );
+		ltds->leseDaten();
+		schriften->add( lSD->zName( i )->getText(), ltds->ladeSchrift() );
+		ltds->release();
+	}
+	lSD->release();
+	// Speicher freigeben
+	lB->removeMember( lBgB );
+	lB->removeMember( lTF );
+	lBgB->release();
+	lTF->release();
+	lF->setAnzeigeModus( 0 );
+	StopNachrichtenSchleife( lF->getFensterHandle() );
+	lF->zerstören();
+	lF->setBildschirm( 0 );
+	lB->release();
+}
+
+// constant
+RessourceBild *LadeBildschirm::getBilder()
+{
+	return bilder->getThis();
+}
+
+RessourceSchrift *LadeBildschirm::getSchriften()
+{
+	return schriften->getThis();
+}
+
+// reference Counting
+LadeBildschirm *LadeBildschirm::getThis()
+{
+	ref++;
+	return this;
+}
+
+LadeBildschirm *LadeBildschirm::release()
+{
+	ref--;
+	if( !ref )
+		delete this;
+	return 0;
+}
+
+// Start des Programms
+int KSGStart Framework::Start( Startparam p )
+{
+	Network::Start( 20 );
+	// Erstellen eines Fensters
+	WNDCLASS wc = F_Normal( p.hinst );
+	wc.lpszClassName = "SMP";
+	WFenster *lF = new WFenster();
+	lF->erstellen( WS_POPUP, wc );
+	// Laden von Schrift und Optionen
+	InitDatei *iD = new InitDatei( "data/start/optionen.ini" );
+	iD->laden();
+	LTDSDatei *sD = new LTDSDatei();
+	sD->setPfad( iD->getWert( "LadenSchriftDatei" ) );
+	sD->leseDaten();
+	Schrift *schrift = sD->ladeSchrift();
+	sD->release();
+	// Laden anderer Dateien
+	LadeBildschirm *lb = new LadeBildschirm( schrift, iD->getThis(), lF );
+	StartNachrichtenSchleife();
+	lb->warteAufThread( 1000 );
+	// Fortsetzung nach laden
+	RessourceBild *bilder = lb->getBilder();
+	RessourceSchrift *schriften = lb->getSchriften();
+    lF->zerstören();
+	lb->release();
+	// Haupt Fenster erstellen
+	if( !iD->wertExistiert( "DisplayMonitor" ) )
+		iD->addWert( "DisplayMonitor", "0" );
+	int monitorId = TextZuInt( iD->zWert( "DisplayMonitor" )->getText(), 10 );
+	Monitor mon = getMonitor( monitorId );
+	if( !mon.existiert )
+		mon = getMonitor( 0 );
+	WFenster *hF = new WFenster();
+	hF->erstellen( WS_POPUP, wc );
+	hF->setPosition( Punkt( mon.x, mon.y ) );
+	hF->setSize( mon.breite, mon.height );
+	hF->setMausAktion( hFMausEreignis );
+	hF->setTastaturAktion( hFTastaturEreignis );
+	hF->setVSchließAktion( hFVorSchließEreignis );
+	Bildschirm *hB = new Bildschirm2D( hF->getThis() );
+	hF->setBildschirm( hB->getThis() );
+	hB->setdeckFarbe( 0x00000000 );
+	hB->setRenderZeichnungen( 1 );
+    hB->setTestRend( 0 );
+	hB->update();
+	hF->setAnzeigeModus( 1 );
+	hB->render();
+	hB->tick( 0 );
+
+	Programm *prog = new Programm( hB->getThis(), schriften->get( iD->zWert( "Schrift" )->getText() ) );
+
+	// Renderer erstellen
+	Render *r = new Render( hB->getThis() );
+	// Beenden Abschnitt Erstellen
+	Beenden *beenden = new Beenden( schriften->get( iD->zWert( "Schrift" )->getText() ), hB->getThis() );
+	prog->addAbschnitt( "Beenden", beenden );
+	// Mit Datenbank verbinden
+	// Login Abschnitt erstellen
+	Login *login = new Login( schriften->get( iD->zWert( "Schrift" )->getText() ), prog, iD->getThis(), bilder->getThis(), hB->getThis() );
+	prog->addAbschnitt( "Login", login );
+	prog->abschnittAuswählen( "Login" );
+	// Nachrichten verarbeiten
+	r->start();
+	StartNachrichtenSchleife();
+	r->beenden();
+
+	// Speicher freigeben
+	prog->release();
+
+	r->release();
+	hB->release();
+	hF->setBildschirm( 0 );
+	hF->release();
+
+	bilder->release();
+	schriften->release();
+	iD->release();
+
+	Network::Exit();
+
+	return 0;
+}

+ 37 - 0
SMP/Start/Start.h

@@ -0,0 +1,37 @@
+#ifndef Start_H
+#define Start_H
+
+#include <Schrift.h>
+#include <Thread.h>
+#include <InitDatei.h>
+#include <Fenster.h>
+#include "../Ressourcen/Ressourcen.h"
+
+using namespace Framework;
+
+class LadeBildschirm : public Thread
+{
+private:
+	Schrift *schrift;
+	InitDatei *iD;
+	WFenster *lF;
+	RessourceBild *bilder;
+	RessourceSchrift *schriften;
+	int ref;
+
+public:
+	// Konstruktor
+	LadeBildschirm( Schrift *s, InitDatei *d, WFenster *f );
+	// Destruktor
+	~LadeBildschirm();
+	// nicht constant
+	virtual void thread();
+	// constant
+	RessourceBild *getBilder();
+	RessourceSchrift *getSchriften();
+	// reference Counting
+	LadeBildschirm *getThis();
+	LadeBildschirm *release();
+};
+
+#endif

+ 2 - 0
SMP/data/Client.ini

@@ -0,0 +1,2 @@
+WIN32=../../Klient/Fertig/x32
+WIN64=../../Klient/Fertig/Debug/x64

+ 2 - 0
SMP/data/Minigames.ini

@@ -0,0 +1,2 @@
+WIN32=../../Klient/Fertig/Minigames/x32
+WIN64=../../Klient/Fertig/Debug/Minigames/x64

+ 2 - 0
SMP/data/Spiel_Asteroids.ini

@@ -0,0 +1,2 @@
+WIN32=../../Klient/Fertig/Spiele/x32/Asteroids
+WIN64=../../Klient/Fertig/Debug/Spiele/x64/Asteroids

+ 2 - 0
SMP/data/Spiel_Linie.ini

@@ -0,0 +1,2 @@
+WIN32=../../Klient/Fertig/Spiele/x32/Linie
+WIN64=../../Klient/Fertig/Debug/Spiele/x64/Linie

+ 2 - 0
SMP/data/Spiel_Stickman World Online.ini

@@ -0,0 +1,2 @@
+WIN32=../../Klient/Fertig/Spiele/x32/Stickman World Online
+WIN64=../../Klient/Fertig/Debug/Spiele/x64/Stickman World Online

二進制
SMP/data/bilder/icons.ltdb


二進制
SMP/data/bilder/startbg.ltdb


二進制
SMP/data/schrift/normal.ltds


+ 5 - 0
SMP/data/start/ladebilder.ini

@@ -0,0 +1,5 @@
+neuladen.png=data/bilder/icons.ltdb/neuladen.png
+weiter.png=data/bilder/icons.ltdb/weiter.png
+zurück.png=data/bilder/icons.ltdb/zurück.png
+speichern.png=data/bilder/icons.ltdb/speichern.png
+neu.png=data/bilder/icons.ltdb/neu.png

+ 1 - 0
SMP/data/start/ladeschriften.ini

@@ -0,0 +1 @@
+normal=data/schrift/normal.ltds

+ 14 - 0
SMP/data/start/optionen Test.ini

@@ -0,0 +1,14 @@
+DisplayMonitor=0
+LadenSchriftDatei=data/schrift/normal.ltds
+Schrift=normal
+LadenHintergrundDatei=data/bilder/startbg.ltdb
+LadenHintergrundBild=bg.png
+LadeBilder=data/start/ladebilder.ini
+LadeSchriften=data/start/ladeschriften.ini
+DBBenutzer=smpuser
+DBPasswort=SMPUserP
+DBDatenbank=testdb
+DBIP=88.198.205.67
+DBPort=5254
+MainServerIP=88.198.205.67
+MainServerPort=5252

+ 14 - 0
SMP/data/start/optionen.ini

@@ -0,0 +1,14 @@
+DisplayMonitor=1
+LadenSchriftDatei=data/schrift/normal.ltds
+Schrift=normal
+LadenHintergrundDatei=data/bilder/startbg.ltdb
+LadenHintergrundBild=bg.png
+LadeBilder=data/start/ladebilder.ini
+LadeSchriften=data/start/ladeschriften.ini
+DBBenutzer=smpuser
+DBPasswort=SMPUserP
+DBDatenbank=testdb
+DBIP=94.130.27.12
+DBPort=5254
+MainServerIP=94.130.27.12
+MainServerPort=5252

+ 14 - 0
SMP/data/start/optionen1.ini

@@ -0,0 +1,14 @@
+DisplayMonitor=0
+LadenSchriftDatei=data/schrift/normal.ltds
+Schrift=normal
+LadenHintergrundDatei=data/bilder/startbg.ltdb
+LadenHintergrundBild=bg.png
+LadeBilder=data/start/ladebilder.ini
+LadeSchriften=data/start/ladeschriften.ini
+DBBenutzer=smpuser
+DBPasswort=SMPUserP
+DBDatenbank=koljadb
+DBIP=88.198.205.67
+DBPort=4254
+MainServerIP=88.198.205.67
+MainServerPort=4252

+ 14 - 0
SMP/data/start/optionen2.ini

@@ -0,0 +1,14 @@
+DisplayMonitor=0
+LadenSchriftDatei=data/schrift/normal.ltds
+Schrift=normal
+LadenHintergrundDatei=data/bilder/startbg.ltdb
+LadenHintergrundBild=bg.png
+LadeBilder=data/start/ladebilder.ini
+LadeSchriften=data/start/ladeschriften.ini
+DBBenutzer=smpuser
+DBPasswort=SMPUserP
+DBDatenbank=koljadb
+DBIP=127.0.0.1
+DBPort=49134
+MainServerIP=127.0.0.1
+MainServerPort=4252

二進制
SMP/framework.dll


二進制
SMP/network.dll


二進制
SMP/sql.dll


二進制
SMP/vx32/data/bilder/game.ltdb


二進制
SMP/vx32/data/bilder/system.ltdb


二進制
SMP/vx32/data/client/bilder/chat.ltdb


二進制
SMP/vx32/data/client/bilder/ladeanimation.ltdb


二進制
SMP/vx32/data/client/bilder/spielen.ltdb


二進制
SMP/vx32/data/client/bilder/titel.ltdb


+ 2 - 0
SMP/vx32/data/optionen.ini

@@ -0,0 +1,2 @@
+ServerIP=127.0.0.1
+ServerPort=4253

二進制
SMP/vx32/data/patch/bilder/news.ltdb


二進制
SMP/vx32/data/patch/bilder/patcher.ltdb


+ 4 - 0
SMP/vx32/data/patch/news/Willkommen/data.new

@@ -0,0 +1,4 @@
+a.png
+Willkommen bei Lenck-Tech!
+Viel Spaß beim spielen...
+www.lencktech.com

二進制
SMP/vx32/data/schriften/normal.ltds


二進制
SMP/vx32/data/spiele/Linie/bilder/start.ltdb


+ 1 - 0
SMP/vx32/data/spiele/Linie/data/beschreibung.ltgb

@@ -0,0 +1 @@
+Bei dem spiel Linie bewegen sich die Spieler duch ein Spielfeld und können nur ihre Richtung beeinflussen. Dabei hinterlässt Jeder Spieler eine Linie die nicht berührt werden darf. Viel spaß wünscht ihnen Lenck Tech Games.

+ 3 - 0
SMP/vx32/data/spiele/Linie/data/game.ini

@@ -0,0 +1,3 @@
+start.ltdb
+beschreibung.ltgb
+id.ltgid

二進制
SMP/vx32/data/spiele/Linie/data/id.ltgid


二進制
SMP/vx32/data/spiele/Linie/maps/offiziell/Normal/bilder/bilder.ltdb


+ 6 - 0
SMP/vx32/data/spiele/Linie/maps/offiziell/Normal/data/beschreibung.ltgb

@@ -0,0 +1,6 @@
+Karte zum testen von Linie.
+
+-Spieltyp: Deathmatch
+-Siegesbedingung: zuerst 100 Punkte erreichen.
+-Spieleranzahl: 10
+-Teamanzahl: 0

+ 4 - 0
SMP/vx32/data/spiele/Linie/maps/offiziell/Normal/data/map.ini

@@ -0,0 +1,4 @@
+bilder/bilder.ltdb/icon.png
+bilder/bilder.ltdb/vorschau.png
+data/beschreibung.ltgb
+bilder/bilder.ltdb/spielladen.png

二進制
SMP/vx32/data/spiele/Stickman World Online/bilder/start.ltdb


+ 1 - 0
SMP/vx32/data/spiele/Stickman World Online/data/beschreibung.ltgb

@@ -0,0 +1 @@
+Stickman World online ist eines der Ersten Spiele von Lenck Tech Games. Es gibt verschiedene Karten mit jeweils anderen Spielsystemen. Lenck Tech wünscht dir viel Spaß beim Spielen.

+ 3 - 0
SMP/vx32/data/spiele/Stickman World Online/data/game.ini

@@ -0,0 +1,3 @@
+start.ltdb
+beschreibung.ltgb
+id.ltgid

二進制
SMP/vx32/data/spiele/Stickman World Online/data/id.ltgid


二進制
SMP/vx32/data/spiele/Stickman World Online/maps/offiziell/Test Karte/bilder/bilder.ltdb


+ 22 - 0
SMP/vx32/data/spiele/Stickman World Online/maps/offiziell/Test Karte/data/beschreibung.ltgb

@@ -0,0 +1,22 @@
+Karte zum testen von Stickman World online.
+
+-Spieltyp: Team Deathmatch
+-Siegesbedingung: Jeder andere Spieler muss mindestens 1 mal von deinem Team getötet werden.
+-Spieleranzahl: 24
+-Teamanzahl: 4
+ -Team 1 (grün):
+  -Spieleranzahl: 6
+  -Verbündete: --
+  -Feinde: Team 2, Team 3, Team 4
+ -Team 2 (blau):
+  -Spieleranzahl: 6
+  -Verbündete: --
+  -Feinde: Team 1, Team 3, Team 4
+ -Team 3 (gelb):
+  -Spieleranzahl: 6
+  -Verbündete: --
+  -Feinde: Team 1, Team 2, Team 4
+-Team 4 (rot):
+  -Spieleranzahl: 6
+  -Verbündete: --
+  -Feinde: Team 1, Team 2, Team 3

+ 3 - 0
SMP/vx32/data/spiele/Stickman World Online/maps/offiziell/Test Karte/data/map.ini

@@ -0,0 +1,3 @@
+bilder/bilder.ltdb/icon.png
+bilder/bilder.ltdb/vorschau.png
+data/beschreibung.ltgb

二進制
SMP/vx32/data/start/icon.exe


二進制
SMP/vx32/data/version


二進制
SMP/vx32/framework.dll


二進制
SMP/vx32/network.dll


二進制
SMP/vx32/start.exe


二進制
SMP/vx64/data/bilder/game.ltdb


二進制
SMP/vx64/data/bilder/system.ltdb


二進制
SMP/vx64/data/client/bilder/chat.ltdb


二進制
SMP/vx64/data/client/bilder/ladeanimation.ltdb


二進制
SMP/vx64/data/client/bilder/spielen.ltdb


二進制
SMP/vx64/data/client/bilder/titel.ltdb


+ 2 - 0
SMP/vx64/data/optionen.ini

@@ -0,0 +1,2 @@
+ServerIP=127.0.0.1
+ServerPort=4253

二進制
SMP/vx64/data/patch/bilder/news.ltdb


二進制
SMP/vx64/data/patch/bilder/patcher.ltdb


+ 4 - 0
SMP/vx64/data/patch/news/Willkommen/data.new

@@ -0,0 +1,4 @@
+a.png
+Willkommen bei Lenck-Tech!
+Viel Spaß beim spielen...
+www.lencktech.com

二進制
SMP/vx64/data/schriften/normal.ltds


二進制
SMP/vx64/data/spiele/Linie/bilder/start.ltdb


+ 1 - 0
SMP/vx64/data/spiele/Linie/data/beschreibung.ltgb

@@ -0,0 +1 @@
+Bei dem spiel Linie bewegen sich die Spieler duch ein Spielfeld und können nur ihre Richtung beeinflussen. Dabei hinterlässt Jeder Spieler eine Linie die nicht berührt werden darf. Viel spaß wünscht ihnen Lenck Tech Games.

+ 3 - 0
SMP/vx64/data/spiele/Linie/data/game.ini

@@ -0,0 +1,3 @@
+start.ltdb
+beschreibung.ltgb
+id.ltgid

二進制
SMP/vx64/data/spiele/Linie/data/id.ltgid


二進制
SMP/vx64/data/spiele/Linie/maps/offiziell/Normal/bilder/bilder.ltdb


+ 6 - 0
SMP/vx64/data/spiele/Linie/maps/offiziell/Normal/data/beschreibung.ltgb

@@ -0,0 +1,6 @@
+Karte zum testen von Linie.
+
+-Spieltyp: Deathmatch
+-Siegesbedingung: zuerst 100 Punkte erreichen.
+-Spieleranzahl: 10
+-Teamanzahl: 0

+ 4 - 0
SMP/vx64/data/spiele/Linie/maps/offiziell/Normal/data/map.ini

@@ -0,0 +1,4 @@
+bilder/bilder.ltdb/icon.png
+bilder/bilder.ltdb/vorschau.png
+data/beschreibung.ltgb
+bilder/bilder.ltdb/spielladen.png

二進制
SMP/vx64/data/spiele/Stickman World Online/bilder/start.ltdb


+ 1 - 0
SMP/vx64/data/spiele/Stickman World Online/data/beschreibung.ltgb

@@ -0,0 +1 @@
+Stickman World online ist eines der Ersten Spiele von Lenck Tech Games. Es gibt verschiedene Karten mit jeweils anderen Spielsystemen. Lenck Tech wünscht dir viel Spaß beim Spielen.

+ 3 - 0
SMP/vx64/data/spiele/Stickman World Online/data/game.ini

@@ -0,0 +1,3 @@
+start.ltdb
+beschreibung.ltgb
+id.ltgid

二進制
SMP/vx64/data/spiele/Stickman World Online/data/id.ltgid


二進制
SMP/vx64/data/spiele/Stickman World Online/maps/offiziell/Test Karte/bilder/bilder.ltdb


+ 22 - 0
SMP/vx64/data/spiele/Stickman World Online/maps/offiziell/Test Karte/data/beschreibung.ltgb

@@ -0,0 +1,22 @@
+Karte zum testen von Stickman World online.
+
+-Spieltyp: Team Deathmatch
+-Siegesbedingung: Jeder andere Spieler muss mindestens 1 mal von deinem Team getötet werden.
+-Spieleranzahl: 24
+-Teamanzahl: 4
+ -Team 1 (grün):
+  -Spieleranzahl: 6
+  -Verbündete: --
+  -Feinde: Team 2, Team 3, Team 4
+ -Team 2 (blau):
+  -Spieleranzahl: 6
+  -Verbündete: --
+  -Feinde: Team 1, Team 3, Team 4
+ -Team 3 (gelb):
+  -Spieleranzahl: 6
+  -Verbündete: --
+  -Feinde: Team 1, Team 2, Team 4
+-Team 4 (rot):
+  -Spieleranzahl: 6
+  -Verbündete: --
+  -Feinde: Team 1, Team 2, Team 3

+ 3 - 0
SMP/vx64/data/spiele/Stickman World Online/maps/offiziell/Test Karte/data/map.ini

@@ -0,0 +1,3 @@
+bilder/bilder.ltdb/icon.png
+bilder/bilder.ltdb/vorschau.png
+data/beschreibung.ltgb

二進制
SMP/vx64/data/start/icon.exe


二進制
SMP/vx64/data/version


二進制
SMP/vx64/framework.dll


二進制
SMP/vx64/network.dll


二進制
SMP/vx64/start.exe


+ 2 - 0
build.bat

@@ -0,0 +1,2 @@
+"D:\Visual Studio 2017\MSBuild\15.0\Bin\MSBuild.exe" "SMP.sln" /p:configuration=release /p:platform=win32
+"D:\Visual Studio 2017\MSBuild\15.0\Bin\MSBuild.exe" "SMP.sln" /p:configuration=release /p:platform=x64