Allegro.cc - Online Community

Allegro.cc Forums » Allegro Development » [a5] Multisampling not working in Direct3D

This thread is locked; no one can reply to it. rss feed Print
[a5] Multisampling not working in Direct3D
Mark Oates
Member #1,146
March 2001
avatar

I think I may have reported this issue a while back, but I can't remember exactly. I apologize if this is a known issue. Essentially, multisampling does not work in Direct3D mode. I'm using the latest release of 5.1.10.

With Direct3D
https://d1cxvcw9gjxu2x.cloudfront.net/attachments/609419

With OpenGL
https://d1cxvcw9gjxu2x.cloudfront.net/attachments/609418

Here is a program that demonstrates the issue (using ALLEGRO_DIRECT3D_INTERNAL)

#SelectExpand
1 2#include <allegro5/allegro.h> 3 4#include <allegro5/allegro_color.h> 5#include <allegro5/allegro_primitives.h> 6 7 8int main(int argc, char **argv()) 9{ 10 al_init(); 11 12 al_init_primitives_addon(); 13 14 al_set_new_display_option(ALLEGRO_SAMPLE_BUFFERS, 1, ALLEGRO_SUGGEST); 15 al_set_new_display_option(ALLEGRO_SAMPLES, 8, ALLEGRO_SUGGEST); 16 17 al_set_new_display_flags(ALLEGRO_DIRECT3D_INTERNAL); 18 19 ALLEGRO_DISPLAY *display = al_create_display(1024, 600); 20 al_clear_to_color(al_color_name("black")); 21 22 al_draw_circle(500, 300, 200, al_color_name("white"), 5.0); 23 al_draw_line(200, 200, 700, 300, al_color_name("white"), 5.0); 24 25 al_flip_display(); 26 27 al_rest(3); 28 29 return 0; 30}

[edit: sorry had some screenshot issues, should be fixed now]

Edgar Reynaldo
Member #8,592
May 2007
avatar

I tried to reproduce your problem, but the OpenGL and the Direct3D one look the same to me, and they both look aliased. Note that I used ALLEGRO_DIRECT3D, not 'ALLEGRO_DIRECT3D_INTERNAL' as that shouldn't be visible anyway. Why are you trying to use _INTERNAL?

Here's the code I used :

#SelectExpand
1 2#include <allegro5/allegro.h> 3#include <allegro5/allegro_color.h> 4#include <allegro5/allegro_primitives.h> 5#include <allegro5/allegro_direct3d.h> 6 7#include <cstdio> 8 9int main(int argc, char **argv) { 10 11 if (!al_init()) {return 1;} 12 al_init_primitives_addon(); 13 al_install_keyboard(); 14 15 ALLEGRO_EVENT_QUEUE* queue = al_create_event_queue(); 16 if (!queue) {return 2;} 17 al_register_event_source(queue , al_get_keyboard_event_source()); 18 19 al_set_new_display_option(ALLEGRO_SAMPLE_BUFFERS, 1, ALLEGRO_SUGGEST); 20 al_set_new_display_option(ALLEGRO_SAMPLES, 8, ALLEGRO_SUGGEST); 21 22 int use_opengl = 0; 23 if (argc > 1) { 24 if (1 == sscanf(argv[1] , "%i" , &use_opengl)) { 25 26 } 27 else { 28 use_opengl = 0; 29 } 30 } 31 32 if (use_opengl) { 33 al_set_new_display_flags(ALLEGRO_OPENGL); 34 } 35 else { 36 al_set_new_display_flags(ALLEGRO_DIRECT3D); 37 } 38 39 ALLEGRO_DISPLAY *display = al_create_display(1024, 600); 40 if (!display) {return 2;} 41 al_register_event_source(queue , al_get_display_event_source(display)); 42 43 al_clear_to_color(al_color_name("black")); 44 al_draw_circle(500, 300, 200, al_color_name("white"), 5.0); 45 al_draw_line(200, 200, 700, 300, al_color_name("white"), 5.0); 46 al_flip_display(); 47 48 bool quit = false; 49 while (!quit) { 50 ALLEGRO_EVENT ev; 51 al_wait_for_event(queue , &ev); 52 if (ev.type == ALLEGRO_EVENT_KEY_DOWN && ev.keyboard.keycode == ALLEGRO_KEY_ESCAPE) {quit = true;} 53 if (ev.type == ALLEGRO_EVENT_DISPLAY_CLOSE) {quit = true;} 54 } 55 return 0; 56}

{"name":"609420","src":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/a\/1\/a1b96f63099bc65d333f5b6ca484ba5e.png","w":1036,"h":632,"tn":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/a\/1\/a1b96f63099bc65d333f5b6ca484ba5e"}609420

Mark Oates
Member #1,146
March 2001
avatar

Having dug deeper into the issue, it seems like I have some dated drivers (2012) for this onboard graphic card (Intel HD 4000). My laptop won't let me update to the latest drivers (2015) due to a custom driver for this specific model of laptop (Sony Vaio Z Series).

But, the laptop does come with an external graphics card, an AMD Radeon HD 7670M. With the Radeon in use, it does render multisampling as expected but the window doesn't show up on the desktop when created. According to al_get_window_position a newly created ALLEGRO_DISPLAY is placed all the way at (32767, 32767), so I have to al_set_window_position to move it back in place.

It's kind of a clusterfuck. ;)

Attached are screenshots using the Radeon card.

Thomas Fjellstrom
Member #476
June 2000
avatar

So that window positioning bug is still there? sigh I thought it was gone.

--
Thomas Fjellstrom - [website] - [email] - [Allegro Wiki] - [Allegro TODO]
"If you can't think of a better solution, don't try to make a better solution." -- weapon_S
"The less evidence we have for what we believe is certain, the more violently we defend beliefs against those who don't agree" -- https://twitter.com/neiltyson/status/592870205409353730

SiegeLord
Member #7,827
October 2006
avatar

It won't be gone until somebody fixes it :P.

"For in much wisdom is much grief: and he that increases knowledge increases sorrow."-Ecclesiastes 1:18
[SiegeLord's Abode][Codes]:[DAllegro5]:[RustAllegro]

Edgar Reynaldo
Member #8,592
May 2007
avatar

There can't be that many places a window is registered and created. (On Windows I mean) Fix it each time it is and you're done.

Also a simple hack would be to alter al_create_display to center the window after creation.

beoran
Member #12,636
March 2011

Let the person who is using Allegro on Windows make the first patch. ;)

Edgar Reynaldo
Member #8,592
May 2007
avatar

Allegro Git 5.1.X said:

win\wwindow.c#SelectExpand
125 126HWND _al_win_create_window(ALLEGRO_DISPLAY *display, int width, int height, int flags) 127{ 128 HWND my_window; 129 DWORD style; 130 DWORD ex_style;
131 int pos_x, pos_y;
132 bool center = false; 133 ALLEGRO_DISPLAY_WIN *win_display = (ALLEGRO_DISPLAY_WIN *)display; 134 WINDOWINFO wi; 135 int lsize, rsize, tsize, bsize; // left, right, top, bottom border sizes 136 137 wi.cbSize = sizeof(WINDOWINFO); 138 139 display_flags_to_window_styles(flags, &style, &ex_style); 140 141 al_get_new_window_position(&pos_x, &pos_y); 142 if ((flags & ALLEGRO_FULLSCREEN) || (flags & ALLEGRO_FULLSCREEN_WINDOW)) { 143 pos_x = pos_y = 0; 144 } 145 else if (pos_x == INT_MAX) { 146 pos_x = pos_y = 0; 147 center = true; 148 } 149 150 if (center) { 151 _al_win_get_window_center(win_display, width, height, &pos_x, &pos_y); 152 } 153 154 my_window = CreateWindowEx(ex_style, 155 L"ALEX", L"Allegro", style, 156 pos_x, pos_y, width, height, 157 NULL,NULL,window_class.hInstance,0);

Uninitialized values for pos_x and pos_y cause the problem. :P

{"name":"4179768.jpg","src":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/0\/4\/046208b5daa5779b471042af34eb0c8a.jpg","w":400,"h":300,"tn":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/0\/4\/046208b5daa5779b471042af34eb0c8a"}4179768.jpg

Dude. A monkey could've fixed that. Wait. Maybe I am a monkey! :o

Attached is a patch https://www.allegro.cc/files/attachment/609426

#SelectExpand
1 src/win/wwindow.c | 13 +++++-------- 2 1 file changed, 5 insertions(+), 8 deletions(-) 3 4diff --git a/src/win/wwindow.c b/src/win/wwindow.c 5index a18acea..b0767bc 100644 6--- a/src/win/wwindow.c 7+++ b/src/win/wwindow.c 8@@ -128,8 +128,9 @@ HWND _al_win_create_window(ALLEGRO_DISPLAY *display, int width, int height, int 9 HWND my_window; 10 DWORD style; 11 DWORD ex_style; 12- int pos_x, pos_y; 13- bool center = false; 14+ int pos_x = 0; 15+ int pos_y = 0; 16+// bool center = false;// center windows automatically for now 17 ALLEGRO_DISPLAY_WIN *win_display = (ALLEGRO_DISPLAY_WIN *)display; 18 WINDOWINFO wi; 19 int lsize, rsize, tsize, bsize; // left, right, top, bottom border sizes 20@@ -142,12 +143,8 @@ HWND _al_win_create_window(ALLEGRO_DISPLAY *display, int width, int height, int 21 if ((flags & ALLEGRO_FULLSCREEN) || (flags & ALLEGRO_FULLSCREEN_WINDOW)) { 22 pos_x = pos_y = 0; 23 } 24- else if (pos_x == INT_MAX) { 25- pos_x = pos_y = 0; 26- center = true; 27- } 28- 29- if (center) { 30+ else { 31+ // window, center for now, unless we can remember the old position somehow 32 _al_win_get_window_center(win_display, width, height, &pos_x, &pos_y); 33 }

beoran
Member #12,636
March 2011

Thanks for looking into this! However ...

 al_get_new_window_position(&pos_x, &pos_y);

...should initialize those variables. Most likely the problem in in that function. The rabbit hole goes deeper...

Edit:

It turns out al_get_new_window_position sets those values to INT_MAX by default!
This means that an al_set_new_window_position(0, 0) or whatever would be needed somewhere (but where?) to fix this.

I also noticed that in wwindow.c we don't check properly the return values of GetWindowRect()and SetWindowRect() for success. Hilarity ensues! :p

Edgar Reynaldo
Member #8,592
May 2007
avatar

Edit2
I totally didn't see that call to al_get_new_window_position. :o

Wasn't aware that function existed. Now you're gonna have to store new_win_x and new_win_y somewhere and use those instead.

Edit
We don't want 0,0 as the default though, rather to center the window or put it into its last known location.

Thomas Fjellstrom
Member #476
June 2000
avatar

We don't want 0,0 as the default though, rather to center the window or put it into its last known location.

If a custom position isn't set, we should let the window manager place the window.

--
Thomas Fjellstrom - [website] - [email] - [Allegro Wiki] - [Allegro TODO]
"If you can't think of a better solution, don't try to make a better solution." -- weapon_S
"The less evidence we have for what we believe is certain, the more violently we defend beliefs against those who don't agree" -- https://twitter.com/neiltyson/status/592870205409353730

Edgar Reynaldo
Member #8,592
May 2007
avatar

Well you have to pass CreateWindow a certain value to use default positioning, CW_USEDEFAULT for the x value of the window.

x [in]

Type: int

The initial horizontal position of the window. For an overlapped or pop-up window, the x parameter is the initial x-coordinate of the window's upper-left corner, in screen coordinates. For a child window, x is the x-coordinate of the upper-left corner of the window relative to the upper-left corner of the parent window's client area. If this parameter is set to CW_USEDEFAULT, the system selects the default position for the window's upper-left corner and ignores the y parameter. CW_USEDEFAULT is valid only for overlapped windows; if it is specified for a pop-up or child window, the x and y parameters are set to zero.
y [in]

Type: int

The initial vertical position of the window. For an overlapped or pop-up window, the y parameter is the initial y-coordinate of the window's upper-left corner, in screen coordinates. For a child window, y is the initial y-coordinate of the upper-left corner of the child window relative to the upper-left corner of the parent window's client area. For a list box, y is the initial y-coordinate of the upper-left corner of the list box's client area relative to the upper-left corner of the parent window's client area.

If an overlapped window is created with the WS_VISIBLE style bit set and the x parameter is set to CW_USEDEFAULT, then the y parameter determines how the window is shown. If the y parameter is CW_USEDEFAULT, then the window manager calls ShowWindow with the SW_SHOW flag after the window has been created. If the y parameter is some other value, then the window manager calls ShowWindow with that value as the nCmdShow parameter.

beoran
Member #12,636
March 2011

They are defines as followed in windows:

#define CW_USEDEFAULT     ((int)0x80000000) /* 2147483648 */
#define INT_MAX           2147483647

That's quite suspicious, I guess the current Allegro code happens to work "by accident" but not in all cases?

Elias
Member #358
May 2000

Well, we never pass INT_MAX to Windows from what I see...

But this is very suspicious: https://github.com/liballeg/allegro5/blob/HEAD/src/win/d3d_disp.cpp#L1251

Why would the internal D3D code ever call al_set_new_window_position which is our user API function to set a window position? Even if it's just for the case that INT_MAX was passed by the user it seems wrong to overwrite that.

--
"Either help out or stop whining" - Evert

Mark Oates
Member #1,146
March 2001
avatar

As a workaround, I tried positioning the window in the center of the screen by using al_get_monitor_info and al_set_window_position, but the numbers returned by al_get_monitor_info not sane. :-/ It was the same with the ALLEGRO_OPENGL flag or not.

Also, the al_get_new_window_position did not match the al_get_window_position after creation. All of them were crazy values.

{"name":"609427","src":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/b\/e\/be6d0bb7cc13f5e13cc404812c6fddb4.png","w":1513,"h":837,"tn":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/b\/e\/be6d0bb7cc13f5e13cc404812c6fddb4"}609427

#SelectExpand
1#include <allegro5/allegro.h> 2#include <allegro5/allegro_color.h> 3#include <allegro5/allegro_primitives.h> 4#include <iostream> 5 6int main(int argc, char **argv()) 7{ 8 al_init(); 9 10 al_init_primitives_addon(); 11 12 int newx, newy; 13 al_get_new_window_position(&newx, &newy); 14 std::cout << "al_get_new_window_position(" << newx << ", " << newy << ")" << std::endl; 15 16 ALLEGRO_DISPLAY *display = al_create_display(1024, 600); 17 18 ALLEGRO_MONITOR_INFO monitor_info; 19 al_get_monitor_info(0, &monitor_info); 20 std::cout << "ALLEGRO_MONITOR_INFO(" << monitor_info.x1 << ", " << monitor_info.y1 21 << ", " << monitor_info.x2 << ", " << monitor_info.y2 << ")" << std::endl; 22 23 int winx, winy; 24 al_get_window_position(display, &winx, &winy); 25 std::cout << "al_get_window_position(" << monitor_info.x2 << ", " << monitor_info.y2 << ")" << std::endl; 26 27 28 29 al_clear_to_color(al_color_name("white")); 30 al_draw_filled_rectangle(300, 300, 500, 380, al_color_name("orange")); 31 al_flip_display(); 32 33 al_rest(300); 34 35 return 0; 36}

It could totally just be my computer, guys. Unless anybody else has reported these bugs. I can't update any drivers, so I can't eliminate that possibility.

beoran
Member #12,636
March 2011

Even if your drivers are a bit weird, Allegro should do something sensible, or as sensible as possible in your case. Actually checking the return values of the Windows API to see if what we are trying to do is working would be a good start...

Edgar Reynaldo
Member #8,592
May 2007
avatar

Your current video adapter is not guaranteed to be number 0 in the adapter list. You need to enumerate all the adapters and see which one is the primary adapter (it is the one at 0,0).

   printf("Monitor info :\n");
   for (int i = 0 ; i < al_get_num_video_adapters() ; ++i) {
      ALLEGRO_MONITOR_INFO info;
      if (al_get_monitor_info(i , &info)) {
         printf("Adapter #%d : x1 y1 x2 y2 = %d %d %d %d\n" , i , info.x1 , info.y1 , info.x2 , info.y2);
      }
      else {
         printf("Failed to read monitor info for adapter #%d\n" , i);
      }
   }

Thomas Fjellstrom
Member #476
June 2000
avatar

Your current video adapter is not guaranteed to be number 0 in the adapter list.

True, but the values he was getting were completely invalid. Whether that's allegro's fault or windows's, I don't know.

--
Thomas Fjellstrom - [website] - [email] - [Allegro Wiki] - [Allegro TODO]
"If you can't think of a better solution, don't try to make a better solution." -- weapon_S
"The less evidence we have for what we believe is certain, the more violently we defend beliefs against those who don't agree" -- https://twitter.com/neiltyson/status/592870205409353730

Go to: