Page 1 of 4

Return more than one variable?

Posted: Wed May 05, 2004 12:09 pm
by GeoTrail
When using ProcedureDLL or just Procedure, can it return more than one variable?

Like this:

Code: Select all

ProcedureReturn Result1$,Result2$
?

Posted: Wed May 05, 2004 12:15 pm
by freedimension
No, but you can use Structures to return multiple values:

Code: Select all

Structure test
  a.l
  b.l
EndStructure

Procedure test(*ReturnMe.test)
  *ReturnMe\a = 42
  *ReturnMe\b = 23
EndProcedure

TestMe.test
TestMe\a =0815
TestMe\b = 4711

test(TestMe)

Debug TestMe\a
Debug TestMe\b

Posted: Wed May 05, 2004 12:28 pm
by GeoTrail
OK, thanks for that :)

Re: Return more than one variable?

Posted: Wed May 05, 2004 2:46 pm
by einander
GeoTrail wrote:When using ProcedureDLL or just Procedure, can it return more than one variable?
Having 2 small arrays as return buffers, you can return numbers or strings easily.

Code: Select all

;Return multiple values from Procedure

Dim Buff.L(10):Dim Buff$(10)  ; Return buffers

Procedure.s DoSomething() 
  Buff(0)=111:  Buff(1)=222  : Buff(2)=333       
  Buff$(0)="Result$ Zero" : Buff$(1)="Result$ One" :Buff$(2)="Result$ Two"
  ProcedureReturn "Here are 6 returns from Procedure DoSomething:"
EndProcedure

Debug DoSomething()

For i=0 to2
  Debug Str(buff(i))+"  "+ buff$(i)
Next
Best regards
Einander

Posted: Wed May 05, 2004 4:03 pm
by GeoTrail
Wow, that looks complicated. Haven't gotten that far in learning PB yet ;)
Thanks anyways :)

Posted: Wed May 05, 2004 4:14 pm
by localmotion34
why cant you use:

procedure dothis()
var1 =
var2=
procedurereturn var1 and var2
endprocedure

Posted: Wed May 05, 2004 4:15 pm
by GeoTrail
AND
?

Will that work? Has anyone tried that?

Posted: Wed May 05, 2004 5:30 pm
by freak
No, this won't work.

Timo

Posted: Thu May 06, 2004 2:58 pm
by blueb
GeoTrail wrote:Wow, that looks complicated. Haven't gotten that far in learning PB yet ;)
Thanks anyways :)
GeoTrail,

It's not that complicated... In PureBasic arrays are always global. So if you update an array element inside a procedure, it's value will be available anywhere in your program.

HTH,
blueb

Posted: Thu May 06, 2004 3:18 pm
by blueznl
i sometimes do use globals as well to return values from procedures

it all depends on what you do with them, see, if i write one or more procedures that happen to do related stuff, they might share some information... in those caes, i use some specific variable names that are a. unlikely to be used elsewhere, and b. global, and c. shared between the different procedures and have similar functionality

for example:

Code: Select all

Procedure.l x_exist(filename.s)
  Global x_creation.l, x_lastaccess.l, x_lastwrite.l, x_filesize.l
  Protected st.SYSTEMTIME
  ;
  ; *** check if a file exist and if so, retrieve information on a file
  ;
  ; in:     filename.s               - path + filename
  ; retval: 1 #True                  - found and info retrieved
  ;         0 #False                 - not found or cannot get my greedy fingers on it
  ; out:    x_filesize.l             - size of file
  ;         x_creation.l             - when created
  ;         x_lastaccess.l           - when last accessed
  ;         x_lastwrite.l            - last written To
  ;
  file_h = CreateFile_(@filename.s,0,0,0,#OPEN_EXISTING,0,0)    ; open only for retrieval of attributes
  If file_h <> #INVALID_HANDLE_VALUE                            ; ok it exists
    x_filesize.l = GetFileSize_(file_h,0)                       ; that's the size
    ;
    creation.FILETIME                                           ; create temp vars  
    lastaccess.FILETIME
    lastwrite_ft.FILETIME
    st.SYSTEMTIME
    ;
    GetFileTime_(file_h,@creation,@lastaccess,@lastwrite)
    ;
    x_creation.l = x_filetimetodate(@creation)
    x_lastaccess.l = x_filetimetodate(@lastaccess)
    x_lastwrite.l = x_filetimetodate(@lastwrite)
    CloseHandle_(file_h) 
    ProcedureReturn #True
  Else
    ProcedureReturn #False
  EndIf
EndProcedure
all the procedures in my personal library use the following naming scheme: x_whatever... so if i need to return more than one thing from a procedure, i either use x_procedurename_whatever if it's meant to be shared between procedures but i normally don't touch it, or i use x_whatever to return additional information

for example, the procedure above returns x_creation with creation time and date of the file, x_lastaccess, and x_lastwrite

of course it's essential to document this kind of usage, and to declare those variables global

Posted: Fri May 07, 2004 12:59 am
by localmotion34
ok, so if in a LIB i write with tailbite, i want to create a command that gets an MDI gadget properties and store them in a structure.

basically i want the user to be able to set values for an x, y, width height of an MDI gadget when a window is in a docked position, and then when the window is undocked, the MDI automaticlly resizes to predefined x,y,width,height values in the undocked state.

Code: Select all

Structure dockedproperties
  MDIWidth.l 
  MDIHeight.l 
  MDIdockedx.l
 MDIdockedy.l
EndStructure 

Structure undockedproperties
  MDIWidth.l 
  MDIHeight.l 
  MDIdockedx.l
 MDIdockedy.l
EndStructure 

proceduredll dockedproperties(MDIgadget);this will set the efined values of above structures
endprocedure

proceduredll undockedproperties(

endprocedure

proceduredll flipdockstate(dockhandle,MDIgadget,@docked/undockedproperties)
resizegadget(MDIgadget,----structure here)
endprocedure


this way, quick undocking or docking a window automatically resizes the MDI to values defined in the procedures. basically i want to the user to be able to setup these values just by using the procedures and then flipping the "dock" state.

Posted: Fri May 07, 2004 1:10 am
by El_Choni
If you only have one docked window, I would store the data in a global structured variable. Otherwise, I would use a structured linked list (if using TailBite, remember to declare the list in a procedure).

Posted: Fri May 07, 2004 1:26 am
by localmotion34
can you give an example. i thought variables in a library or DLL cant be accessed in PB code?

Posted: Fri May 07, 2004 1:30 am
by Dare2
Would using Global makes a variable in a dll sortof-kindof public? Ditto in a tailbite lib?

Can't test this myself right at the mo.

Posted: Fri May 07, 2004 1:32 am
by El_Choni
Yes, you can, by providing a pointer to the variable. But a more clean solution is to give a function that retrieves that value like, for example, WindowID() XD

That is, your DLL/lib code accesses the variable/linkedlist/memory block, and returns it to the main code.

Using Global makes your variable permanent in memory, and public to the same process (even the program calling the DLL/lib) but not by name, but by pointer. Locals are only in the procedure stack.