Started adding TextField.ReadOnly() and implemented it (mostly) on Windows.

This commit is contained in:
Pietro Gagliardi 2014-11-05 12:59:44 -05:00
parent 0bd58006a6
commit 5fc368fc23
6 changed files with 43 additions and 0 deletions

View File

@ -57,6 +57,11 @@ type TextField interface {
// The string passed to Invalid will be displayed to the user to inform them of what specifically is wrong with the input.
// Pass an empty string to remove the warning.
Invalid(reason string)
// ReadOnly and SetReadOnly get and set whether the TextField is read-only.
// A read-only TextField cannot be changed by the user, but its text can still be manipulated in other ways (selecting, copying, etc.).
ReadOnly() bool
SetReadOnly(readonly bool)
}
// NewTextField creates a new TextField.
@ -127,6 +132,7 @@ func NewGroup(text string, control Control) Group {
// TODO rename to TextBox? merge with TextField (but cannot use Invalid())? enable/disable line wrapping?
// TODO events
// TODO Tab key - insert horizontal tab or tab stop?
// TODO ReadOnly
type Textbox interface {
Control

View File

@ -128,6 +128,19 @@ void textfieldHideInvalidBalloonTip(HWND hwnd)
xpanic("error hiding TextField.Invalid() balloon tip", GetLastError());
}
// also good for Textbox
int textfieldReadOnly(HWND hwnd)
{
return (GetWindowLongPtrW(hwnd, GWL_STYLE) & ES_READONLY) != 0;
}
// also good for Textbox
void textfieldSetReadOnly(HWND hwnd, BOOL readonly)
{
if (SendMessageW(hwnd, EM_SETREADONLY, (WPARAM) readonly, 0) == 0)
xpanic("error setting TextField/Textbox as read-only/not read-only", GetLastError());
}
static LRESULT CALLBACK groupSubProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR id, DWORD_PTR data)
{
LRESULT lResult;

View File

@ -85,6 +85,7 @@ BOOL sharedWndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam, LRESULT *
return TRUE;
case WM_CTLCOLORSTATIC:
case WM_CTLCOLORBTN:
// TODO exempt read-only textboxes
if (SetBkMode((HDC) wParam, TRANSPARENT) == 0)
xpanic("error setting transparent background mode to Labels", GetLastError());
paintControlBackground((HWND) lParam, (HDC) wParam);

View File

@ -58,6 +58,18 @@ func (t *textfield) Invalid(reason string) {
C.textfieldSetAndShowInvalidBalloonTip(t.hwnd, toUTF16(reason))
}
func (t *textfield) ReadOnly() bool {
return C.textfieldReadOnly(t.hwnd) != 0
}
func (t *textfield) SetReadOnly(readonly bool) {
if readonly {
C.textfieldSetReadOnly(t.hwnd, C.TRUE)
return
}
C.textfieldSetReadOnly(t.hwnd, C.FALSE)
}
//export textfieldChanged
func textfieldChanged(data unsafe.Pointer) {
t := (*textfield)(data)

View File

@ -74,6 +74,8 @@ extern void checkboxSetChecked(HWND, BOOL);
extern void setTextFieldSubclass(HWND, void *);
extern void textfieldSetAndShowInvalidBalloonTip(HWND, WCHAR *);
extern void textfieldHideInvalidBalloonTip(HWND);
extern int textfieldReadOnly(HWND);
extern void textfieldSetReadOnly(HWND, BOOL);
extern void setGroupSubclass(HWND, void *);
extern HWND newUpDown(HWND, void *);
extern void setSpinboxEditSubclass(HWND, void *);

View File

@ -54,6 +54,8 @@ var ddata = []dtype{
type testwin struct {
t Tab
w Window
roenter TextField
roro TextField
repainter *repainter
fe *ForeignEvent
festack Stack
@ -176,6 +178,13 @@ func (tw *testwin) make(done chan struct{}) {
done <- struct{}{}
return true
})
tw.roenter = NewTextField()
tw.roro = NewTextField()
tw.roro.SetReadOnly(true)
tw.roenter.OnChanged(func() {
tw.roro.SetText(tw.roenter.Text())
})
tw.t.Append("Read-Only", newVerticalStack(tw.roenter, tw.roro))
tw.icons, tw.il = readIcons() // repainter uses these
tw.repainter = newRepainter(15)
tw.t.Append("Repaint", tw.repainter.grid)