2026-05-01 11:29:53 +02:00
|
|
|
FUNCTION textinput$ (x AS INTEGER, y AS INTEGER, w AS INTEGER, h AS INTEGER, __text AS STRING)
|
|
|
|
|
DIM text AS STRING, keyin AS STRING
|
|
|
|
|
DIM cursor AS INTEGER, done AS INTEGER
|
|
|
|
|
DIM pasteData AS STRING
|
|
|
|
|
text = __text
|
|
|
|
|
' Initial Hover Check
|
|
|
|
|
IF NOT (_MOUSEX > x AND _MOUSEY > y AND _MOUSEX < x + w AND _MOUSEY < y + h) THEN
|
|
|
|
|
drawtextinput x, y, w, h, __text, 0
|
|
|
|
|
EXIT FUNCTION
|
|
|
|
|
END IF
|
2026-04-29 09:28:35 +02:00
|
|
|
|
2026-05-01 11:29:53 +02:00
|
|
|
drawtextinput x, y, w, h, __text, 1
|
|
|
|
|
IF NOT mouseclicked THEN EXIT FUNCTION
|
|
|
|
|
text=""
|
|
|
|
|
cursor = LEN(text) + 1
|
|
|
|
|
dim relativeX AS INTEGER
|
|
|
|
|
DO
|
|
|
|
|
keyin = INKEY$
|
|
|
|
|
|
|
|
|
|
' Handle Extended Keys (Arrows, Home, End, Delete)
|
|
|
|
|
IF LEN(keyin) = 2 THEN
|
|
|
|
|
SELECT CASE ASC(RIGHT$(keyin, 1))
|
|
|
|
|
CASE 75 ' Left Arrow
|
|
|
|
|
IF cursor > 1 THEN cursor = cursor - 1
|
|
|
|
|
CASE 77 ' Right Arrow
|
|
|
|
|
IF cursor <= LEN(text) THEN cursor = cursor + 1
|
|
|
|
|
CASE 71 ' Home Key
|
|
|
|
|
cursor = 1
|
|
|
|
|
CASE 79 ' End Key
|
|
|
|
|
cursor = LEN(text) + 1
|
|
|
|
|
CASE 83 ' Delete Key
|
|
|
|
|
IF cursor <= LEN(text) THEN
|
|
|
|
|
text = LEFT$(text, cursor - 1) + MID$(text, cursor + 1)
|
|
|
|
|
END IF
|
|
|
|
|
END SELECT
|
|
|
|
|
ELSEIF LEN(keyin) = 1 THEN
|
|
|
|
|
SELECT CASE ASC(keyin)
|
|
|
|
|
CASE 22 ' Ctrl + V (Paste)
|
|
|
|
|
' Note: _CLIPBOARD$ is standard in modern BASIC like QB64
|
|
|
|
|
pasteData = _CLIPBOARD$
|
|
|
|
|
text = LEFT$(text, cursor - 1) + pasteData + MID$(text, cursor)
|
|
|
|
|
cursor = cursor + LEN(pasteData)
|
|
|
|
|
CASE 32 TO 126 ' Regular Typing
|
|
|
|
|
text = LEFT$(text, cursor - 1) + keyin + MID$(text, cursor)
|
|
|
|
|
cursor = cursor + 1
|
|
|
|
|
CASE 8 ' Backspace
|
|
|
|
|
IF cursor > 1 THEN
|
|
|
|
|
text = LEFT$(text, cursor - 2) + MID$(text, cursor)
|
|
|
|
|
cursor = cursor - 1
|
|
|
|
|
END IF
|
|
|
|
|
CASE 13 ' Enter
|
|
|
|
|
done = -1
|
|
|
|
|
CASE 27 ' Escape (Cancel)
|
|
|
|
|
text = __text
|
|
|
|
|
done = -1
|
|
|
|
|
END SELECT
|
|
|
|
|
END IF
|
|
|
|
|
|
|
|
|
|
' Send the cursor position to your drawing routine
|
|
|
|
|
drawtextinput x, y, w, h, text, cursor
|
|
|
|
|
|
|
|
|
|
' Check for clicks inside the box to reposition cursor
|
|
|
|
|
WHILE _MOUSEINPUT: WEND
|
|
|
|
|
IF _MOUSEBUTTON(1) THEN
|
|
|
|
|
IF (_MOUSEX >= x AND _MOUSEX <= x + w AND _MOUSEY >= y AND _MOUSEY <= y + h) THEN
|
|
|
|
|
relativeX = _MOUSEX - x
|
|
|
|
|
cursor = (relativeX \ 8) + 1
|
|
|
|
|
|
|
|
|
|
' Constrain cursor to text boundaries
|
|
|
|
|
IF cursor < 1 THEN cursor = 1
|
|
|
|
|
IF cursor > LEN(text) + 1 THEN cursor = LEN(text) + 1
|
|
|
|
|
ELSE
|
|
|
|
|
done = -1 ' Clicked outside, exit focus
|
|
|
|
|
END IF
|
|
|
|
|
END IF
|
|
|
|
|
_LIMIT 60
|
|
|
|
|
_DISPLAY
|
|
|
|
|
LOOP UNTIL done
|
|
|
|
|
textinput = text
|
|
|
|
|
END FUNCTION
|
|
|
|
|
|
|
|
|
|
SUB drawtextinput (x AS INTEGER, y AS INTEGER, w AS INTEGER, h AS INTEGER, text AS STRING, state AS INTEGER)
|
|
|
|
|
DIM outtext AS STRING
|
|
|
|
|
DIM charWidth AS INTEGER: charWidth = 8 ' Standard font width
|
|
|
|
|
DIM cursorX AS INTEGER, textX AS INTEGER, textY AS INTEGER
|
|
|
|
|
|
|
|
|
|
' Background Drawing
|
|
|
|
|
IF state > 0 THEN ' If state is cursor pos, it's "active"
|
|
|
|
|
COLOR backgroundcolor1
|
|
|
|
|
ELSE
|
|
|
|
|
COLOR backgroundcolor2
|
|
|
|
|
END IF
|
|
|
|
|
LINE (x, y)-(x + w, y + h), , BF
|
|
|
|
|
|
|
|
|
|
' Border Drawing
|
|
|
|
|
IF state > 0 THEN
|
|
|
|
|
COLOR highlightcolor
|
|
|
|
|
ELSE
|
|
|
|
|
COLOR textcolor
|
|
|
|
|
END IF
|
|
|
|
|
LINE (x, y)-(x + w, y + h), , B
|
|
|
|
|
|
|
|
|
|
' Text Alignment Calculation
|
|
|
|
|
_PRINTMODE _KEEPBACKGROUND
|
|
|
|
|
' We keep your original logic for scrolling/clipping text
|
|
|
|
|
outtext = RIGHT$(text, MIN(w / charWidth, LEN(text)))
|
|
|
|
|
|
|
|
|
|
' Calculate the starting X/Y for the text to center it
|
|
|
|
|
textX = 2 + x' + w / 2 - LEN(outtext) * charWidth / 2
|
|
|
|
|
textY = 1 + y + h / 2 - 8
|
|
|
|
|
|
|
|
|
|
_PRINTSTRING (textX, textY), outtext
|
|
|
|
|
|
|
|
|
|
' --- Cursor Logic ---
|
|
|
|
|
IF state > 0 THEN
|
|
|
|
|
' Calculate cursor position relative to the visible text
|
|
|
|
|
' We use (TIMER * 2) to make it blink
|
|
|
|
|
IF INT(TIMER * 2) MOD 2 = 0 THEN
|
|
|
|
|
' state is the cursor index (1-based)
|
|
|
|
|
' We need to find where that character is relative to our clipped outtext
|
|
|
|
|
DIM relativeCursor AS INTEGER
|
|
|
|
|
relativeCursor = state - (LEN(text) - LEN(outtext))
|
|
|
|
|
|
|
|
|
|
' Only draw if the cursor is actually within the visible box
|
|
|
|
|
IF relativeCursor >= 1 AND relativeCursor <= LEN(outtext) + 1 THEN
|
|
|
|
|
cursorX = textX + (relativeCursor - 1) * charWidth
|
|
|
|
|
' Draw a vertical line for the cursor
|
|
|
|
|
LINE (cursorX, textY)-(cursorX, textY + 14), highlightcolor
|
|
|
|
|
END IF
|
|
|
|
|
END IF
|
|
|
|
|
END IF
|
|
|
|
|
END SUB
|
|
|
|
|
|
|
|
|
|
function min(a,b)
|
|
|
|
|
if a<=b then min=a else min=b
|
|
|
|
|
end function
|
2026-04-29 09:28:35 +02:00
|
|
|
function button (x as integer,y as integer,w as integer,h as integer,caption as string)
|
|
|
|
|
if _mousex>x and _mousey>y and _mousex<x+w and _mousey<y+h then
|
|
|
|
|
drawbutton x,y,w,h,caption,1
|
|
|
|
|
if mouseclicked then button=-1
|
|
|
|
|
else
|
|
|
|
|
drawbutton x,y,w,h,caption,0
|
|
|
|
|
end if
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function buttonhold (x as integer,y as integer,w as integer,h as integer,caption as string)
|
|
|
|
|
if _mousex>x and _mousey>y and _mousex<x+w and _mousey<y+h then
|
|
|
|
|
drawbutton x,y,w,h,caption,1
|
|
|
|
|
if _mousebutton(1)then buttonhold=-1
|
|
|
|
|
else
|
|
|
|
|
drawbutton x,y,w,h,caption,0
|
|
|
|
|
end if
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function imagebutton (x as integer,y as integer,w as integer,h as integer,iconhandle as long)
|
|
|
|
|
if _mousex>x and _mousey>y and _mousex<x+w and _mousey<y+h then
|
|
|
|
|
drawimagebutton x,y,w,h,iconhandle,1
|
|
|
|
|
if mouseclicked then imagebutton=-1
|
2026-04-29 12:36:31 +02:00
|
|
|
if rmouseclicked then imagebutton=-2
|
2026-04-29 09:28:35 +02:00
|
|
|
else
|
|
|
|
|
drawimagebutton x,y,w,h,iconhandle,0
|
|
|
|
|
end if
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function imagebuttonhold (x as integer,y as integer,w as integer,h as integer,iconhandle as long)
|
|
|
|
|
if _mousex>x and _mousey>y and _mousex<x+w and _mousey<y+h then
|
|
|
|
|
drawimagebutton x,y,w,h,iconhandle,1
|
|
|
|
|
if _mousebutton(1) then imagebuttonhold=-1
|
|
|
|
|
else
|
|
|
|
|
drawimagebutton x,y,w,h,iconhandle,0
|
|
|
|
|
end if
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function checkbox (x as integer,y as integer, state as integer)
|
|
|
|
|
if _mousex>x and _mousey>y and _mousex<x+16 and _mousey<y+16 then
|
|
|
|
|
drawcheckbox x,y,2 + state
|
|
|
|
|
if mouseclicked then checkbox=(state+1) mod 2:exit function
|
|
|
|
|
else
|
|
|
|
|
drawcheckbox x,y,0 + state
|
|
|
|
|
end if
|
|
|
|
|
checkbox=state
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function link(x,y,label as string)
|
|
|
|
|
dim w as integer
|
|
|
|
|
w=len(label)*8
|
|
|
|
|
if _mousex>x and _mousey>y and _mousex<x+w and _mousey<y+16 then
|
|
|
|
|
drawlink x,y,label,1
|
|
|
|
|
if mouseclicked then link=-1
|
|
|
|
|
else
|
|
|
|
|
drawlink x,y,label,0
|
|
|
|
|
end if
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function vscrollbar(x as long,y as long,h as long,value as single)
|
|
|
|
|
dim tmpval as single
|
|
|
|
|
tmpval=value
|
|
|
|
|
if buttonhold(x,y,23,23,"U") then tmpval=tmpval-1
|
|
|
|
|
if buttonhold(x,h-23,23,23,"D") then tmpval=tmpval+1
|
|
|
|
|
tmpval= vbar(x,y+23,h-46,tmpval)
|
|
|
|
|
if tmpval<0 then tmpval=0
|
|
|
|
|
if tmpval>100 then tmpval=100
|
|
|
|
|
vscrollbar=tmpval
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function vbar(x as long,y as long,h as long,value as single)
|
|
|
|
|
dim tmpval as single
|
|
|
|
|
tmpval=value
|
|
|
|
|
if _mousex>x and _mousey>y and _mousex<x+23 and _mousey<y+h then
|
|
|
|
|
drawvbar x,y,h,value,1
|
|
|
|
|
if _mousebutton(1) then tmpval=((_mousey-y)/(h))*100
|
|
|
|
|
else
|
|
|
|
|
drawvbar x,y,h,value,0
|
|
|
|
|
end if
|
|
|
|
|
vbar=tmpval
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function hscrollbar(x as long, y as long, w as long, value as single)
|
|
|
|
|
dim tmpval as single
|
|
|
|
|
tmpval = value
|
|
|
|
|
if button(x, y, 23, 23, "L") then tmpval = tmpval - 1
|
|
|
|
|
if button(x + w - 23, y, 23, 23, "R") then tmpval = tmpval + 1
|
|
|
|
|
tmpval = hbar(x + 23, y, w - 46, tmpval)
|
|
|
|
|
if tmpval < 0 then tmpval = 0
|
|
|
|
|
if tmpval > 100 then tmpval = 100
|
|
|
|
|
hscrollbar = tmpval
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function hbar(x as long, y as long, w as long, value as single)
|
|
|
|
|
dim tmpval as single
|
|
|
|
|
tmpval = value
|
|
|
|
|
if _mousex > x and _mousey > y and _mousex < x + w and _mousey < y + 23 then
|
|
|
|
|
drawhbar x, y, w, value, 1
|
|
|
|
|
if _mousebutton(1) then tmpval=((_mousex-x)/(w))*100
|
|
|
|
|
else
|
|
|
|
|
drawhbar x, y, w, value, 0
|
|
|
|
|
end if
|
|
|
|
|
hbar = tmpval
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
sub drawbutton(x as integer,y as integer,w as integer,h as integer,caption as string, state as integer)
|
|
|
|
|
if state and 2 then
|
2026-05-01 11:29:53 +02:00
|
|
|
color backgroundcolor1
|
2026-04-29 09:28:35 +02:00
|
|
|
line (x,y)-(x+w,y+h),,bf
|
|
|
|
|
else
|
|
|
|
|
color backgroundcolor2
|
|
|
|
|
line (x,y)-(x+w,y+h),,bf
|
|
|
|
|
end if
|
|
|
|
|
if state and 1 then
|
|
|
|
|
color highlightcolor
|
|
|
|
|
line (x,y)-(x+w,y+h),,b
|
|
|
|
|
else
|
|
|
|
|
color textcolor
|
|
|
|
|
line (x,y)-(x+w,y+h),,b
|
|
|
|
|
end if
|
|
|
|
|
_printmode _keepbackground
|
|
|
|
|
_printstring (1+x+w/2-len(caption)*8/2,1+y+h/2-8),caption
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub drawimagebutton(x as integer,y as integer,w as integer,h as integer,iconhandle as long, state as integer)
|
|
|
|
|
if state and 2 then
|
|
|
|
|
color backgroundcolor2
|
|
|
|
|
line (x,y)-(x+w,y+h),,bf
|
|
|
|
|
_putimage (x,y),iconhandle
|
|
|
|
|
else
|
|
|
|
|
color backgroundcolor2
|
|
|
|
|
line (x,y)-(x+w,y+h),,bf
|
|
|
|
|
_putimage (x,y),iconhandle
|
|
|
|
|
end if
|
|
|
|
|
if state and 1 then
|
|
|
|
|
color highlightcolor
|
|
|
|
|
line (x,y)-(x+w,y+h),,b
|
|
|
|
|
else
|
|
|
|
|
color textcolor
|
|
|
|
|
line (x,y)-(x+w,y+h),,b
|
|
|
|
|
end if
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub drawcheckbox(x,y,state)
|
|
|
|
|
if state and 2 then
|
|
|
|
|
color highlightcolor
|
|
|
|
|
line (x,y)-(x+16,y+16),&hffdddddd,b
|
|
|
|
|
else
|
|
|
|
|
color textcolor
|
|
|
|
|
line (x,y)-(x+16,y+16),&hffbbbbbb,b
|
|
|
|
|
end if
|
|
|
|
|
if state and 1 then
|
|
|
|
|
color textcolor
|
|
|
|
|
line (x+3,y+3)-(x+13,y+13),,bf
|
|
|
|
|
end if
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub drawframe(x,y,w,h,label as string)
|
|
|
|
|
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub drawlink(x,y,label as string,state as integer)
|
|
|
|
|
if state=1 then
|
|
|
|
|
color highlightcolor
|
|
|
|
|
else
|
|
|
|
|
color textcolor
|
|
|
|
|
end if
|
|
|
|
|
_printstring (x,y),label
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub drawhline(x,y,w)
|
|
|
|
|
line (x,y)-(x+w,y),backgroundcolor1
|
|
|
|
|
line (x,y+1)-(x+w,y+1),backgroundcolor2
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub drawvbar(x as long,y as long,h as long,value as single, state as integer)
|
|
|
|
|
if state and 2 then
|
|
|
|
|
color backgroundcolor2
|
|
|
|
|
line (x,y)-(x+23,y+h),,bf
|
|
|
|
|
else
|
|
|
|
|
color backgroundcolor2
|
|
|
|
|
line (x,y)-(x+23,y+h),,bf
|
|
|
|
|
end if
|
|
|
|
|
if state and 1 then
|
|
|
|
|
color highlightcolor
|
|
|
|
|
line (x,y)-(x+23,y+h),,b
|
|
|
|
|
else
|
|
|
|
|
color textcolor
|
|
|
|
|
line (x,y)-(x+23,y+h),,b
|
|
|
|
|
end if
|
|
|
|
|
dim indicator as long
|
|
|
|
|
indicator=((h-23) / 100)*value
|
|
|
|
|
line (x+1,y+indicator)-step(21,21),,bf
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub drawhbar(x as long, y as long, w as long, value as single, state as integer)
|
|
|
|
|
color backgroundcolor2
|
|
|
|
|
line (x, y)-(x + w, y + 23),, bf
|
|
|
|
|
if state and 1 then
|
|
|
|
|
color highlightcolor
|
|
|
|
|
line (x, y)-(x + w, y + 23),, b
|
|
|
|
|
else
|
|
|
|
|
color textcolor
|
|
|
|
|
line (x, y)-(x + w, y + 23),, b
|
|
|
|
|
end if
|
|
|
|
|
dim indicator as long
|
|
|
|
|
indicator = ((w - 23) / 100) * value
|
|
|
|
|
line (x + indicator, y + 1)-step(21, 21),, bf
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
sub textcolor (value as long)
|
|
|
|
|
ignore=__interncolors(1,1,value)
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub highlightcolor (value as long)
|
|
|
|
|
ignore=__interncolors(1,2,value)
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub backgroundcolor1 (value as long)
|
|
|
|
|
ignore=__interncolors(1,3,value)
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
sub backgroundcolor2 (value as long)
|
|
|
|
|
ignore=__interncolors(1,4,value)
|
|
|
|
|
end sub
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function textcolor ()
|
|
|
|
|
textcolor=__interncolors(2,1,ignore)
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function highlightcolor ()
|
|
|
|
|
highlightcolor=__interncolors(2,2,ignore)
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function backgroundcolor1 ()
|
|
|
|
|
backgroundcolor1=__interncolors(2,3,ignore)
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
function backgroundcolor2 ()
|
|
|
|
|
backgroundcolor2=__interncolors(2,4,ignore)
|
|
|
|
|
end function
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function __interncolors(mode as integer, object as integer, value as long)
|
|
|
|
|
static textc as long
|
|
|
|
|
static highc as long
|
|
|
|
|
static bgrc1 as long
|
|
|
|
|
static bgrc2 as long
|
|
|
|
|
static linc as long
|
|
|
|
|
static init as long
|
|
|
|
|
if init=0 then
|
|
|
|
|
textc=&hffbbbbbb
|
|
|
|
|
highc=&hffdddddd
|
|
|
|
|
bgrc1=&hff282828
|
|
|
|
|
bgrc2=&hff282828
|
|
|
|
|
linc =&hffdddddd
|
|
|
|
|
init =-1
|
|
|
|
|
end if
|
|
|
|
|
if mode=1 then
|
|
|
|
|
select case object
|
|
|
|
|
case 1
|
|
|
|
|
textc=value
|
|
|
|
|
case 2
|
|
|
|
|
highc=value
|
|
|
|
|
case 3
|
|
|
|
|
bgrc1=value
|
|
|
|
|
case 4
|
|
|
|
|
bgrc2=value
|
|
|
|
|
end select
|
|
|
|
|
end if
|
|
|
|
|
if mode=2 then
|
|
|
|
|
select case object
|
|
|
|
|
case 1
|
|
|
|
|
__interncolors=textc
|
|
|
|
|
case 2
|
|
|
|
|
__interncolors=highc
|
|
|
|
|
case 3
|
|
|
|
|
__interncolors=bgrc1
|
|
|
|
|
case 4
|
|
|
|
|
__interncolors=bgrc2
|
|
|
|
|
end select
|
|
|
|
|
end if
|
|
|
|
|
end function
|