Hallo,
ich möchte gerne events auslösen. Beim Server kommt das Event an, aber nicht
beim Client. Warum nicht, muss ich da noch etwas beachten?
Hier der Code dazu:
server
static void Main(string[] args)
{
IpcChannel channel = new IpcChannel("localhost:32600");
ChannelServices.RegisterChannel(channel,true);
GethLib.serverMethods.critmsg += new GethLib.serverMethods.critmsgHandler(serverMethods_critmsg);
Console.WriteLine("The name of the channel is {0}.",
channel.ChannelName);
Console.WriteLine("The priority of the channel is {0}.",
channel.ChannelPriority);
System.Runtime.Remoting.Channels.ChannelDataStore channelData =
(System.Runtime.Remoting.Channels.ChannelDataStore)
channel.ChannelData;
foreach (string uri in channelData.ChannelUris)
{
Console.WriteLine("The channel URI is {0}.", uri);
}
System.Runtime.Remoting.RemotingConfiguration.
RegisterWellKnownServiceType(
typeof(GethLib.serverMethods), "serverMethods",
System.Runtime.Remoting.WellKnownObjectMode.Singleton);
string[] urls = channel.GetUrlsForUri("serverMethods");
if (urls.Length > 0)
{
string objectUrl = urls[0];
string objectUri;
string channelUri = channel.Parse(objectUrl, out objectUri);
Console.WriteLine("The object URI is {0}.", objectUri);
Console.WriteLine("The channel URI is {0}.", channelUri);
Console.WriteLine("The object URL is {0}.", objectUrl);
}
Console.WriteLine("Press ENTER to exit the server.");
Console.ReadLine();
Console.WriteLine("The server is exiting.");
}
static void serverMethods_critmsg(string CritMsg)
{
Console.WriteLine(CritMsg);
}
}
servermethods:
public class serverMethods:MarshalByRefObject
{
private int msg;
private string xCritmsg = "Kritischer Wert erreicht!";
public delegate void critmsgHandler(string CritMsg);
public static event critmsgHandler critmsg = null;
public int Msg
{
get
{
if (msg > 5)
{
if (critmsg != null)
{
critmsg(xCritmsg);
}
}
return (msg++);
}
}
}
Client:
class Program
{
static void Main(string[] args)
{
IpcClientChannel clientChannel = new IpcClientChannel();
ChannelServices.RegisterChannel(clientChannel,true);
RemotingConfiguration.RegisterWellKnownClientType(typeof(GethLib.serverMethods), "ipc://localhost:32600/serverMethods");
GethLib.serverMethods sm = null;
for (int i = 0; i < 10; i++)
{
sm = new GethLib.serverMethods();
Console.WriteLine(sm.Msg);
}
GethLib.serverMethods.critmsg += new GethLib.serverMethods.critmsgHandler(serverMethods_critmsg);
}
static void serverMethods_critmsg(string CritMsg)
{
Console.WriteLine(CritMsg);
}
}
Danke
void lb_aufstellung_SelectedIndexChanged(object sender, EventArgs e)
{
lbl_stärke.Text = Reader.GetValue(1).ToString();
}
sollte schon ausserhalb deiner ersten funktion stehen...
lies doch die daten erst einmal ein und dann arbeite darauf.
ergo:
Dictionary<Spieler,Stärke> _Spielerdaten = new Dictionary<Spieler,Stärke>();
void ReadDB()
{
...
while (Reader.Read())
{
_Spielerdaten[new Spieler(Reader.GetValue(0).ToString())] = new Stärke(Reader.GetValue(1).ToString());
}
...
}
dann kannst du dir eine funktion schreiben die auf "SelectedIndexChanged" horcht.
darin:
-wer wurde angeklickt?
-wer ist das in meinen _Spielerdaten
-_Spielerdaten[Spieler] in dein Label eintragen
Grüße
Ich hatte gerade eine "Idee". Bevor du weiterliest, möchte ich dich mit zwei Dingen konfrontieren:
1. Wie weit bist du bereit zu gehen?
2. Der nachfolgende Code ist ein Proof Of Concept und soll nur eine Lösung skizzieren. Aber der Code funktioniert.
Ich habe eine funktionierende Lösung gefunden. Sie ist allerdings krank und bringt eine Menge anderer Nachteile mit. Aber wer weiss ...
struct Image
{
int width;
int height;
};
#define MY_EXPORT extern "C" __declspec(dllexport)
MY_EXPORT void InitImage(int width, int height, Image* img)
{
img->width = width;
img->height = height;
}
using System;
using System.Dynamic;
using System.Runtime.InteropServices;
namespace SharpTest
{
[StructLayout(LayoutKind.Sequential)]
class Image
{
private readonly int m_width;
private readonly int m_height;
public Image()
{
m_width = 0;
m_height = 0;
}
public int Width { get { return m_width; } }
public int Height { get { return m_height; } }
}
static class NativeMethods
{
[DllImport("NativeLibTest.dll", EntryPoint = "InitImage", CallingConvention = CallingConvention.Cdecl)]
public static extern void CreateImage(int width, int height, [Out] Image img);
}
class NativeCaller
: DynamicObject
{
public override bool TryInvokeMember(InvokeMemberBinder binder, object[] args, out object result)
{
var method = typeof(NativeMethods).GetMethod(binder.Name);
var parameters = method.GetParameters();
if((parameters.Length - 1) != args.Length)
{
result = null;
return false;
}
var lastParameter = parameters[parameters.Length - 1];
var arguments = new object[args.Length + 1];
for(int i = 0; i < args.Length; ++i)
{
arguments[i] = args[i];
}
result = arguments[args.Length] = Activator.CreateInstance(lastParameter.ParameterType);
method.Invoke(null, arguments);
return true;
}
}
public class Program
{
public static void Main(string[] args)
{
dynamic nativeCaller = new NativeCaller();
var image = nativeCaller.CreateImage(100, 200);
Console.WriteLine("Width: {0}\tHeight: {1}", image.Width, image.Height);
Console.ReadKey(true);
}
}
}
Das NativeCaller Objekt passt den Aufruf der Methode entsprechend an und erstellt für dich das letzte Argument und gibt dieses als Resultat zurück. Die Klasse NativeCaller , einmal korrekt implementiert, muss nicht mehr angepasst werden und lädt alle nötigen Informationen aus den Methoden definiert in NativeMethods . Die importierten Methoden definiert man wie bisher.
Es lebe dynamic !
Grüssli
hustbaer schrieb:
Eigentlich sollte
Dispatcher.BeginInvoke(() =>
{
// Hier der Code für die Control-Elemente
});
ausreichend sein.
Da bekomme ich eine lambda/Delegat-Konvertierung Fehlermeldung.
Aber trotzdem danke, Variante 2 scheint "normaler" zu sein, also nehm ich die.
Da ich bei meinem Projekt auch an der Problematik dran war möchte ich ein paar Tipps dazu geben. Es ist nämlich so, dass WPF-Applikationen immer erstmal auf US/EN eingestellt sind. Das kann man leicht ändern indem man in den Konstruktor vom MainWindow das reinschreibt:
// Set Operating-System-Culture for this Application
FrameworkElement.LanguageProperty.OverrideMetadata(typeof(FrameworkElement),
new FrameworkPropertyMetadata(XmlLanguage.GetLanguage(CultureInfo.CurrentCulture.IetfLanguageTag)));
Das bewirkt dass das Programm nach aussen hin das Komma als Dezimal-Separator benutzt. Also sowohl beim Import/Export von double als auch bei der Darstellung in Control-Elementen. Nur im Code selber benutzt man dann weiterhin den Punkt.
Auch praktisch ist, wenn man den aktuell verwendeten Separator ausliest:
string separator = NumberFormatInfo.CurrentInfo.CurrencyDecimalSeparator;
Grüsse
Ank
Bei TextBox geht es wohl nur so. Was man machen kann, ist RichTextBox verwenden, und den Text als PlainText laden bzw speichern. Bei RichTextBox gibt es eine Methode namens Find(). Mit dieser kann man nach Wörtern suchen. Eine Methode zu Ersetzen gibt es dort nicht. Man kann dazu aber SelectedText verwenden. Tschüüüüsss.
Mit vielen Textboxen brauchst Du entweder
- eine hartcodierte Zuordnung von Textbox zu Wert oder
- eine Vorschrift, die diese Zuordnung zur Laufzeit berechnet.
Die erste ist sozusagen die "naive" Variante. Leicht zu schreiben, aber der Horror, wenn man so eine Anwendung länger als eine Woche pflegen soll.
Die zweite Variante kann man in Erwägung ziehen. Jede TextBox hat die Properties Name und Tag. Über eine davon oder eine Kombination von beiden kann man jede einzelne TextBox in der Collection .Controls (http://msdn.microsoft.com/en-us/library/system.windows.forms.control.controls(v=vs.80).aspx) des übergeordneten Containers wiederfinden.
Die Daten kannst Du über ihren Index aus der Liste fischen:
Liste<TabelleA> list = new Liste<TabelleA>();
// list füllen
for( int index = 0; index < list.Count; index++)
{
TextBox textBox = GetRelevantTextBox( index);
textBox.Text = list[index].Verein;
}
Th69 schrieb:
Tja, RightToLeft ist etwas anderes als rechtsbündige Ausrichtung!
Genau das ist mir mittlerweile auch aufgefallen, habs dann mit dem Parameter "TextAlign" beheben können.
1. Was heisst "Kann die Applikation nicht beenden"? Was passiert? Was hast du erwartet?
2. Was ist das für eine C++ Applikation? Graphische Oberfläche? Konsole? Selbstgeschrieben? Was verstehst du unter einem "Entwicklungs-Tool"?
3. Abgesehen davon schliesst man andere Applikationen nicht so. Was du hier machst ist die Hau-Drauf-Methode. Korrekt wäre, wenn du der anderen Applikation eine Nachricht senden würdest, dass sie sich doch bitte sauber beenden soll. In der anderen Applikation implementierst du eine entsprechende Behandlung dieser Nachricht und lässt sie sauber beenden. Es gibt zahlreiche Möglichkeiten eine solche Nachricht zu schicken, da kommt es vor allem wieder darauf an, was das für eine C++ Applikation ist.
Grüssli
ich habs jetzt in ein byte array gepackt und über den networkstream(größe, daten) gemacht... war wie mir schon erwähnt sehr einfach... meine denkweise geht immer nur zu viele wege...
danke an alle!!!
:p
oder:
WebClient wc=new WebClient();
wc.Proxy=null; // schaltet Suche nach Proxy-Einstellungen aus - die kann ordentlich verzögerungen verursachen
string html=wc.DownloadString("http://www.google.de");
Hm ja stimmt das hatte ich nicht bedacht. Kommt dann halt immer drauf an was genau man erreichen will.
Vielleicht wäre es auch möglich das ganze ohne Rollback zu machen ?
Das Fenster ist nicht 350 sondern 525 breit, 350 ist die Höhe.
Und was ich machen will, hat mit genau der gleichen Sache zu tun. Ich habe ein etwas komplexeres Fenster programmiert, dessen Positionen auf der Margin Eigenschaft basieren. Das Programm soll jedoch nicht nur auf Windows XP, sondern auch auf anderen Betriebssystemen ausführbar sein, ohne dass sich Labels und Buttons unschön verziehen.
Dir lässt sich leider nur sehr schwer helfen. Denn der Code ist sehr lang und sehr unübersichtlich...
Wenn es mit einem Port bereits funktioniert, dann sollte ein anderer Port eigentlich keine Probleme bereiten. Mir fällt dazu keine Erklärung ein. Startest du das Programm zur Änderung des Ports neu? Wenn nicht, dann könnte es sein, dass du die alte Verbindung nicht richtig schließt und daher keinen anderen Port wählen kannst.
Wenn es beim Schließen des Programms eine Fehlermeldung gibt, dann solltest du den Debugger nutzen, um festzustellen wo dieser Fehler auftritt. Ich könnte mir vorstellen, dass du damit einen Verbindungsabbruch o.ä. erzeugst und dann eine Exception geworfen wird.
Alternativ könntest du auch mit einem anderen Tool (z.B. Putty, DebugTCP-Tool) versuchen einen Client/Server zu simulieren, um sicherzustellen, dass der Client/Server korrekt arbeitet.