XNA resolution independence - c#

For some reason, everything I tried that was online about resolution independence doesn't really work the way I would want it to. Most of the solutions suggest a way to get the width and height and then use a class with them, but the result is always a cutoff picture(too big picture) or a picture in the top left corner with smaller height and width than those of the screen.
P.S. The game is in fullscreen, but we tried windowed and it didn't work either.

This is actually a pretty simple fix. Basically, create a RenderTarget object somewhere and do all your drawing to that object, then resize that to the screen.
Use GraphicsDevice.SetRenderTarget(target) to change the render target, then do all your drawing operations, then change it back to the back buffer afterwards by setting it to null. RenderTargets actually derive from Texture2D, so you can use it in as an argument, such as: SpriteBatch.Draw(renderTarget, Viewport.Bounds, Color.White), and this will stretch it to fit the screen.

Related

How to change aspect ratio or resolution, without needing to rewrite all code Unity?

Recently I thought: "Let's set the 'resolution' from 16:9 to 16:9(1920x1080)" but i noticed that now all my positioning* code was off, and the size of pictures and text was way too small.
My problem now is, if I should just use the 16:9 aspect ratio or an fixed resolution (I don't know the benefits). But if I shouldn't use the aspect ratio, how to change the fixed resolution when the Project is ready, for example in the settings, without needing to rewrite all my code* and rescale all my images on the Canvas according to the resolution.
*For those of you who don't know what I mean with 'positioning', I mean setting the position of an Image on the Canvas, which obviously needs to be changed because the resolution is different. You could make something that detects your resolution and positions you image based on that, but idk if there is a better solution.
The best way to do this is during positioning ui using procentage also canvas Type which is displayed to resolution.
https://youtu.be/Tys6QWi9RpM
Solution on yt.

How to stretch the video completely

I am using axWindowsMediaPlayer and when I make the screen full, video is being shown but the player put 2 black block near side of video. I don't want these blocks.
I tried
axWindowsMediaPlayer1.stretchToFit = true;
but that didn't work. Because my video is 800*600 and my screen 1920*1080, the problem might be. Any way to solve this problem programatically? I don't want to resize video.
Thanks in advance.
AxWMPlayer does not support nonuniform stretching. So, you have to either:
- make the WMPlayer of normal desired size, stretch uniformly (StretchToFit=true) and live with the black margins if they show up
- make the WMPlayer oversized in Height or Width (so that it sticks out of the target space), stretch uniformly (StretchToFit=true). Due to the oversized WMPlayer, some of the video will be trucated (displayed outside of the space) but also the black margins will be truncated
Those two ways will mantain aspect ratio.
If you don't need aspect ratio kept, you may apply some ScalingTransform (WPF) or another similar effect to stretch the view afterwards. You will need to calculate coordinates properly, but the fact that WMP always centers the video and that you can read the video dimensions from IWMPMedia helps much.

Standard way of resizing DirectX control

I would like to know the standard method for resizing my DirectX control. A model is shown in the control, and I want it to be the same size after resize, only more of its environment should be visible.
I managed to do it with resetting the viewport and swapchain buffers, but I could do it another way too (moving the camera), and maybe others I didn't think of. I just don't know which is the "best" way.
Changing the viewport size should only show "more" of the viewing area as a matter of changing the aspect ratio. For instance, if the viewport doubles in width and height, the aspect ratio will be the same, therefore the same image will be shown, just larger.
In contrast, moving the camera will change the amount that is viewed, e.g. If you move the camera back, you will see more. However, this may not be what you are looking for. You are physically moving the camera to another location rather than simply changing the view properties.
What you are probably looking for is to change the camera projection properties, which would likely be done using "PerspectiveFovLH", the input for which is: ("field of view", "aspect ratio", "z near plane", "z far plane"). Widening the field of view (FOV) will allow you to see more of the scene. Changing the aspect ratio will scale that appropriately. Typically the aspect ratio should be the ratio between the screen width and height, and if you want a larger screen to show more overall, scale the FOV by the amount the screen has been re-sized.

Interactive Zooming into a 2D graphics bitmap in C#

I have made a program that reads voltage and current values of some diode curves from an xml file and draws them on screen (Just using plain 2D graphics and some simple commands like DrawCurve and stuff like that).
My main image frame is 800 by 800 pixels (you can see a smaller screenshot down below). Now I want to add a zoom function that when I hover the mouse over this image area, a flying smaller square pops up and zooms in + moves when I move the mouse over this area.
I have no idea how to approach this. Ofcourse I don't ask the full working code but please help me to get closer and closer!
For instance, can I make the zoom to work, without reading the curve data and painting real time? or there is no escape from it? How can I have a hovering image box when I move mouse over the orginal image?
Thanks!
Have you timed how long DrawCurve takes? Perhaps it's fast enough to do in real time. Don't forget, the GDI will clip the drawing primitives to the drawing area. You just need to set up a clipping rectangle as you move the mouse around.
To speed up the redraw, create the main window image (the one you pasted) as an off-screen bitmap, and just DrawImage the off-screen version to the window in the paint events. That way you reduce the impact of the DrawCurve.
Finally, to get good looking results, overload the OnPaintBackground (can't remember the name exactly but it's something like that) so it does nothing (not even call the base class) and do all your painting in the OnPaint method using a BufferedGraphics object.
Update
Your paint function might look like this:
OnPaint (...)
{
the_graphics_object.DrawImage (the background image);
the_graphics_object.Clip = new Region (new Rectangle (coords relative to mouse position));
the_graphics_object.TranslateTransform (drawing offset based on mouse position);
RenderScene (the_graphics_object, scale_factor); // draws grid and curve, etc
the_graphics_object.DrawRectangle (zoom view rectangle); // draw a frame around the zoomed view
}
This will produce a floating 'window' relative to the mouse position.
Typically, cases where redrawing can be time consuming, zooming is usually tackled by providing a "quick but ugly" implementation, alongside the "correct but slow" implementation. While the zoom operation is actively in progress (say, while the user has a slider clicked, or until a 50ms since the last change in zoom value has happened), you use the quick and ugly mode, so the user can see a preview of what the final image will be. Once they let go of the zoom slider (or whatever mechanism you provided), you can recalculate the image in detail. The quick version is usually calculated based on the original image that you are working with.
In your case, you could simply take the original image, work out the bounding box of the new, zoomed image, and scale the relevant part of the original image up to the full image size. If say 100ms has passed with no change in zoom, recalculate the entire image.
Examples of this kind of functionality are quite widespread: most fractal generators use exactly this technique, and even unrelated things like Google StreetView (which provides a very ugly distorted version of the previous image when you move around, until the actual image has downloaded).

How do I position lines exactly in C#

I do NOT want the system trying to scale my drawing, I want to do it entirely on my own as any attempt to squeeze/stretch the graphics will produce ugly results. The problem is that as the image gets bigger I want to add more detail rather than have it simply scale up.
Right now I'm looking at two sets of stripes. One is black/white, the other is black/white/white. The pen width is set to 1.
When the line is drawn horizontally it's correct. The same logic drawing vertical lines appears to be doing some antialiasing, bleeding the black onto the nearby white. The black/white/white doesn't look as good as the horizontal, the black/white looks more like medium++ gray/medium-- gray.
The same code is generating the coordinates in all cases, the transform logic is simply selecting what offset to apply where as I am only supporting orientations on the cardinals. Since there's no floating point involved I can't be looking at precision issues.
How do I get the system to leave my graphics alone???
(Yeah, I realize this won't work at very high resolution and eventually I'll have to scale up the lines. Over any reasonable on-screen zoom factor this won't matter, for printer use I'll have to play with it and see where I need to scale. The basic problem is that I'm trying to shoehorn things into too few pixels without just making blobs.)
Edit: There is no scaling going on. I'm generating a bitmap the exact size of the target window. All lines are drawn at integer coordinates. The recommendation of setting SmoothingMode to None changes the situation: Now the black/white/white draws as a very clear gray/gray/white and the black/white draws as a solid gray box. Now that this is cleaned up I can see some individual vertical lines that were supposed to be black are actually doing the same thing of drawing as 2-pixel gray bars. It's like all my vertical lines are off by 1/2 pixel--yet every drawing command gets only integers.
Edit again: I've learned more about the problem. The image is being drawn correctly but trashed when displayed to the screen. (Saving it to disk and viewing it on the very same monitor shows it drawn correctly.)
You really should let the system manage it for you. You have described a certain behavior that is specific to the hardware you are using. Given different hardware, the problem may not exist at all, or it may exist horizontally but not vertically, or may only exist at much smaller or much larger resolutions, etc. etc.
The basic problem you described sounds like the vertical lines are being drawn "between" vertical stacks of pixels, which is causing the system to draw an anti-aliased line. The alternative to anti-aliasing the line is to shift it. The problem with that is the lines will "jitter" or "jerk" if the image is moved around, animated, or scaled or transformed in any other way. Generally, jerk is MUCH less desirable than anti-aliasing because it is more distracting.
You should be able to turn off anti-aliasing using the SmoothingMode enum, or you could try to handle positioning yourself. Either way, you are trading anti-aliasing for jittery, jerky rendering during any movement or transformation.
Have a look at System.Drawing.Drawing2d.SmoothingMode. Setting it to 'Default' or 'None' should turn off anti aliasing when doing line drawing. If you're talking about scaling an image without anti aliasing effects, have a look at InterpolationMode. Specifically, you might wish to set it to 'Nearest-Neighbor' which will keep your rectangular blocks perfectly crisp. Note that you will see some odd effects if you scale your image by anything other than whole numbers.
Perhaps you need to align your lines on half-pixel coordinates? A one pixel line drawn at say x = 5 would be drawn on the center of the line, which means it would go from x = 4.5 to x = 5.5. If you want it to go from x = 4 to x = 5 then you'd need to set its coordinate to x = 4.5.
GDI+ has a property: http://msdn.microsoft.com/en-us/library/system.drawing.graphics.pixeloffsetmode.aspx that allows you to control this behavior.
Sounds like you need to change your application to tell the system it is DPI aware so scaling doesn't occur. Here's an article on doing that: http://msdn.microsoft.com/en-us/library/ms701681%28VS.85%29.aspx

Categories

Resources