|
Luc,
thank you. Using your hint I created login form class below.
However I have the following issues with it:
1. Log message is shown only after messagebox is displayed.
How to force text to be displayed in login form immediately after calling Log method ?
2. Log window is displayed in top of screen.
Top = (int)(0.6 * (double)screen.WorkingArea.Height);
seems not working. How to show login form in lower part of screen ?
3. If there are more items than login area height, a scroll bar appears.
How to remove the scroll bar.
4. How to remove icon and all buttons from login form title bar ?
Andus.
using System;<br />
using System.Windows.Forms;<br />
using System.IO;<br />
<br />
class main {<br />
[STAThreadAttribute()]<br />
public static void Main() {<br />
<br />
Status s = new Status("Performing task x");<br />
s.Log("This text is not shown immediately");<br />
<br />
System.Threading.Thread.Sleep(8000);<br />
MessageBox.Show ("now it is shown");<br />
}<br />
<br />
public class Status : Form {<br />
<br />
ListBox lb;<br />
<br />
public Status(string title) {<br />
<br />
lb = new ListBox();<br />
lb.Dock = DockStyle.Fill;<br />
Controls.Add(lb);<br />
<br />
Screen screen = Screen.AllScreens[0];<br />
AutoScroll = false;<br />
FormBorderStyle = FormBorderStyle.FixedSingle;<br />
Text = title;<br />
Left = 0;<br />
Top = (int)(0.6 * (double)screen.WorkingArea.Height);<br />
Height = screen.WorkingArea.Height / 3;<br />
Width = screen.WorkingArea.Width;<br />
Show();<br />
}<br />
<br />
public void Log(string s) {<br />
lb.Items.Add(s);<br />
lb.TopIndex = lb.Items.Count - 1;<br />
}<br />
}<br />
}
Andrus
|
|
|
|
|
Hi,
1.
I am not surprised; you are doing it in a strange (probably wrong) way as I told you before.And it is only getting worse. You should not have the Sleep, dont do MessageBox if there is
something better (your form), dont include Show() in a form's constructor,
use Application.Run so you have a message pump, etc.
2.
A form's location is either automatic or user defined, depending on Form.StartPosition
3.
Normally the idea of logging is to have a record of the entire history.
If you dont like it, you could make the listbox taller, remove the oldest logs,
not use a listbox at all, etc
4.
read up on Form properties. If you set a sufficient number of them to false or "" you
can get rid of anything you dont want.
I must insist you study some more, and start doing things in a more conventional way;
otherwise you will have problems all over the place.
|
|
|
|
|
Luc,
1. This issue reproduction performs some task and exists.
It uses form only to show progress messages.
Since it does not need to enter to message bump it does not call Application.Run() method.
My actual MDI application calles Run() method for MDI parent form.
However, it encounters exactly the same issue.
So my questions were:
A. How to force listbox to show new item immediately, without entering wait state ?
B. How to force status window to continue display messages when I switch to other application and then back to my application ?
Current not responding appears and window stops updating.
2. StartPosition = FormStartPosition.Manual; fixes the issue. Thank you.
3. I close login window immediately after task is completed.
So I'm looking a way not to hold all messages in listbox and remove listbox scrollbar or to use some other method which does not waste memory.
4. After setting some properties to false, all icons from title bar disappear. Thank you.
Andrus
|
|
|
|
|
When I use ShowDialog directly from a form, it opens the second form and stops the first, but now I am trying do this by invoking it from a different thread with a timer in it and the call looks a bit like this now:
public partial class frmMain : Form
{
private delegate void ShowVoidDelegate();
private void ShowFrmList()
{
try
{
if (!FrmList.InvokeRequired)
{
FrmList.ShowDialog();
}
else
{
Invoke(new ShowVoidDelegate(ShowFrmList), null);
}
}
catch (Exception e)
{
Debug.WriteLine(e.ToString());
}
}
}
The problem now is, that frmMain doesn't wait anymore for the frmList form to close and executes all the code after the showdialog invoke inside frmMain.
How can I get the usual behavior back when using invoke, so that frmMain waits until frmList is closed ?
Thanks, Eike
|
|
|
|
|
Hi Eike,
if I understand you correctly, you have a main thread and a main form (obviously),
then have some job spun off into another thread, and all of a sudden that job needs
to interact with the user, hence wants to show a dialog, then has to continue with
its job.
I have three comments:
1.
The InvokeRequired/Invoke thing is all right; it operates in a synchronous mode, that is
Invoke will return only when the delegate it calls has finished. So that does not seem
to fit with your observation. I dont know what is wrong.
2.
There are several timer classes. I would recommend you look at the System.Windows.Forms.Timer
since that one fires on the main thread, so you probably would not need the Invoke stuff
at all.
3.
I am not fond of programs that throw modal dialogs at me without me asking them to do that.
If such app's functionality is anything less than exceptional, it will soon end up in
the trash bin.
Hope this helps.
|
|
|
|
|
Thanks, it is a compact framework project with several forms, and I want to control all the input and methods used in the different forms by an independent class, but maybe I just put all of it into the main form, if that is easier to manage after all.
With compact framework I can use only System.Windows.Forms.Timer or System.Threading.Timer (that's what I use right now). This controlling class gets all the input from the forms, and then checks what to do and sends out what the forms shall do back to them, or that was the plan at least.
Still, the problem remains, that the showdialog of the frmList does not make frmMain wait anymore with invoke, it just jumps right back into the code block that calls the ShowFrmList() function and continues while the frmList is still open.
The modal dialogs are useful where they are, for example things like user login at the start or after logout.
|
|
|
|
|
Hi Eike,
I have no experience with Compact Framework, I expect the subset it offers works the same
as on the classic Framework.
Manage all the forms from inside the main form (or possibly the static Main method)
seems the right approach.
If the timer's main job is GUI stuff, Forms.Timer is the right one.
If you were to use Forms.Timer and have its Tick handler create and ShowDialog() the
dialog, I am confident the main form would come to a halt until you close the dialog.
The behavior you describe is unfamiliar to me. Normally Application.Run() starts your
first message pump, the loop that keeps your GUI active. Calling ShowDialog() creates
a new message pump, that now gets all the messages, until the dialog gets closed.
You can interfere a bit by calling Application.DoEvents() but that is not recommended
in general (I use it only to restore a GUI after closing a dialog, when a short action
is to be executed on the main thread but you dont want to see the damaged GUI that long).
Did you by any chance try it also as a regular app on classic FrameWork ?
|
|
|
|
|
Hi Luc,
>Did you by any chance try it also as a regular app on classic FrameWork ?
No sorry, I didn't try that, the forms are all FormFactor PocketPC and I have some external compiled ARM .DLLs in it as well. I can't convert it to an ordinary Windows program that easy. But usually Compact and Full Framework behave the same way, just that a lot of nice methods and whole classes are missing in CF.
Nevertheless, if I actually change everything and use the timer in the main form, wouldn't it stop when other forms are opened as modal dialog ? I still need to control the other forms by some sort of timer, if the timer in the main form keeps running, that would work though.
Thanks, Eike
|
|
|
|
|
Hi Eike,
even with a modal dialog open, the main form stays alive: all its Window messages get handled
(e.g. it repaints when you move another window over it) and it keeps getting and executing
its timer ticks (watch the clock in apps that have it in the their status bar).
-- modified at 3:49 Tuesday 24th July, 2007
|
|
|
|
|
I am writing a Windows service in C#, in the constructor for the service I create and two threads to do the work, I then call Start() on both threads in the OnStart event. When I attempt to start the service in the Services manager I get the progress bar for about 30 seconds and then I get a dialog telling me the service did not respond in time (Error 1053).
I have added some debug comments and I can see that the OnStart event handler does return and that the two threads are running. From what I understand the service is up and running when the OnStart handler returns. What would be causing the timeout?
OS is Windows XP SP2, service is .NET 1.1
|
|
|
|
|
It is not completely clear to me from what you are describing, but I guess it is one of these
two:
- your service is not available soon enough, does your initial delay prevent it from
responding to the Services Maneger ? (i.e. did you do say a Thread.Sleep() in the main
thread, instead of using a timer ?)
- or your service exits for some reason (so it starts up OK, but you did not debug till the
end, or for some reason under Services Manager it fails (you are catching all exceptions
and logging them, are you ?)
Hope this helps
|
|
|
|
|
There are a few quirks about creating threads, one of these is that the response to Start (or is it initialise, been a while since I did this) cannot take more than 30 seconds and must return.
It is pretty normal (if not 100% correct or ideal) to start a seperate thread for the initialisation and then return imediatly to the Service Control Manager. This way you avoid the 30 second issue, especially when you need to do things like access a database etc
This way the Service Control Manager gets its desired service started / Initialised in time and leaves you to get on with the work you app needs to do in its own time.
|
|
|
|
|
plz just go through below code:
public class Base
{
public void GetbasePrivate() { }
protected void GetbaseProtected() { }
}
public class child : Base
{
protected void GetchildProtected() { }
public void GetchildPublic() { }
}
static class Program
{
static void Main()
{
Base objbase = new Base();
Base objbase = new Child(); //Please can any one explain these line in details.
}
}
Plz any one can tell me the differences of bold lines. Thx in advance.
Anmol Gupta
|
|
|
|
|
Hi,
new Base() creates an instance of Base, capable of whatever methods/properties are available
in the Base class.
Base objbase = new Base(); sets the variable objbase to refer to that instance, so now
you can do things such as objbase.GetbasePrivate() since that one is public (!)
new Child() creates an instance of Child, capable of whatever methods/properties are available
in the Child class or the Base class, since Child inherits from base.
if you were to do Child child=new Child(); you could now do both child.GetbasePrivate()
and child.GetchildPublic();
Base objbase = new Child(); creates an instance of Child, which automatically also is an
instance of Base since Child inherits from Base, and now the objbase variable refers to it
but acts as if it is a Base instance, forgetting all the extras that may come with
being a Child object too. So now you can do objbase.GetbasePrivate() but you cant
do objbase.GetchildPublic() since the Base class does not have such a method.
This is one of the fundamentals in object-orientation. It is not specific to C#.
If unclear, I strongly suggest you buy a book on C# (or on OO in general) and work
your way through it.
Good luck in the OO world !
|
|
|
|
|
Thanks for your quick response. I agree, what ever you have written there but Just I wanted to know that what is significant of Base objbase = new Child();.
I do not see any differences[Practically] between Base objbase = new Child(); and Base objbase = new Base();
If I am right then why do we use Base objbase = new Child();.
Thanks
Anmol gupta
|
|
|
|
|
Because Child could possibly override and change functionality of it's base class. So it can polymorphically be treated as an instance of the base class but have different behavior. For one thing.
And in the real world, your base class will likely be abstract, meaning you can't create an instance of it directly.
|
|
|
|
|
Hi,
the easiest way to understand its power requires three classes (one parent, two children)
say Control, TextBox, Button
Now you have a Windows Form that contains a lot of Controls, some of them are TextBox,
some are Button, some are whatever...
Form has a collection called Controls that holds all its controls, whatever their
exact type is. You can iterate over that collection like so:
foreach (Control c in myForm.Controls) {
Console.WriteLine(c.Text);
}
So by not relying on specific features, the more general base class works just fine here.
You cannot do foreach (Button btn in myForm.Controls) since now, at run-time it
will encounter a control that is not a Button and the implicit cast will fail.
You cannot do c.PerformClick();
the compiler rejects this because Control does not have that method, Button has.
You can cast explicitly, as in:
Button btn=(Button)c;
And a common pattern is (clicking all the buttons):
foreach (Control c in myForm.Controls) {
Button btn=c as Button;
if (btn!=null) btn.PerformClick();
}
So the advantage is: use a less specialized variable, if you want to generalize your code
(as in c.Text), use the more specialized variable if you need it.
And then there is the whole story about virtual methods and properties...
You really need to read a book you know.
|
|
|
|
|
OK Luc Pattyn Thanks for your suggestion. Can you give me name of some good and comprehensive books which cover Object Oriented concepts with C#.
|
|
|
|
|
Almost any book would do;
my first C# book was "Microsoft Visual C#.NET step by step" by John Sharp and Jon Jagger (2002),
but that is a bit outdated now, since there is C$ 2.0 now, adding features to the language
so you might want to look for a more recent book.
My first OO experience dates way back, cant even remember.
You may find some book recommendations on one of the CP forums.
And you might want to visit the Amazon site, and look at the hundrads of C# books there.
They come with stars and recommendations too.
But then, in my experience book appreciation is a very subjective matter; it all depends
on prior knowledge, personal style, and your attitude towards the balance between
reading, following a classroom course, and doing your own experiments.
|
|
|
|
|
|
As you can see from your example, Child derives from Base. This means that you can create an instance of Child even if you refer to it by an ancestor class. Now, why is this useful? Consider this design (highly contrived, but it does illustrate the point):
public class Sales
{
private double _salesTax = 1.05;
public double CalculateSale(double basePrice)
{
return basePrice * this.SalesTax;
}
public virtual double SalesTax
{
get { return _salesTax; }
}
}
public class EuSales : Sales
{
public override double SalesTax
{
get { return 1.175; }
}
}
public class ShoppingCart
{
private SaleLines _saleLines = new SaleLines();
public SaleLines Lines
{
get { return _saleLines ; }
set { _saleLines = value; }
}
public double TotalSales(Sales tax)
{
return _salesLine.TotalCost * tax.SalesTax;
}
public class SaleLine
{
public string Item;
public double ItemCost;
public int Qty;
}
public class SaleLines
{
private List<SaleLine> _lines = new List<SaleLine>();
public void AddLine(string item, double cost, int qty)
{
SaleLine line = new SaleLine();
line.Item = item;
line.ItemCost = cost;
line.Qty = qty;
_lines.Add(line);
}
public double TotalCost
{
get
{
double runningTotal = 0.0;
for (int i = 0; i < _lines.Count; i++)
{
runningTotal = _lines[i].Qty * _lines[i].ItemCost;
}
return runningTotal;
}
}
}
} Now, if you create a test harness for this and pass in an instance of Sales to the TotalSales method, you will get the a total multiplied by 1.05. If you pass in an instance of EuSales, you get the total multiplied by 1.175%.
Deja View - the feeling that you've seen this post before.
|
|
|
|
|
Hi, I am trying to get the username of the user logged into Windows Server 2003 the followiong code seems to work ok for windows xp but when i use the smae code on Server 2003 the code returns a blank.If anyone has any ideas or suggestions they would be appreciated.....
string user = HttpContext.Current.Request.ServerVariables["LOGON_USER"];
Thanks in advance
Tim
|
|
|
|
|
I managed to solve this by turning off anonymous access in iis
|
|
|
|
|
Hi,
Can anybody tell me how to add support for a new languages without ever recompiling the neutral assembly that contains all the application code.After deploying the application I created a satlite assembly for a new language and uploaded to the bin directory of the application.But if I change the application culture it is not reading the values form the new satlite assembly.
Thanks&Regards,
Prajin
|
|
|
|
|
Please don't cross post. It's not good manners.
Deja View - the feeling that you've seen this post before.
|
|
|
|
|