עבור לתוכן

[C#] חדש בתחום, בעייה בתכנות תוכנה

Featured Replies

פורסם

התחלתי אתמול ואיזה מישהו דיי עזר לי

הרכבתי סקריפט של סייד באר.. ואני רוצה לשים בו טיימר

הכנתי את האובייקט של הטיימר ובדקתי אותו - הוא פועל.

עכשיו יש לי בעיה בשינוי תיבת הטקסט:

הפעולה בין תהליכי משנה אינה חוקית. הפקד 'TimeText' ניגש מתהליך משנה שאינו תהליך המשנה בו נוצר.

בטעינת המסמך יש פונקציה שעושה

TimeText.Text = tDate;

זה פועל

אבל אח"כ אני רוצה שכל 1000 מילישניות (שניה) תרוץ פונקציה אחרת שתעשה בדיוק אותו דבר. אם אני עושה MessageBox זה מראה לי את התאריך והשעה הנכונים, אבל אם אני עושה TimeText.Text = tDate (ומכין לפני זה את הtDate כמובן..) זה לא פועל ומראה לי תשגיאה הזאת =\ (למרות שהוא מצליח לבנות תSolution)...

למישהו יש מושג?

פורסם

אתה מריץ את הטיימר ב thread נפרד נכון?

אם כן אתה צריך לבצע invoke ע"מ לעדכן את התיבה אחרת יהיה cross-threading

בפונקציית ה tick של הטיימר תכתוב את הדבר הבא

this.Invoke(new MethodInvoker(delegate() { TimeText.Text = tDate; }));

// רק שתבין מה קורה כאן בעצם. הת'רד היחידי שיכול לשנות את ה

GUI

הוא הת'רד המרכזי, לא יכולים להיות 2 ת'רדים שיעדכנו את ה

GUI

דבר הזה נקרא cross threading

ואני חושב שזו הייתה הבעיה שלך במקרה הזה.

אם לא אז ניסיתי :silly:

פורסם
  • מחבר

תודה רבה, איפה רק למקם את זה?

עריכה:

הבנתי, ממש תודה.[br]פורסם בתאריך: 29.06.2007 בשעה 22:04:22


טוב, זה פועל, אבל משום מה אחרי דקה בערך (קצת פחות) זה פשוט מפסיק להתעדכן..

הקוד של הטיימר:

      TimerCallback tc = new TimerCallback(CheckTime);

System.Threading.Timer t = new System.Threading.Timer(tc, null, 1000, 1000);

הקוד של CheckTime:

    public void CheckTime(Object state)
{
string tDate = DateTime.Now.Hour + ":" + DateTime.Now.Minute + ":" + DateTime.Now.Second + "\n";
tDate += DateTime.Now.Day + "." + DateTime.Now.Month + "." + DateTime.Now.Year;
this.Invoke(new MethodInvoker(delegate() { TimeText.Text = tDate; }));

}

פורסם

אצלי עובד מצויין


using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;

namespace WindowsApplication2
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
TimerCallback tc = new TimerCallback(CheckTime);

System.Threading.Timer t = new System.Threading.Timer(tc, null, 1000, 1000);
}
public void CheckTime(Object state)
{
string tDate = DateTime.Now.Hour + ":" + DateTime.Now.Minute + ":" + DateTime.Now.Second + "\n";
tDate += DateTime.Now.Day + "." + DateTime.Now.Month + "." + DateTime.Now.Year;
this.Invoke(new MethodInvoker(delegate() { TimeText.Text = tDate; }));

}
}
}

פורסם
  • מחבר

אז יש משהו לעשות בקשר לזה בכלל?

פורסם

כן - לשמור רפרנס לטיימר מחוץ לפונקציה.

נניח, ככה:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;

namespace WindowsApplication2
{
public partial class Form1 : Form
{

private System.Threading.Timer t;

public Form1()
{
InitializeComponent();
TimerCallback tc = new TimerCallback(CheckTime);

t = new System.Threading.Timer(tc, null, 1000, 1000);
}
public void CheckTime(Object state)
{
string tDate = DateTime.Now.Hour + ":" + DateTime.Now.Minute + ":" + DateTime.Now.Second + "\n";
tDate += DateTime.Now.Day + "." + DateTime.Now.Month + "." + DateTime.Now.Year;
this.Invoke(new MethodInvoker(delegate() { TimeText.Text = tDate; }));

}
}
}

שים לב שהצהרתי על t כ-member של הטופס, ולא כמשתנה בתוך הפונקציה.

בדוגמא הספציפית הזו, אתה צריך לדאוג שהטיימר ייעצר ברגע שסוגרים את הטופס (אחרת הקריאה ל-TimeText.Text לא תהיה רלוונטית).

פורסם
  • מחבר

טוב, נראה לי שהבנתי.

תודה רבה לכולם.

ד"א, איך משייכים לפתיחת קובץ בקליק?

אני רוצה לפתוח את הווינאמפ בלחיצה.. איך אני פותח אותו?

פורסם

אתה מתכוון בEXPLORER?

יש בכלים->אפשרויות תיקייה.

פורסם
  • מחבר

לא, את זה אני יודע.

התכוונתי לפתיחת קובץ בC# - מן הסתם, כי זה בנושא של C# :s07:

בכל מקרה איך פותחים קובץ בלחיצה על כפתור לדוגמא? מה הפקודה?

ארכיון

דיון זה הועבר לארכיון ולא ניתן להוסיף בו תגובות חדשות.

דיונים חדשים