Strange phenomenon

This forum is for eXpress++ general support.
Post Reply
Message
Author
User avatar
Tom
Posts: 1172
Joined: Thu Jan 28, 2010 12:59 am
Location: Berlin, Germany

Strange phenomenon

#1 Post by Tom »

Hi, Roger.

This is really hard to explain and I can't build a sample. It worked with build 254. Now in 256, I face this problem:

A dialog (#1) calls a modal dialog (#2), so the calling dialog should be inactive (it is). Now, a new thread is started, which creates the original dialog again (#3) for a second time (please don't ask why). If this (#3) now is closed (only #1 and #2 open, but #1 still inactive), somehow eXpress++ tries to refresh the original (first) dialog, which should be inactive at this time. This causes an error in _EditProteced() at line #5099, since an EDITPROTECT codeblock is to be evaluated, even though the dialog containing it should be disabled (which is the fact). Callstack is: DC_ReadGUI(108) -> DC_GetList:ReadGUI(3704) -> DC_GetList:EventLoop(4411) -> _EditProteced(5099). The problem is: The shown error is somehow "correct": If dialog #2 is created, some tables for #1 are closed, so some table references are invalid now. They are reopened again if #2 gets closed. The EDITPROTECT codeblock causing the problem references one of those tables - but this should not create a problem, since the dialog #1 is inactive. With 256, eXpress++ somehow tries to refresh it anyway. New stuff lock LOCKTOOWNER is not used.
Best regards,
Tom

"Did I offend you?"
"No."
"Okay, give me a second chance."

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Strange phenomenon

#2 Post by rdonnay »

Tom -

I need to compare code in _DCGETBX.PRG between builds 254 and 256 to see what may be going on here.

Roger
The eXpress train is coming - and it has more cars.

User avatar
Tom
Posts: 1172
Joined: Thu Jan 28, 2010 12:59 am
Location: Berlin, Germany

Re: Strange phenomenon

#3 Post by Tom »

GOT IT!

After working for hours and days on this problem, I finally found out what seems to cause it. Compile and run the attached sample on a system that supports visual styles. Click "New dialog" on the first screen, then "Old dialog" on the second. You will receive a runtime error, where the function _EditProtected() from _DCGETBX.PRG tries to evaluate a WHEN codeblock of the first dialog - what it should not do.

Now, comment out line 10: "GetApplication:EnableVisualStyles := XBPAPP_ALLSTYLES"

Try again. It works. You can create as many dialogs as you want - everything is just fine.

This code in line 10 is a part of something I already used with build 254 - there is a user option whether visual styles should be supported or not.
Attachments
murks.zip
(1.67 KiB) Downloaded 540 times
Best regards,
Tom

"Did I offend you?"
"No."
"Okay, give me a second chance."

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Strange phenomenon

#4 Post by rdonnay »

Hours and Days?

And all this time I thought you were on vacation.
I'll give it a look right away.

Thanks.
The eXpress train is coming - and it has more cars.

User avatar
Tom
Posts: 1172
Joined: Thu Jan 28, 2010 12:59 am
Location: Berlin, Germany

Re: Strange phenomenon

#5 Post by Tom »

And all this time I thought you were on vacation.
If you run your own business, something like "vacation" does not exist. 8-)
Best regards,
Tom

"Did I offend you?"
"No."
"Okay, give me a second chance."

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Strange phenomenon

#6 Post by rdonnay »

I am surprised that this code has not given you problems prior to now.
The reason for the error is because the database in the thread of the first dialog is being closed and then the WHEN clause is being evaluated.
Putting a test in the code blocks solves that problem. See the code snippet below.

I do not know of any easy solution to prevent the evaluation of the WHEN in the first thread without some major changes to the event loop and that may cause some regression. I will look into this anyway and see what I can do.

Code: Select all

USE test ALIAS tst NEW EXCLUSIVE

APPEND BLANK
REPLACE field1 with Replicate(SubStr(cTitle,1,1),50)
REPLACE field2 with Replicate(SubStr(cTitle,2,1),50)
REPLACE field3 with Replicate(SubStr(cTitle,3,1),50)
REPLACE field4 with Replicate(SubStr(cTitle,4,1),50)

cField1 := tst->Field1
cField2 := tst->Field2
cField3 := tst->Field3
cField4 := tst->Field4
lField5 := tst->Field5

@ 0,1 DCSAY DbInfo(DBO_FILENAME)

@ 1,1 DCTABPAGE oTab1 SIZE 100,18 STATICAREA oTab1Static

DCSETPARENT TO oTab1Static

@ 1,1 DCSAY 'Test 1' GET cField1 GETOBJECT oSle1
@ 2,1 DCSAY 'Test 2' GET cField2
@ 3,1 DCSAY 'Test 3' GET cField3 WHEN {||Select('tst')>0 .AND. tst->field5}  <<<<<< added new code here
@ 4,1 DCSAY 'Test 4' GET cField4 EDITPROTECT {||Select('tst') > 0 .AND. !tst->field5}  <<<<<< added new code here

@ 6,1 DCPUSHBUTTON CAPTION 'New dialog' SIZE 10,1 ACTION {||nTest:=tst->(RecNo()),tst->(DbCloseArea()),NewDialog(oDialog,.T.),ReUse(nTest)}  <<<<<<<<<<<<<<<< database is closed here

@ 6,15 DCPUSHBUTTON CAPTION 'Inspect' SIZE 10,1 ACTION {||DC_InspectObject(oSle1)} ;
   WHEN {||Select('tst') >0 .AND. tst->field5} ;  <<<<<< added new code here
   TOOLTIP 'Test'

@ 8,1 DCBROWSE oBROWSE DATA aTest SIZE 60,5 FIT
DCBROWSECOL ELEMENT 1 HEADER 'One'   WIDTH 10 PARENT oBROWSE
DCBROWSECOL ELEMENT 2 HEADER 'Two'   WIDTH 10 PARENT oBROWSE
DCBROWSECOL ELEMENT 3 HEADER 'Three' WIDTH 10 PARENT oBROWSE

DCREAD GUI ADDBUTTONS TITLE cTitle FIT PARENT @oDialog CLEAREVENTS OPTIONS GetOptions EVAL {|o|SetAppWindow(o),o:SetDisplayFocus := {||SetAppWindow(o)}}

CLOSE DATA

RETURN nil
The eXpress train is coming - and it has more cars.

User avatar
Tom
Posts: 1172
Joined: Thu Jan 28, 2010 12:59 am
Location: Berlin, Germany

Re: Strange phenomenon

#7 Post by Tom »

Hi, Roger.

This code worked for years. The reason for that approach is that the new dialog (in my real application) is normally started as a new thread, but in this special situation, it is called as a modal dialog in the same thread. Because both - the old and the new dialog - use the same tables and aliases, all tables get closed before the new dialog is started, and they are opened up again when it's finished (all pointers restored a.s.o.). Since the new dialog is modal, nothing should happen concerning the old dialog while the new one is in use, and the WHEN-codeblocks should not be evaluated at any time. In fact, they are not - as long as I don't use build 257 and/or GetApplication():EnableVisualStyles. I know how to work around this problem, but the real dialogs are huge and contain tons of those. Anyway, in my humble opinion (and is I said), the old dialog should not be touched while the new one is running. Only with GetApp... and in build 257, it is. So, this obscure behaviour may point to some regression that may cause other problems in more "normal" applications aswell.

I removed GetApplication():EnableVisualStyles to fix this temporarily. This is not a really important feature in my app.
Best regards,
Tom

"Did I offend you?"
"No."
"Okay, give me a second chance."

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Strange phenomenon

#8 Post by rdonnay »

Still trying to figure out a solution for you.
The eXpress train is coming - and it has more cars.

User avatar
Tom
Posts: 1172
Joined: Thu Jan 28, 2010 12:59 am
Location: Berlin, Germany

Re: Strange phenomenon

#9 Post by Tom »

Hi, Roger.

It's not about "finding a solution for me" - my workaround is good enough for me, since that functionality (swichting visual styles off if they are active for the OS) is not really important - it's just cosmetics. It seems that you added something that references an inactive GetList, which even is no part of the actual dialog/eventloop at the time. The problem I faced may point to some other kind of regression that may cause problems for others aswell in the future. eXpress++ evaluates an "inactive" GetList which has nothing to do with active processes, and it did not do that in older builds - that code, even with "GetApplication():EnableVisualStyles", worked fine in 254.
Best regards,
Tom

"Did I offend you?"
"No."
"Okay, give me a second chance."

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Strange phenomenon

#10 Post by rdonnay »

I agree that the problem is related to an "inactive" Getlist, but it is not necessarily easy to determine what is meant by "inactive". If an object is disabled, then it surely is inactive, but if it is in the background, then it may not be inactive. It is easy to determine if an object is disabled, but not if it is in the background.
The eXpress train is coming - and it has more cars.

Post Reply