Temperature TextBox In C# - c#

I need some code to convert standard C# TextBox to temperature TextBox which means adding "°C" to end of the text in the textbox with another color than the default color.

To get the degree symbol you can use character code 176 e.g.
Char degree = (Char)176
You can then append this to your textbox content or I would just add a label to the right of the textbox with the degree symbol if you want to control the forecolor easily.

TextBox is a plain text editor. To get different colours you would have to muck around with a rich text box. Why not put the "°C" in a label positioned to the right of the text box? That would also make your parsing and rendering code much easier.

You could probably create your own control which inherits from TextBox and then override Text property to automaticaly add °C though other color inside the same TextBox could be problem.
Why you want to have °C in TextBox ?
Can't it just be label right after TextBox ?
You can set static text and color to what you want.

The other solutions proposed here are probably sufficient for your application; however, if you had the need to implement this with re-usability in mind, here is a custom control solution which you may extend to better suit your application:
public class TemperatureTextBox : ContainerControl
{
private const int BORDER_SIZE = 1;
// Exposes text property of text box,
// expose other text box properties as needed:
public override string Text
{
get { return textBox.Text; }
set { textBox.Text = value; }
}
private TextBox textBox = new TextBox()
{
Text = string.Empty,
BorderStyle = BorderStyle.None,
Dock = DockStyle.Fill
};
private Label label = new Label()
{
Text = "°C",
TextAlign = ContentAlignment.MiddleCenter,
Size = new Size()
{
Width = 32
},
BackColor = SystemColors.Window,
Dock = DockStyle.Right
};
public TemperatureTextBox()
{
this.BackColor = SystemColors.Window;
this.Padding = new Padding(BORDER_SIZE);
this.Controls.Add(label);
this.Controls.Add(textBox);
this.PerformLayout();
}
// Constrain control size to textbox height plus top and bottom border:
protected override void OnResize(EventArgs e)
{
base.OnResize(e);
this.Height = (textBox.Height + (BORDER_SIZE * 2));
}
// Render a border around the control:
protected override void OnPaint(PaintEventArgs e)
{
base.OnPaint(e);
e.Graphics.DrawRectangle(
SystemPens.ControlDarkDark,
new Rectangle()
{
Width = (this.Width - BORDER_SIZE),
Height = (this.Height - BORDER_SIZE)
});
}
}
Simply create a new class and drop this code in and rebuild you solution. It will create a new TemperatureTextBox control in the toolbox which can be dropped onto a new form and visually designed.
This example exposes the Text property of the underlying text box by overriding the custom control's text property. You may want to expose other properties, and events depending on what your application needs to accomplish.

Related

WinForms Element messes up vertical text alignment after border removal

I have a Control that ultimately inherits from TextBox
If I don't remove the border then the text vertical alignment is fine:
But I want to remove the border like this:
public partial class MyReadonlyDataField : TextBox
{
private void InitializeComponent()
{
this.BorderStyle = System.Windows.Forms.BorderStyle.None;
this.Appearance.BorderAlpha = Infragistics.Win.Alpha.Transparent;
this.TextAlign = System.Windows.Forms.HorizontalAlignment.Right;
this.Height = 19;
}
}
But then the text alignment is off. How can I fix that?
I solved it. If I set the perfect height for my TextBox control then the text will be centered, because the control has the exact height that matches the text font.
To achieve that I set the hidden AutoSize property of TextBox. It can't be set in the Forms-Designer nor does IntelliSense list it as property. But it exists and works when set to true!

My windows form button is set to width 0 when it should be full width

I'm working on a Excel add-in project that will require me to procedurally generate some controls in a windows task pane. While experimenting, I ran into an issue where this button keeps having its width set to 0, and I don't understand why.
If I don't use any anchoring or docking then the button shows up, but at its default width and height. I am trying to get it to span the width of the layout panel, and it was my understanding you could accomplish this by using AnchorStyles Left and Right, or with DockStyle Fill. However, as soon as I add these properties the width gets set to 0 (as seen from the debugger). I checked the width of the root control (this) and the button's parent control FlowLayoutPanel, and they are both the default non-zero size.
What am I doing wrong?
public MyUserControl()
{
FlowPanel = new FlowLayoutPanel
{
Name = "My Flow Panel",
TabIndex = 0,
FlowDirection = FlowDirection.TopDown,
};
Button button1 = new Button
{
Name = "button1",
Text = this.Width.ToString(),
FlatStyle = FlatStyle.Flat,
Padding = new Padding
{
Left = 10
},
Parent = FlowPanel,
Anchor = (AnchorStyles.Left | AnchorStyles.Right)
};
FlowPanel.Controls.Add(button1);
this.Controls.Add(FlowPanel);
}
You can't anchor like that in FlowLayoutPanels. Instead, subscribe to the SizeChanged event and modify the button width there. You'll probably also need to set the width when you create the button, so below I've just created a method you can call from both places.
FlowPanel.SizeChanged += new System.EventHandler(this.FlowPanel_SizeChanged);
private void FlowPanel_SizeChanged(object sender, EventArgs e)
{
SetButtonWidth();
}
void SetButtonWidth()
{
button1.Width = FlowPanel.Width - FlowPanel.Padding.Horizontal - button1.Margin.Horizontal;
}

How to make group box text alignment center in win forms?

I am using a group box and there are several controls inside this.
My requirement is to set the group box title to the middle of the group box instead of Left.
How?
you can extend the group box class like this.
public class CustomGrpBox : GroupBox
{
private string _Text = "";
public CustomGrpBox()
{
//set the base text to empty
//base class will draw empty string
//in such way we see only text what we draw
base.Text = "";
}
//create a new property a
[Browsable(true)]
[Category("Appearance")]
[DefaultValue("GroupBoxText")]
[DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)]
public new string Text
{
get
{
return _Text;
}
set
{
_Text = value;
this.Invalidate();
}
}
protected override void OnPaint(PaintEventArgs e)
{
//first let the base class to draw the control
base.OnPaint(e);
//create a brush with fore color
SolidBrush colorBrush = new SolidBrush(this.ForeColor);
//create a brush with back color
var backColor = new SolidBrush(this.BackColor);
//measure the text size
var size = TextRenderer.MeasureText(this.Text, this.Font);
// evaluate the postiong of text from left;
int left = (this.Width - size.Width) / 2;
//draw a fill rectangle in order to remove the border
e.Graphics.FillRectangle(backColor, new Rectangle(left, 0, size.Width, size.Height));
//draw the text Now
e.Graphics.DrawString(this.Text, this.Font, colorBrush, new PointF(left, 0));
}
}
add the above class into your project and use "CustomGrpBox" instead of "GroupBox" which will be created after build in your tool box.
and you can set the text any time like this.
private void Form2_Load(object sender, EventArgs e)
{
customGrpBox1.Text = "Hello World";
}
it will look like this in design time visual studio
Unfortunately, you may set the title on the right by using the RightToLeft property, but there is no property to set it in the middle.
What you can do is to set an empty Text in your GroupBox, create a Label with the title and put that label above the GroupBox (with the same parent).
You may do it dynamically at form initialization by calling following procedure:
private void CenterGroupBoxTitle(GroupBox groupbox)
{
Label label = new Label() ;
label.Text = groupbox.Text ;
groupbox.Text = "" ;
label.Left = groupbox.Left+(groupbox.Width-label.Width)/2 ;
label.Top = groupbox.Top + 2 ; // 2 is an example : adjust the constant
label.Parent = groupbox.Parent ;
label.BringToFront() ;
}
Try to create a custom control using Panel as container and draw border around this, you can then have full control of the title's alignment.
If you would like a simple approach, you can leave the groupbox's title as empty text, and then place a label at the center position of the groupbox. You can also define this as user-control so you wouldn't need to do this repeatedly.
Not an eloquent solution, but if you have a simple GroupBox, that stays the( same size, you can just pad the beginning, and the end with spaces.
example : GroupBox.Text = " This is the groupbox text ";
The amount of padding of space's will depend on the length of the box.
Of course you'll lose some of the GroupBox's beginning and end lines on top, and if that's important, then Answer 3 seems like a good solution.

C# Resize textbox to fit content

I'm writing a program where the user should be able to write text in a TextBox. I'd like the TextBox to resize itself, so it fits to the content.
I've tried the following:
private void textBoxTitle_TextChanged(object sender, TextChangedEventArgs e)
{
System.Drawing.Font myFont = new System.Drawing.Font("Verdana", 8);
System.Drawing.SizeF mySize = e.Graphics.MeasureString("This is a test", myFont);
this.textBoxTitle.Width = (int)Math.Round(mySize.Width, 0);
}
I get an error saying that Graphics doesn't work for TextChangedEventArgs. Is there another way I can resize the TextBox?
You should try a code something like below. It has worked for me well.
private void textBox1_TextChanged(object sender, EventArgs e)
{
Size size = TextRenderer.MeasureText(textBox1.Text, textBox1.Font);
textBox1.Width = size.Width;
textBox1.Height = size.Height;
}
For more information refer to TextRenderer.MeasureText()
I am adding this answer as I do not see the fixed width aspect of a textbox being discussed in any of the other. If you have a fixed width for your textbox, and you want to adjust only its height you can do something like the following:
Something like this gives the height of the text as how it is drawn in the multiline wordwrapped textbox itself:
SizeF MessageSize = MyTextBoxControl.CreateGraphics()
.MeasureString(MyTextBoxControl.Text,
MyTextBoxControl.Font,
MyTextBoxControl.Width,
new StringFormat(0));
I am not sure what StringFormat should be but the values StringFormatFlags do not seem to apply to a default TextBox make up.
Now with MessageSize.Height you know the height of the text in the textbox.
I had the same problem and I solved it in a simpler way.
I used the AutoSize property of a Label control.. I added an invisible label to my form, set its AutoSize property True. When the I need to change the size of my TextBox I use this code:
MyLabel.Text = MyTextBox.Text;
MyTextBox.Size = MyLabel.Size;
I set the Maximum and Minimum Size of the label for better results.
Have Fun
Your binding to the wrong event, and you cannot use the graphics object in the TextChangedEventArgs object.
Try using the TextChanged event. The following snippet is working:
public Form1()
{
InitializeComponent();
this.textBox1.TextChanged += new EventHandler(textBox1_TextChanged);
}
void textBox1_TextChanged(object sender, EventArgs e)
{
System.Drawing.SizeF mySize = new System.Drawing.SizeF();
// Use the textbox font
System.Drawing.Font myFont = textBox1.Font;
using (Graphics g = this.CreateGraphics())
{
// Get the size given the string and the font
mySize = g.MeasureString(textBox1.Text, myFont);
}
// Resize the textbox
this.textBox1.Width = (int)Math.Round(mySize.Width, 0);
}
}
first, create method to Make the TextBox fit its contents.
private void AutoSizeTextBox(TextBox txt)
{
const int x_margin = 0;
const int y_margin = 2;
Size size = TextRenderer.MeasureText(txt.Text, txt.Font);
txt.ClientSize =
new Size(size.Width + x_margin, size.Height + y_margin);
}
then with the TextChanged event handler calls AutoSizeTextBox() function to make the TextBox fit its text when the text changes.
private void txtContents_TextChanged(object sender, EventArgs e)
{
AutoSizeTextBox(sender as TextBox);
}
That’s all, for more info:
resize-a-textbox-to-fit-its-text
You will need to use the CreateGraphics() method of the form to create the Graphics instance to measure the string on.
The TextChangedEventArgs class does not have a Graphics property, that is a property of the PaintEventArgs class passed in to the Paint event handler
Try this:
using System.Drawing;
...
private void textBoxTitle_TextChanged(object sender, TextChangedEventArgs e)
{
// Determine the correct size for the text box based on its text length
// get the current text box safely
TextBox tb = sender as TextBox;
if (tb == null) return;
SizeF stringSize;
// create a graphics object for this form
using(Graphics gfx = this.CreateGraphics())
{
// Get the size given the string and the font
stringSize = gfx.MeasureString(tb.Text, tb.Font);
}
// Resize the textbox
tb.Width = (int)Math.Round(stringSize.Width, 0);
}
Essentially you create your own Graphics object for the form, then measure it based on the text and font of the TextBox. The using will properly dispose the Graphics object - your previous code would have leaked horribly!
Whatever the aim is.
If the size of the textbox should be dynamically set up based on the string, which should be the text inside this box, there is no nice option.
Reasons : MeasureString uses usual string formatters as delimiters for its own width and height.
Means, carriage return and line feed are parsed, too. Resulting in a sizeF.Width and sizeF.Height.
Depending on the string( and its font and number of lines ) these both variables can carry values, which are sometimes useless to be used as width/height values of a textbox ( because they can be bigger than the parentform's values and this would resize the textbox to a size, with left and bottom borders beyond those of the parent form).
Some solutions are still available, depending on the aim, one would like to achieve.
One idea would be :
Create a textbox in designer, size = 100 X 100. enable word-wrapping.
In the OnTextChanged event handler of the textbox, we just resize the textbox's width to a value, defined by ourself (e.g. parentform.Width or another hard value ).
This would cause the word wrap to recalculate the string in the textbox and this would rearrange all the characters inside the textbox, because word wrap is enabled.
The height of the textbox could can be set hard to parentform.Height, for example.
BUT,
better : set the height dynamically,based on the Y value of the ReturnValue (Point) of the method texbox.GetPositionFromCharIndex(textbox.TextLength -1 ).
Then, with Math.Min() determine, which is smaller ( either parentform.Height or Point.Y ) , and reset the textbox size to new Size(previousDeterminedWidth, nowDeterminedHeight).
Please keep in mind ( if scrollbars are enabled ) to add about 17 pixs to Your width calculation.
Best regards
Did you try to set yourTextBox.AutoSize = true;?
This property may be hidden in the GUI designer, but you can set it in the form constructor right after InitializeComponent(); call.
Graphics.Measure string you can do o PaintEventArgs, not on TextChangedEventArgs
What I think you want is this
System.Drawing.Font myFont = new System.Drawing.Font("Verdana", 8);
Graphics graphics = this.CreateGraphics();
SizeF textSize = graphics.MeasureString("This is a test", myFont);
The problem is that you just cannot create a Graphics object by simply allocating it since it has no public constructor, so you should better go and use TextRenderer.MeasureText, as done in http://msdn.microsoft.com/en-us/library/y4xdbe66.aspx
TextRenderer is less accurate because it uses GDI and Graphics uses GDI+, so maybe you should leave a little margin on the value you get from the Width property.
Hope this helps

Label grow from right to left

I have a label on my form which is on the right of the form. This label loads a dynamic text.
Sometimes the text that it loads is too long and the text crosses the border of the form, that is some of the text is out of the form.
I want to make the label to grow from right to left instead of left to right. How do I achieve this?
I solved this by setting the label
AutoSize property to false,
TextAlign to MiddleRight,
an Anchor to the right.
Notice that the label size itself is not growing with the text, but you can handle it by giving it enough width to fit the content. The visual effect is the same.
My problem here was that my label was in a panel, and anything I did wasn't working.
What I did was to place the label in a TableLayoutPanel control and set the TableLayoutPanel's RightToLeft property to True; this did the trick.
You can't make it "grow from right to left", but you can assign it's Left property so that it won't go out of the form:
label1.Text = "some dynamic text here...";
if (label1.Right > this.Width)
label1.Left = this.Width - label1.Width;
If the design allows it, you can also double its height so that the text will span two lines.
You can use the TableLayoutPanel or other compatible container control, but instead setting RightToLeft property for the container set Dock="Right" for the label
Setting RightToLeft property does not always give the expected results as for some string formats the string is modified changing the order of the words.
you can Write it:
public enum Leftorright { left,right}
private Leftorright _LeftToRight = Leftorright.left;
public Leftorright LeftToRight
{
get { return _LeftToRight; }
set { _LeftToRight = value; }
}
protected override void OnTextChanged(EventArgs e)
{
int oldWidth;
oldWidth = this.Width;
base.OnTextChanged(e);
if (LeftToRight == Leftorright.right && this.Width != oldWidth)
{
this.Left = this.Left - this.Width + oldWidth;
}
}
using System.Windows.Forms;
/// <summary>
/// The position of myLabel to the left of the otherControl component when entering
/// text "s".
/// You must set myLabel.AutoSize = true
/// </summary>
/// <param name="s">text</param>
void WriteText(string s)
{
int len = TextRenderer.MeasureText ( s, myLabel.Font ).Width;
myLabel.Left = otherControl.Left - 5 - len;
myLabel.Text = s;
}
Wrap the label inside a FlowLayoutPanel and set the following properties in the panel:
Anchor to right;
AutoSize to GrowAndShrink;
FlowDirection to RightToLeft

Categories

Resources