DVX_GUI/src/apps/kpunch/dvxbasic/form.dhs
2026-10-20 17:24:15 -05:00

237 lines
17 KiB
Text

# The MIT License (MIT)
#
# Copyright (C) 2026 Scott Duensing
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to
# deal in the Software without restriction, including without limitation the
# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
# sell copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
# IN THE SOFTWARE.
.topic ctrl.form
.title Form
.toc 1 Form
.index Form
.index Window
.index Caption
.index AutoSize
.index Resizable
.index Load
.index Unload
.index Show
.index Hide
.index Padding
.index Spacing
.index vbModal
.index New (forms)
.index WindowState
.index MaxWidth (form)
.index MaxHeight (form)
.index GameInput
.index FullScreen (form)
.index dvxFullScreenActive
.index vbMinimized
.index NewArgs
.index COMMAND$ (new arguments)
.index vbMaximized
.index Several copies of a form
.index Controls (form)
.index DesignMode
.index DesignSelection
.index DesignMouse
.index DesignKey
.index DesignPropertyChanged
.index Design surface
.index Icon (form)
.index Tag (form)
.index MousePointer (form)
.index FontName (form)
.index Font (form)
.index ActiveControl
.index FitWidth
.index FitHeight
.index SaveScreenshot
.h1 Form
VB Equivalent: Form -- DVX Widget: Window + VBox/HBox root
The Form is the top-level container representing a DVX window. It is declared in the .frm file with Begin Form FormName. All controls are children of the form's content box, which uses either VBox (default) or HBox layout.
.h2 Form Properties
.table
Property Type Default Description
---------- ------- -------------- -------------------------------------------
Name String "Form1" The form's name, used for event dispatch and Load statement.
Caption String (same as Name) Window title bar text.
Width Integer 400 Window width in pixels. In the .frm file it is ignored when AutoSize is True.
Height Integer 300 Window height in pixels. In the .frm file it is ignored when AutoSize is True.
Left Integer 0 Initial X position. Used when Centered is False.
Top Integer 0 Initial Y position. Used when Centered is False.
Layout String "VBox" Content box layout: "VBox" (vertical) or "HBox" (horizontal).
AutoSize Boolean False When True, the window shrink-wraps to fit its content.
Resizable Boolean True Whether the user can resize the window at runtime.
Centered Boolean True When True, the window is centered on screen. When False, Left/Top are used.
Visible Boolean False True shows the form and False hides it, exactly like Show and Hide (the first show fires Activate).
ContextMenu String "" Name of a popup menu shown when the form is right-clicked.
HelpTopic String "" Help topic opened by F1 while the form is active and the focused control has no HelpTopic of its own. Empty opens the project's help file at its default page.
Padding Integer 4 Space in pixels between the window's edges and the controls (the content box's Padding); 0 is none.
Spacing Integer 4 Space in pixels between one control and the next (the content box's Spacing); 0 is none.
WindowState Integer 0 vbNormal (0), vbMinimized (1, shown only as an icon at the bottom of the screen), or vbMaximized (2, filling the screen). Set on a hidden form (or in the .frm file), it takes effect when the form is shown; reading it then gives the state the form will have.
Controls Collection (none) The form's controls (read-only), in the order they were made: Me.Controls.Count, Me.Controls(1) (the first), Me.Controls("Text1"), For Each c In Me.Controls. Elements of a control array are in it too but have no name key. Each use makes a new Collection; changing it does not change the form.
DesignMode Boolean False True puts the form in design mode, for a form designer: see Designing Forms below. Not in .frm files.
Icon Picture (DVX's) The picture shown for the window while it is minimized: a picture file name (BMP, PNG, JPEG, or GIF) or a picture from LOADPICTURE or LOADPICTUREDATA (Set works too); "" puts DVX's back. Reading it gives a Picture object. Also in the .frm file. A file that is not a picture is an error.
Tag String "" Any text the program wants to keep with the form, as for controls.
MousePointer Integer 0 The mouse pointer over the form where its controls have none (see MousePointer under Common Properties).
FontName String "System" The form's font: the font of every control on it that has none of its own, and of the form's Print and TextWidth. FontSize, FontBold, FontItalic, FontUnderline, and FontStrikethru go with it, as for controls (see Fonts under Common Properties). Also in the .frm file.
ActiveControl Control (none) The control of the form that has the keyboard focus (read-only), Nothing when none of them has it: Me.ActiveControl.SelText for an Edit menu's Copy. Screen.ActiveControl is the focused control of the whole program. Not in .frm files.
DesignSelection String "" The name of the control (Text1, or Text1(2) in a control array) whose selection handles are drawn while the form is in design mode; "" for none. Not in .frm files.
MaxWidth Integer 0 The widest the user can make the window, by dragging or maximizing; 0 is the screen's width. A window wider than a new MaxWidth shrinks to it. Also in the .frm file.
MaxHeight Integer 0 The tallest the window can be made, as MaxWidth; 0 is the screen's height.
GameInput Boolean False True for a game: while the form has the keyboard, every key goes to it -- none to F1 (help), F10 or Alt (the menu bar), menu shortcuts, or DVX's shortcut keys. Only Alt+Tab, Ctrl+Esc, and Alt+F4 still reach DVX. Also in the .frm file.
FullScreen Boolean False True gives the form the whole screen: a video mode as large as the form's inside (its controls and drawing, without the title bar), the form shown on it at the largest whole multiple of its size that fits, centred on black, kept up to date as it changes. The mouse works on it as in the window, and every key goes to it as with GameInput. A hidden form is shown first. When the user switches to another program (Alt+Tab, Ctrl+Esc), or the program shows a message box or another form, the desktop comes back; the form gets the whole screen again with the focus. Reads False when no video mode could be set (the form stays in its window). False gives the desktop back. Run time only; see the FullScreen event.
.endtable
Maximizing a window, or restoring a maximized one, changes its size, so Resize fires. Minimizing does not change the size and fires no Resize. A minimized window keeps its maximized state: set WindowState = vbMaximized to bring it back filling the screen, vbNormal to bring it back at its normal size.
.code
frmTerminal.Show
frmTerminal.WindowState = vbMinimized ' starts as an icon
.endcode
.h2 Form Events
.table
Event Parameters Description
----------- --------------------- -------------------------------------------
Load (none) Fires after the form and all controls are created. This is the default event.
Unload (none) Fires when the form is being closed or unloaded.
QueryUnload Cancel As Integer Fires before Unload. Set Cancel = 1 to abort the close.
Resize (none) Fires when the window changes size: resized by the user, maximized, or restored (by the user or WindowState).
Activate (none) Fires when the window gains focus.
Deactivate (none) Fires when the window loses focus.
Paint (none) Fires when the form is shown or resized and on Refresh, unless AutoRedraw is True (see Drawing on Forms and PictureBoxes).
DragDrop Source As Control, X As Integer, Y As Integer Fires when a dragged control is dropped on an empty part of the form. X and Y are where, in the form.
DragOver Source As Control, X As Integer, Y As Integer, State As Integer Fires while a dragged control moves over an empty part of the form. State is vbEnter, vbLeave, or vbOver.
NewArgs (none) Fires when the running program is handed new arguments: COMMAND$ has changed (see New Arguments below).
FullScreen State As Integer With FullScreen True: dvxFullScreenActive (1) when the form has the whole screen (draw anything that must look new then), dvxFullScreenSuspended (2) when the desktop came back while another window has the focus, dvxFullScreenEnded (0) when the form's video mode could not be set again (FullScreen is False now).
DesignMouse Action As Integer, Button As Integer, X As Integer, Y As Integer, CtrlName As String, Handle As Integer In design mode: the mouse was pressed, moved, released, or double-clicked in the form. See Designing Forms below.
DesignKey KeyCode As Integer, Shift As Integer In design mode: a key was pressed in the form (KeyCode and Shift as in KeyDown).
DesignPropertyChanged CtrlName As String, PropertyName As String In design mode: the code of a UserControl on the form called PropertyChanged. See Designing Forms below.
.endtable
See Drag and Drop under Common Properties, Events, and Methods. While a control is dragged over a form with no DragDrop event procedure, the mouse pointer shows the "no drop" sign.
.h2 New Arguments
A program with a NewArgs event procedure on any of its forms can be handed new arguments while it runs, instead of DVX starting another copy of it. COMMAND$ (and COMMAND$(1), COMMAND$(2), ...) then give the new arguments, and NewArgs fires on every loaded form that has the procedure. When the arguments arrive while one of the program's event procedures is still running -- for example while it shows a message box or a dialog, or a form with vbModal -- they are held, and NewArgs fires once that procedure has finished; if several arrive meanwhile, only the last is given.
DVX hands new arguments to the help viewer: F1 and the Help menus of programs (and HelpView in BASIC) send "helpfile topic" to the program installed as APPS\KPUNCH\DVXHELP\DVXHELP.APP when it is already running. A help viewer written in BASIC and installed there gets them in NewArgs. Starting a program that is already running -- from Program Manager, the Run dialog, a document opened in it, or ShellRun -- gives it the new arguments when it allows only one copy and has a NewArgs procedure: its window comes to the front and NewArgs fires. Without a NewArgs procedure DVX says it is already running; a program that allows more than one copy (Project Properties) starts another copy instead.
.code
Sub Form1_NewArgs ()
' F1 in another program while this help viewer is open
If COMMAND$(1) <> openFile Then OpenHelpFile COMMAND$(1)
GoTopic HlpStartTopic(hlp, COMMAND$(2))
End Sub
.endcode
.h2 Form Methods
.table
Statement Description
------------------ -------------------------------------------
Load FormName Load the form (creates the window and controls, fires Load event).
Unload FormName Unload the form (fires Unload, destroys window).
FormName.Show Make the form visible.
FormName.Show 1 Show as a modal dialog (vbModal): the statement returns when the form is hidden or unloaded, so the code after it can read what the user chose.
FormName.Hide Hide the form without unloading it.
FormName.FitWidth Make the window just wide enough for its controls, keeping its height (AutoSize fits both).
FormName.FitHeight Make the window just tall enough for its controls, keeping its width.
FormName.SaveScreenshot file$ Save a picture of what the window shows inside its frame to a file: BMP when the name ends in .bmp, PNG otherwise. An error when the form has no window or the file cannot be written.
.endtable
.h2 Several Copies of a Form
A form can be open more than once, the way a program opens a second document window. New FormName makes another copy of the form: its own window, controls, menus, and form-level variables, built from the same .frm. Its Load event runs, and it starts hidden like any loaded form, so call Show. Keep the copy in a variable declared As the form's name (or As Form, As Object):
.code
Dim f As Form1 ' a Form1 copy, or the form itself
Set f = New Form1 ' a new copy
f.Caption = "Second window"
f.Text1.Text = "Hello" ' this copy's Text1
f.Show
Dim g As New Form1 ' declares and makes a copy at once
.endcode
The code of the form serves every copy. In it, Me, the controls named on their own (Text1), and the form-level variables are those of the copy whose event is running, so each window keeps its own state. Unload f closes that copy only.
The form's name (Form1.Caption, Form1.Show, Load Form1) always means the first copy loaded -- the one the program starts with -- as in Visual Basic. If that copy was unloaded, the name means the next one still open.
.h2 Designing Forms
A form designer written in BASIC shows the form being designed as a real form and turns on its design mode. While DesignMode is True, the controls on the form take no mouse clicks or keys and fire no events (Timers too are quiet); the form instead tells the designer what the user does:
.list
.item DesignMouse (Action, Button, X, Y, CtrlName, Handle): Action is DSGN_MOUSE_DOWN (1, a button was pressed), DSGN_MOUSE_MOVE (2), DSGN_MOUSE_UP (3), or DSGN_MOUSE_DBLCLICK (4, a double click: open the code, say). Button is the button pressed or released (1 left, 2 right, 4 middle; for a move, the buttons held). X and Y are where, in the form. CtrlName is the control there -- the innermost one when containers hold others -- or "" for the form itself. Handle is the selection handle of the selected control under the mouse: DSGN_HANDLE_E (3, the right edge: drag to change the width), DSGN_HANDLE_SE (4, the corner), or DSGN_HANDLE_S (5, the bottom edge), or DSGN_HANDLE_NONE (-1).
.item DesignKey (KeyCode, Shift): a key, for Delete, the arrow keys, and so on.
.item DesignPropertyChanged (CtrlName, PropertyName): the code of a UserControl on the form -- one of the project's own, put on the designer's toolbox with CompDesignControls (compiler.bas) -- called UserControl.PropertyChanged PropertyName: read its properties again. Such controls run their code on the form with UserControl.UserMode False.
.endlist
DesignSelection names the selected control; the form draws its eight selection handles over the controls (the three that resize in black) and shows the resize mouse pointers over them. The constants are in designer.bas, which also lists the control types, their properties, and events (see Include Libraries in the language reference). Together with CreateControl, RemoveControl, CallByName, Controls, Container, MoveBefore, LoadFormText, and the .frm model of designer.bas (FrmOpen, FrmText$, FrmCtlText$ / FrmCtlPaste to copy and paste controls, FormText$ to write the live form as .frm text), a designer has what the DVX BASIC IDE's own designer uses.
.code
Sub Canvas_DesignMouse(Action As Integer, Button As Integer, X As Integer, Y As Integer, CtrlName As String, Handle As Integer)
If Action = DSGN_MOUSE_DOWN Then
If Handle <> DSGN_HANDLE_NONE Then
resizing = True ' drag the selected control's size
Else
Canvas.DesignSelection = CtrlName
ShowProperties CtrlName
End If
ElseIf Action = DSGN_MOUSE_UP Then
resizing = False
End If
End Sub
.endcode
.h2 Drawing
Forms have Visual Basic's drawing methods and properties (Cls, PSet, Line, Circle, Point, Print, PaintPicture, DrawFocusRect, DrawBevel, DrawButtonFace, DrawArrow, DrawScrollBar, DrawScrollArrow, ScrollBarClick, ScrollBarsNeeded, PrintAccel, Scale, CurrentX, CurrentY, ForeColor, BackColor, DrawWidth, DrawStyle, FillColor, FillStyle, FontScale, AutoRedraw, ScaleMode, ScaleLeft, ScaleTop, ScaleWidth, ScaleHeight): see Drawing on Forms and PictureBoxes. In the form's own code use Me.Line, Me.Circle, and so on.
.h2 Example
.code
Sub Form1_Load ()
Form1.Caption = "Hello World"
Print "Form loaded!"
End Sub
Sub Form1_QueryUnload (Cancel As Integer)
If MsgBox("Really quit?", 4) <> 6 Then
Cancel = 1
End If
End Sub
Sub Form1_Resize ()
Print "Window resized"
End Sub
.endcode
.link ctrl.common.props Common Properties, Events, and Methods
.link ctrl.drawing Drawing on Forms and PictureBoxes
.link ctrl.frm FRM File Format