PDA

View Full Version : حرفه ای: دریافت داده ها از پروتکل UDP توسط DLL و ارسال آن به برنامه



مهرداد سیف زاده
سه شنبه 13 خرداد 1393, 12:10 عصر
سلام دوستان. برنامه dll رو نوشتم و الان کار میکنه ولی هر بار باید متد getData رو توسط timer هر ثانیه بخونم تا ببینم داده های جدید اومده یا نه که این طور حتی داده های قبلی رو بازم میگیرم.
مشکل من این جاست که میخوام پاکت جدید اومد و رشته ازش جدا شد به برنامه اصلی پاس داده بشه. توی نت خیلی گشتم و راه حلش رو پیدا کردم ولی دانش #c من به حدی نیست که بتونم از Event در این برنامه استفاده کنم و رشته رو به برنامه پاس بدم.
ممنون میشم کمکم کنید
http://stackoverflow.com/questions/16494284/how-to-generate-callback-event-from-library-to-application-in-c-sharp
http://stackoverflow.com/questions/20876520/callback-method-indirectly-calling-back-itself


private static Socket sk;
public static int portNumber;
private static string udpData;


public static void init(int port)
{

portNumber = port;
sk = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
sk.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);


EndPoint RemoteIpEndPoint = new IPEndPoint(IPAddress.Any, port);
sk.Bind(RemoteIpEndPoint);


byte[] buffer = new byte[3000];
sk.BeginReceiveFrom(buffer, 0, buffer.Length, SocketFlags.None, ref RemoteIpEndPoint, new AsyncCallback(recv), buffer);
}


public static string getData()
{
return udpData;
}


private static void recv(IAsyncResult res)
{


try
{
EndPoint RemoteIpEndPoint = new IPEndPoint(IPAddress.Any, portNumber);
int size = sk.EndReceiveFrom(res, ref RemoteIpEndPoint);
if (size > 0)
{
byte[] reciveData = new byte[1464];
reciveData = (byte[])res.AsyncState;
ASCIIEncoding encodeing = new ASCIIEncoding();
udpData = encodeing.GetString(reciveData);


}


byte[] buffer = new byte[3000];
// eventRecive = "";
sk.BeginReceiveFrom(buffer, 0, buffer.Length, SocketFlags.None, ref RemoteIpEndPoint, new AsyncCallback(recv), buffer);


}
catch (Exception e)
{
udpData = e.Message;
}
}

مهرداد سیف زاده
شنبه 17 خرداد 1393, 09:10 صبح
دوستان یعنی این سوال انقدر سخته؟
یعنی هیچ کس هیچ نطری نداره؟

مهرداد سیف زاده
سه شنبه 20 خرداد 1393, 15:28 عصر
یعنی هیچکدام از اساتید و متخصصان قسمت #c هم نتونستن به این سوال پاسخ بدن
من کارم php هست و در یک پروژه ناچار شدم بنا به درخواست مشتری به زبان #c هم برنامه بنویسم.
حل مشکل event حتی با مستندات مایکروسافت هم حل نشد یعنی حتی مایکروسافت برای راحت کردن کار برنامه نویس اومده و مفهوم event رو هم تغییر داده :تشویق:
و اما بعد از چند روز که گشتن در کتاب های خارجی و همچنین خواندن کتاب c# in depth مشکلمو حل کردم. در فصل دوم اومده دل و جیگیر event رو کشیده بیرون و حتی از مستندات و نمونه مثالهای مایکروسافت هم بهتر توضیح داده.
برای event زدن بین یک dll و برنامه #c بصورت زیر کار میشه:

1- تعریف یک event سراسری در class library

public event EventHandler<EventArgs> NewPacket;

2- در جایی که پاکت udp یا هر چیز دیگیری که قراره جدید باشه و به برنامه پاس داده بشه بصورت زیر در event قرار میگیره

NewPacket(StrInPacket,null);

3- این جاش زیاد خوشم نیومد و واقعا مفهوم event رو زیر سوال برده چون نیاز به نوشتن کدهای زیادی برای دریافت event هست حتی من بعد از جدا کردن string از پاکت دریافتی میخواسم در یک listBox نمایش بدم که مشکل thread پیش اومد و دوباره توی وب گشتم و مشکل رو حل کردم
در هنگام فراخوانی کدهای زیر نوشته میشه

NetworkLis.UDP rec= new NetworkLis.UDP();
rec.NewPacket += usesData;

اون قسمت usesData تابعی هست که باید از event استفاده میکنه

public void usesData(object sender, EventArgs e) {
AddItem(sender.ToString());
}
و برای حل مشکل thread هم مقدار دریافتی برای اضافه کردن به listBox از متد AddItem و delegate زیر استفاده کردم

private delegate void stringDelegate(string s);private void AddItem(string s)
{
if (UdpList.InvokeRequired)
{
stringDelegate sd = new stringDelegate(AddItem);
this.Invoke(sd, new object[] { s });
}
else
{
UdpList.Items.Add(s);
}
}

و ممنون از دوستانی که به این پست نگاه کردن و حتی کوچکترین راهنمایی هم شاید از دستشون بر میومد از بنده دریغ کردم.