I'm busy, to add a price-calculation to the function.
As well, it will be possible with a value ( price = .T. ), to define a longer period than the next season
That is used for the Price-calculation.
A customer rents a umbrella from 18.05 - 15.09 ( all seasons ), from LOW = 7.00 Euro to LOW = 7.00 Euro
A extrem-test with values inside => AVERAGE = 28.06. - 25.07., HEIGHT = 26.07. - 29.08.
The season-array gets a extension for the price.
The End-result of the price can be stored to a database-field, as well all values in between, if needed.
aSEASON[1] := { "17.05." + cYEAR, "27.06." + cYEAR, 7.00 } // LOW
aSEASON[2] := { "28.06." + cYEAR, "25.07." + cYEAR, 9.00 } // AVERAGE
aSEASON[3] := { "26.07." + cYEAR, "29.08." + cYEAR, 11.00 } // HIGHT
aSEASON[4] := { "30.08." + cYEAR, "20.09." + cYEAR, 7.00 } // LOW
It's a crazy calculation, but I got it working. Still some finetuning and tests must be done.
I will update the function when the tests are finished.
FUNCTION TEST_PRICE()
LOCAL o Get1, oGet2, oGet3
DEFINE DIALOG oDlg SIZE 300, 220 TITLE "Price Test"
SET DATE GERMAN
SET CENTURY ON
SET DECIMALS TO 2
PRIVATE aDAYS[1][2]
PRIVATE aSEASON[4][3]
cYEAR := LTRIM( STR( YEAR(DATE()) ))
aSEASON[1] := { "17.05." + cYEAR, "27.06." + cYEAR, 7.00 } // LOW
aSEASON[2] := { "28.06." + cYEAR, "25.07." + cYEAR, 9.00 } // AVERAGE
aSEASON[3] := { "26.07." + cYEAR, "29.08." + cYEAR, 11.00 } // HIGHT
aSEASON[4] := { "30.08." + cYEAR, "20.09." + cYEAR, 7.00 } // LOW
dDAY1 := CTOD("18.05." + cYEAR )
dDAY2 := CTOD("15.09." + cYEAR )
nDAYS1 := 0
nDAYS2 := 0
lPRICE := .F.
cSEASON := "LOW"
nPRICE := 0
nCOUNT1 := 0 // LOW
nCOUNT2 := 0 // AVERAGE
nCOUNT3 := 0 // HIGHT
nCOUNT4 := 0 // LOW
nPRICE1 := 0 // LOW
nPRICE2 := 0 // AVERAGE
nPRICE3 := 0 // HIGHT
nPRICE4 := 0 // LOW
@ 0.5, 3 SAY oSay PROMPT "Price = .T. only used for Price-calculation"
@ 2, 5 SAY oSay PROMPT "Start"
@ 2, 13 SAY oSay PROMPT "End"
@ 2, 19 SAY oSay PROMPT "Price ?"
@ 3.2, 2 GET oGet1 VAR dDAY1 OF oDlg SIZE 40, 15 PICTURE "##.##.####"
@ 3.2, 8 GET oGet2 VAR dDAY2 OF oDlg SIZE 40, 15 PICTURE "##.##.####"
@ 3.2, 16 CHECKBOX oGet3 VAR lPRICE PROMPT "&Price" SIZE 100, 20 OF oDlg
@ 4, 2 BUTTON oBtn PROMPT "Date-Test" size 50, 25 OF oDlg ;
ACTION ( oGet1:Refresh(), oGet2:Refresh(), oGet3:Refresh(), ;
IIF( lPRICE = .F., ( nPRICE := GET_DATE( dDAY1, dDAY2, aSEASON ), ;
MsgAlert( STR(nDAYS1) + CRLF + STR(nDAYS2), cSEASON ) ), ;
( nPRICE := GET_PRICE( dDAY1, dDAY2, aSEASON ), ;
MsgAlert( "LOW : " + STR(nCOUNT1) + " * " + LTRIM(STR(aSEASON[1][3])) + " = " + LTRIM(STR(nPRICE1)) + CRLF + ;
"AVERAGE : " + STR(nCOUNT2) + " * " + LTRIM(STR(aSEASON[2][3]))+ " = " + LTRIM(STR(nPRICE2)) + CRLF + ;
"HIGHT : " + STR(nCOUNT3) + " * " + LTRIM(STR(aSEASON[3][3]))+ " = " + LTRIM(STR(nPRICE3)) + CRLF + ;
"LOW : " + STR(nCOUNT4) + " * " + LTRIM(STR(aSEASON[4][3]))+ " = " + LTRIM(STR(nPRICE4)) + CRLF + CRLF + ;
"Days complete : " + LTRIM( STR ( 1 + (dDAY2 - dDAY1) ) ) + CRLF + CRLF + ;
"Price : " + STR( nPRICE ) + " Euro" , cSEASON ) ) ) )
ACTIVATE DIALOG oDlg CENTERED
RETURN ( NIL )
// ---------- PRICE - CALCULATION ----------------------------
FUNCTION GET_PRICE( dDAY1, dDAY2, aSEASON )
nDAYS1 := 0 // Basic Days
nDAYS2 := 0 // next Season Days
nCOUNT1 := 0 // LOW
nCOUNT2 := 0 // AVERAGE
nCOUNT3 := 0 // HIGHT
nCOUNT4 := 0 // LOW
nPRICE1 := 0 // LOW
nPRICE2 := 0 // AVERAGE
nPRICE3 := 0 // HIGHT
nPRICE4 := 0 // LOW
nPRICE := 0
// aSEASON[1] := { "17.05", "27.06" } // LOW
// aSEASON[2] := { "28.06", "25.07" } // AVERAGE
// aSEASON[3] := { "26.07", "29.08" } // HIGHT
// aSEASON[4] := { "30.08", "20.09" } // LOW
// -------------- LOW ---------------------------------------
// aSEASON[1] := { "17.05", "27.06" }
// -------- Test 18.05-15.09 -------------
// If DAY1 >= SEASON_1.1 and DAY2 <= SEASON_1.2
// ----------------------------------------------------------------------------
IF dDAY1 >= cTOD(aSEASON[1][1] ) .and. dDAY2 <= cTOD(aSEASON[1][2])
nCOUNT1 := 1 + ( dDAY2 - dDAY1 )
// msgalert( "LOW 1.1" )
ENDIF
// If DAY1 <= SEASON_1.2 and DAY2 > SEASON_1.2
// -------------------------------------------------------------------------
IF dDAY1 <= cTOD(aSEASON[1][2] ) .and. dDAY2 > cTOD(aSEASON[1][2])
nCOUNT1 := 1 + ( cTOD(aSEASON[1][2]) - dDAY1 )
// msgalert( "LOW 1.2" )
ENDIF
// -------------- AVERAGE ---------------------------------
// aSEASON[2] := { "28.06", "25.07" }
// ---------- Test 18.05-15.09 -----------
// If DAY1 >= SEASON_2.1 and DAY2 <= SEASON_2.2
// ---------------------------------------------------------------------------
IF dDAY1 >= cTOD(aSEASON[2][1] ) .and. dDAY2 <= cTOD(aSEASON[2][2])
nCOUNT2 := 1 + (dDAY2 - dDAY1)
// msgalert( "HEIGHT 2.1" )
ENDIF
// If DAY1 < SEASON_2.1 and DAY2 > SEASON_2.2
// ------------------------------------------------------------------------
IF dDAY1 < cTOD(aSEASON[2][1] ) .and. dDAY2 > cTOD(aSEASON[2][2])
nCOUNT2 := 1 + ( cTOD(aSEASON[2][2]) - cTOD(aSEASON[2][1]) )
// msgalert( "HEIGHT 2.2" )
ENDIF
// If DAY1 < SEASON_2.1 and DAY2 <= SEASON_2.2
// -------------------------------------------------------------------------
IF dDAY1 < cTOD(aSEASON[2][1] ) .and. dDAY2 >= cTOD(aSEASON[2][2])
nCOUNT3 := 1 + ( dDAY2 - cTOD(aSEASON[2][1]) )
// msgalert( "HEIGHT 2.3" )
ENDIF
// If DAY1 >= SEASON_2.1 and DAY2 > SEASON_2.2
// -------------------------------------------------------------------------
IF dDAY1 >= cTOD(aSEASON[2][1] ) .and. dDAY2 > cTOD(aSEASON[2][2])
nCOUNT2 := 1 + ( cTOD(aSEASON[2][2]) - dDAY1 )
// msgalert( "HEIGHT 2.4" )
ENDIF
//------------- HIGHT ---------------------------------------
// aSEASON[3] := { "26.07", "29.08" }
// -------- Test 18.05-15.09 -------------
// If DAY1 >= SEASON_3.1 and DAY2 <= SEASON_3.2
// ---------------------------------------------------------------------------
IF dDAY1 >= cTOD(aSEASON[3][1] ) .and. dDAY2 <= cTOD(aSEASON[3][2])
nCOUNT3 := 1 + (dDAY2 - dDAY1)
// msgalert( "HEIGHT 3.1" )
ENDIF
// If DAY1 < SEASON_3.1 and DAY2 > SEASON_3.2
// -----------------------------------------------------------------------
IF dDAY1 < cTOD(aSEASON[3][1] ) .and. dDAY2 > cTOD(aSEASON[3][2])
nCOUNT3 := 1 + ( cTOD(aSEASON[3][2]) - cTOD(aSEASON[3][1]) )
// msgalert( "HEIGHT 3.2" )
ENDIF
// If DAY1 < SEASON_3.1 and DAY2 <= SEASON_3.2
// -------------------------------------------------------------------------
IF dDAY1 < cTOD(aSEASON[3][1] ) .and. dDAY2 <= cTOD(aSEASON[3][2])
nCOUNT3 := 1 + ( dDAY2 - cTOD(aSEASON[3][1]) )
// msgalert( "HEIGHT 3.3" )
ENDIF
// If DAY1 >= SEASON_3.1 and DAY2 > SEASON_3.2
// --------------------------------------------------------------------------
IF dDAY1 >= cTOD(aSEASON[3][1] ) .and. dDAY2 > cTOD(aSEASON[3][2])
nCOUNT3 := 1 + ( cTOD(aSEASON[3][2]) - dDAY1 )
// msgalert( "HEIGHT 3.4" )
ENDIF
// ------------ LOW ---------------------------------------
// aSEASON[4] := { "30.08", "20.09" }
// --------- Test 18.05-15.09 ------------
// If DAY1 >= SEASON_4.1 and DAY2 <= SEASON_2.2
// ----------------------------------------------------------------------------
IF dDAY1 >= cTOD(aSEASON[4][1] ) .and. dDAY2 <= cTOD(aSEASON[4][2])
nCOUNT4 := 1 + (dDAY2 - dDAY1)
// msgalert( "LOW 4.1" )
ENDIF
// If DAY1 < SEASON_4.1 and DAY2 > SEASON_4.1
// -----------------------------------------------------------------------
IF dDAY1 < cTOD(aSEASON[4][1] ) .and. dDAY2 > cTOD(aSEASON[4][1])
nCOUNT4 := 1 + ( dDAY2 - cTOD(aSEASON[4][1]) )
// msgalert( "LOW 4.2" )
ENDIF
// -------------------------------------
cSTART := ""
cEND := ""
IF dDAY1 >= cTOD(aSEASON[1][1]) .and. dDAY1 <= cTOD(aSEASON[1][2])
cSTART := "LOW"
ENDIF
IF dDAY1 >= cTOD(aSEASON[2][1]) .and. dDAY1 <= cTOD(aSEASON[2][2])
cSTART := "AVERAGE"
ENDIF
IF dDAY1 >= cTOD(aSEASON[3][1]) .and. dDAY1 <= cTOD(aSEASON[3][2])
cSTART := "HIGH"
ENDIF
IF dDAY1 >= cTOD(aSEASON[4][1]) .and. dDAY1 <= cTOD(aSEASON[4][2])
cSTART := "LOW"
ENDIF
IF dDAY2 >= cTOD(aSEASON[1][1]) .and. dDAY2 <= cTOD(aSEASON[1][2])
cEND := "LOW"
ENDIF
IF dDAY2 >= cTOD(aSEASON[2][1]) .and. dDAY2 <= cTOD(aSEASON[2][2])
cEND := "AVERAGE"
ENDIF
IF dDAY2 >= cTOD(aSEASON[3][1]) .and. dDAY2 <= cTOD(aSEASON[3][2])
cEND := "HIGH"
ENDIF
IF dDAY2 >= cTOD(aSEASON[4][1]) .and. dDAY2 <= cTOD(aSEASON[4][2])
cEND := "LOW"
ENDIF
cSEASON := cSTART + " - " + cEND
nPRICE1 := nCOUNT1 * aSEASON[1][3]
nPRICE2 := nCOUNT2 * aSEASON[2][3]
nPRICE3 := nCOUNT3 * aSEASON[3][3]
nPRICE4 := nCOUNT4 * aSEASON[4][3]
nPRICE := nPRICE1 + nPRICE2 + nPRICE3 + nPRICE4
RETURN( nPRICE )
RETURN( nPrice )
// --------- DAY - CALCULATION -----------------------------
FUNCTION GET_DATE(dDAY1, dDAY2, aSEASON)
nDAYS1 := 0 // Basic Days
nDAYS2 := 0 // next Season Days
// LOW
// aSEASON[1] := { "17.05", "27.06" } // LOW
// -------- 20.05 - 24.06 = 36 x LOW -------------------
IF dDAY1 >= cTOD(aSEASON[1][1] ) .and. dDAY2 <= cTOD(aSEASON[1][2])
cSEASON := "LOW"
nDAYS1 := 1 + (dDAY2 - dDAY1)
ENDIF
// LOW + AVERAGE
// aSEASON[1] := { "17.05", "27.06" } // LOW
// aSEASON[2] := { "28.06", "25.07" } // AVERAGE
// ---------- 26.05 - 12.07 = 33 x LOW +15 x AVERAGE ------------
IF dDAY1 >= cTOD(aSEASON[1][1] ) .and. ;
( dDAY2 >= cTOD(aSEASON[2][1]) .and. dDAY2 <= cTOD(aSEASON[2][2]) )
cSEASON := "LOW+AVERAGE"
nDAYS1 := 1 + (cTOD(aSEASON[1][2]) - dDAY1)
nDAYS2 := 1 + (dDAY2 - cTOD(aSEASON[2][1]))
ENDIF
// AVERAGE
// aSEASON[2] := { "28.06", "25.07" } // AVERAGE
//------------- 29.06 - 22.07 = 25 x AVERAGE --------
IF dDAY1 >= cTOD(aSEASON[2][1] ) .and. dDAY2 <= cTOD(aSEASON[2][2])
cSEASON := "AVERAGE"
nDAYS1 := 1 + (dDAY2 - dDAY1)
ENDIF
//--------------------------------------------------------------
// AVERAGE + HIGHT
// aSEASON[2] := { "28.06", "25.07" } // AVERAGE
// aSEASON[3] := { "26.07", "29.08" } // HIGHT
// --------10.07 - 14.08 = 16 x AVERAGE + 20 x HIGHT -------
IF dDAY1 >= cTOD(aSEASON[2][1] ) .and. ;
( dDAY2 >= cTOD(aSEASON[3][1]) .and. dDAY2 <= cTOD(aSEASON[3][2]) )
cSEASON := "AVERAGE+HEIGHT"
nDAYS1 := 1 + (cTOD(aSEASON[2][2]) - dDAY1)
nDAYS2 := 1 + (dDAY2 - cTOD(aSEASON[3][1]))
ENDIF
// HIGHT
// aSEASON[3] := { "26.07", "29.08" } // HIGHT
// --------18.08 - 14.09 = 28 x HEIGHT -------------
IF cTOD(aSEASON[3][1] ) >= dDAY1 .and. cTOD(aSEASON[3][2]) <= dDAY2
cSEASON := "HIGH"
nDAYS1 := 1 + (dDAY2 - dDAY1)
ENDIF
// HIGHT + LOW
// aSEASON[3] := { "26.07", "29.08" } // HIGHT
// aSEASON[4] := { "30.08", "20.09" } // LOW
// --------- 14.08 - 16.09 = 16 x HIGHT + 17 x LOW ------
IF dDAY1 >= cTOD(aSEASON[3][1] ) .and. ;
( dDAY2 >= cTOD(aSEASON[4][1]) .and. dDAY2 <= cTOD(aSEASON[4][2]) )
cSEASON := "HIGH+LOW"
nDAYS1 := 1 + (cTOD(aSEASON[3][2]) - dDAY1)
nDAYS2 := 1 + (dDAY2 - cTOD(aSEASON[4][1]))
ENDIF
// ----------------------------------------------------------------
// LOW
// aSEASON[4] := { "30.08", "20.09" } // LOW
// ---------------- 30.08 - 15.09 = 16 x LOW ----------------
IF dDAY1 >= cTOD(aSEASON[4][1] ) .and. dDAY2 <= cTOD(aSEASON[4][2])
cSEASON := "LOW"
nDAYS1 := 1 + (dDAY2 - dDAY1)
ENDIF
RETURN( nDAYS1, nDAYS2, cSEASON )
Regards
Uwe
