stretching winform with graphics - c#

I'm writing a game using c#'s winforms,
When creating a Scene (holding graphics, objects, etc...) I'm transfering the form so the c'tor looks something like that:
public Scene(Form form)
{
_g = form.CreateGraphics();
RegisterFormEvents(form);
_gameObjects = new List<GameObject>();
Width = form.Width;
Height = form.Height;
}
Now I'm trying to add an option to show the game on full screen,
but when i'm trying to maximize the window it only prints graphics to the original Width x Height,
how can I strecth those?

You just have to listen to the SizeChanged event of the form. Whenever the size has changed you set the Width and Height properties of the scene to match the new dimensions.
So, somewhere in your code you should have the following:
// I assume that this code is in the code-behind of the form, so "this" is the form
this.SizeChanged += new EventHandler(FormSizeChanged);
and
private void FormSizeChanged(object sender, EventArgs e)
{
yourScene.Width = this.Width;
yourScene.Height = this.Height;
}

Related

Dynamically resize WinForms controls when Form is resized

I have a WinForms project on which I would like all of the controls to grow proportionally along with the form as the form is resized. This is what the form looks like in normal state: Normal State Form
I have tried setting the Anchor properties to their appropriate values given the location of each control on the form, and while it does move the controls, they remain the same size. I tried using the AutoSize property, but also to no avail. Here is what the form looks like after being maximized with the Anchor properties set: Maximized Form
I also tried using a formula from Shaun Halverson to dynamically resize everything but it does not relocate the control properly, and I can't seem to figure out why. Here is the code I used to try and resize dynamically:
private void Main_Load(object sender, EventArgs e)
{
originalFormSize = new Rectangle(this.Location.X, this.Location.Y, this.Size.Width, this.Size.Height);
submitBtnOriginal = new Rectangle(submitButton.Location.X, submitButton.Location.Y, submitButton.Width, submitButton.Height);
}
private void Main_Resize(object sender, EventArgs e)
{
resizeControl(submitBtnOriginal, submitButton);
}
private void resizeControl(Rectangle r, Control c)
{
float xRatio = (float)(this.Width) / (float)(originalFormSize.Width);
float yRatio = (float)(this.Height) / (float)(originalFormSize.Height);
int newWidth = (int)(r.Width * xRatio);
int newHeight = (int)(r.Height * yRatio);
int newX = (int)(r.Width * xRatio);
int newY = (int)(r.Height * yRatio);
c.Location = new Point(newX, newY);
c.Size = new Size(newWidth, newHeight);
}
When I run this code, it moves the button to the opposite corner of the form, but it resizes it properly.
This would obviously be quite redundant given that I have to get an original size for every control I want to resize, but I would be fine with that if I could get dynamic resizing to work. I am surprised that this is not a more common problem, and I couldn't find hardly anything on this specific topic other than to use the Anchor and Dock properties. Is there an easy way to do this that I am missing? Is this a more difficult problem than it seems?
Put TextBox anchor property values as Top, Bottom, Left, Right and resize the form. That should work.

How to develop win form application for the system with the resolution of 1080*1920

I want to develop a windows form application where the destination system is having screen resolution of 1080x1920. but my system is not accepting that resolution . even i cant set my winform size to 1080x1920.
can anybody help me out to solve this problem
This works for me. This is the Load event for the form (you can generate this by double clicking the form in the designer). In this event we check the current dimensions of the screen containing the form. Then we set the form size to match. We also move the form's position to 0, 0 so it doesn't clip off the screen.
//the name of this function will be different for you.
//generate this function by double clicking the form in designer.
//the code inside the function is what you're interested in.
private void MainForm_Load(object sender, EventArgs e)
{
Rectangle screenSize = Screen.GetBounds(this); //find out the current screen size
this.Top = 0; //move the form to top
this.Left = 0; //move the form to left
this.Width = screenSize.Width; //set form width to screen width
this.Height = screenSize.Height; //set form height to screen height
}
EDIT: Also, why not just maximize?
this.WindowState = FormWindowState.Maximized;

Why is the windows forms auto-resizing the height when im trying to center a usercontrol on it?(C#)

So basically what I'm trying to do is center a PictureBox control on an empty windows form with specified size, given that the size of the form is actually always bigger than that of my control.However, whenever I'm am trying to center it(what i mean is actually have equal distances from the margins of the form,equal distance for the width and equal distances for the height since the height and width aren't equal in my code.Ex: width=700 and Height=500), between the bottom of my form and the bottom of my control there is less space than between the top of the form and the top of the control.
Here is a picture to illustrate the issue:
https://i.stack.imgur.com/URozj.png
Here is the entire code,please don't critic the reasoning behind how it's made, i would just like to know why the form resizes or puts my control at the bottom if i add it to the form.
public static class Engine
{
public static Graphics G;
public static Bitmap Map;
public static PictureBox Canvas;
public static void Initialize_mystuff(int width, int height)
{
Map = new Bitmap(width, height);
G = Graphics.FromImage(Map);
Canvas = new PictureBox();
Canvas.Size = new Size(Map.Width, Map.Height);
Canvas.BorderStyle = BorderStyle.FixedSingle;
Canvas.BackgroundImage = Map;
}
public static Point CenterUControl(Size Parent, Size Child)
{
return new Point(Parent.Width / 2 - Child.Width / 2, Parent.Height / 2 - Child.Height / 2);
}
}
So above is the code for where I initialize everything I'm working with and also have a function to return me the location of where the object should be centered relative to it's parent.And below is the code where I call the initialize and center functions in the forms constructor.
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
this.SuspendLayout();
Engine.Initialize_mystuff(400,400);
this.Controls.Add(Engine.Canvas);
this.Size = new Size(700, 500);
Engine.Canvas.Location=Engine.CenterUControl(this.Size, Engine.Canvas.Size);
this.ResumeLayout();
}
private void Form1_Load(object sender, EventArgs e)
{
}
}
Also the AutoSize property of the form is set to false.
A form's size include the borders and non-client areas (title bar, etc) of the form. Use the ClientSize property instead when using the dimensions of the form:
Engine.Canvas.Location = Engine.CenterUControl(this.ClientSize, Engine.Canvas.Size);

Set x and y co ordinates in Draw image dynamically

I am resizing a image using DrawImage.
Graphics.DrawImage(SourceImage,0,0,200,200);
Here the source image starts with co ordinates 0.
Suppose i need to calculate the x and y coordinates dynamically how to do i go about it?
By default, the image should start with location 20(ie; x) and 20(ie y).
If i resize the form,it should proportionally calculate according to the resized imaged,that means,if for default it is 20 than for form resize how much?
Thanks
You can register to ResizeEnd event of the form and can redraw the image. Something like;
public Form1()
{
InitializeComponent();
this.ResizeEnd += new EventHandler(Form1_ResizeEnd);
}
void Form1_ResizeEnd(object sender, EventArgs e)
{
//draw the image again using the related calculation
}
From your question it is not clear how the size of the form relates to the desired coordinates.
A form has a ClientRectangle property that you can use to calculate the coordinates with. If you want to display the image in the bottom-right corner for example, you would:
protected override void OnPaint(PaintEventArgs e)
{
int x = this.ClientRectangle.Width - 200;
int y = this.ClientRectangle.Height - 200;
e.Graphics.DrawImage(SourceImage, x, y, 200, 200);
}
I assume the DrawImage code is in a Paint event handler, you could then either
use SetStyle(ControlStyles.ResizeRedraw, true); in the form constructor, so Paint is called when the form is resized
add an event handler for the Resize event and call Invalidate(); yourself

A PictureBox Problem

I have a problem:
I have 3 picture boxes with 3 different images as in Image
what can i set to pictureBox3 so both images look same.....
EDITED:
I want to move pictureBox3 on pictureBox2,
So there is no Option to merge them to single image
Make sure the image in pictureBox3 is transparent. Set the BackColor to transparent. In code, set the Parent property of the pictureBox3 to be pictureBox2. Adjust the Location coordinates of pictureBox3 since they will be relative to the coordinates of pictureBox2 once you've changed the Parent.
private void Form1_Load(object sender, EventArgs e)
{
pictureBox3.Parent = pictureBox2;
pictureBox3.Location =
new Point(
pictureBox3.Location.X
- pictureBox2.Location.X,
pictureBox3.Location.Y
- pictureBox2.Location.Y);
}
In designer you will not see the transparency, but at runtime you will.
Update
In the image, the left side shows the designer view, the right side is the runtime version.
Another update
I really don't understand how it would be possible that this doesn't work for you. I suppose there must be something we are doing different. I'll describe the exact steps to take to create a working sample. If you follow the exact same steps, I wonder if we'll get the same results or not. Next steps describe what to do and use two images I found on the net.
Using Visual Studio 2008, create a New Project using template Windows Forms Application. Make sure the project is targeted at the .NET Framework 3.5.
Set the Size of the Form to 457;483.
Drag a PictureBox control onto the form. Set its Location to 0;0 and its Size to 449;449.
Click the ellipsis besides its Image property, click the Import... button and import the image at http://a.dryicons.com/files/graphics_previews/retro_blue_background.jpg (just type the URL in the File name text box and click Open). Then click OK to use the image.
Drag another PictureBox onto the form, set its Location to 0;0 and its Size to 256;256. Also set its BackColor property to Transparent.
Using the same method as described above, import image http://www.axdn.com/redist/axiw_i.png which is a transparent image.
Now place the following code in the form's OnLoad event handler:
private void Form1_Load(object sender, EventArgs e)
{
pictureBox2.Parent = pictureBox1;
}
That's it! If I run this program I get a transparent image on top of another image.
I'll add another example that according to the updated requirement allows for moving image3.
To get it working, put an image with transparency in Resources\transp.png
This uses the same image for all three images, but you can simply replace transparentImg for image1 and image2 to suitable images.
Once the demo is started the middle image can be dragged-dropped around the form.
public partial class Form1 : Form
{
private readonly Image transparentImg; // The transparent image
private bool isMoving = false; // true while dragging the image
private Point movingPicturePosition = new Point(80, 20); // the position of the moving image
private Point offset; // mouse position inside the moving image while dragging
public Form1()
{
InitializeComponent();
//
// pictureBox1
//
this.pictureBox1.Location = new System.Drawing.Point(0, 0);
this.pictureBox1.Name = "pictureBox1";
this.pictureBox1.Size = new System.Drawing.Size(231, 235);
this.pictureBox1.TabIndex = 0;
this.pictureBox1.TabStop = false;
this.pictureBox1.Paint += new System.Windows.Forms.PaintEventHandler(this.pictureBox1_Paint);
this.pictureBox1.MouseDown += new System.Windows.Forms.MouseEventHandler(this.pictureBox1_MouseDown);
this.pictureBox1.MouseMove += new System.Windows.Forms.MouseEventHandler(this.pictureBox1_MouseMove);
this.pictureBox1.MouseUp += new System.Windows.Forms.MouseEventHandler(this.pictureBox1_MouseUp);
this.Controls.Add(this.pictureBox1);
transparentImg = Image.FromFile("..\\..\\Resources\\transp.png");
}
private void pictureBox1_Paint(object sender, PaintEventArgs e)
{
var g = e.Graphics;
g.DrawImageUnscaled(transparentImg, new Point(20, 20)); // image1
g.DrawImageUnscaled(transparentImg, new Point(140, 20)); // image2
g.DrawImageUnscaled(transparentImg, movingPicturePosition); // image3
}
private void pictureBox1_MouseDown(object sender, MouseEventArgs e)
{
var r = new Rectangle(movingPicturePosition, transparentImg.Size);
if (r.Contains(e.Location))
{
isMoving = true;
offset = new Point(movingPicturePosition.X - e.X, movingPicturePosition.Y - e.Y);
}
}
private void pictureBox1_MouseMove(object sender, MouseEventArgs e)
{
if (isMoving)
{
movingPicturePosition = e.Location;
movingPicturePosition.Offset(offset);
pictureBox1.Invalidate();
}
}
private void pictureBox1_MouseUp(object sender, MouseEventArgs e)
{
isMoving = false;
}
}
This code will do the trick:
using (Graphics g = Graphics.FromImage(pictureBox1.Image))
{
g.DrawImage(pictureBox2.Image,
(int)((pictureBox1.Image.Width - pictureBox2.Image.Width) / 2),
(int)((pictureBox1.Image.Height - pictureBox2.Image.Height) / 2));
g.Save();
pictureBox1.Refresh();
}
It will draw the image from pictureBox2 on the existing image of pictureBox1.
For starters, set the BackColor property of PictureBox3 to Transparent. This should work in almost all cases.
You should also use an image with a transparent background instead of white so you do not have the white borders around your purple circle. (Recommended image format: PNG)
Update
Following the replies I got, it appears setting the BackColor to Transparent doesn't work. In that case, it's best you handle the Paint event of the PictureBox and do the painting of the new image yourself as Albin suggested.
You might do some hack by overriding OnPaint and stuff, example here.
But I'd recommend to merge the pictures in pictureBox2 and 3 into a single image before displaying them in a single pictureBox.

Categories

Resources