Whew, nearly finished!

* Added TextRequestDialog (only asynchronous version because it is easier and the preflet should not block [it gets update messages from the kernel]).
* PPPoE: We now read the available interfaces from the kernel module, so the user does not have to know the exact name of the interface he wants to use. It can be chosen from a BMenuField. You can also enter any interface name if you select "Other: " from the menu.
* Small changes (e.g.: call MakeFocus(), etc.).


git-svn-id: file:///srv/svn/repos/haiku/trunk/current@7120 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Waldemar Kornewald 2004-03-30 11:06:40 +00:00
parent 53a2aa40d5
commit 0f197ce81a
20 changed files with 493 additions and 184 deletions

View File

@ -62,8 +62,8 @@ class DialUpAddon {
{ return false; }
virtual bool HasTemporaryProfile() const
{ return false; }
virtual void IsModified(bool& settings, bool& profile) const
{ settings = profile = false; }
virtual void IsModified(bool *settings, bool *profile) const
{ *settings = *profile = false; }
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary)
{ return false; }
@ -83,7 +83,7 @@ class DialUpAddon {
private:
BMessage *fAddons;
char _reserved[31];
int32 _reserved[7];
};

View File

@ -8,6 +8,8 @@
#include <Application.h>
#include <Window.h>
#include "InterfaceUtils.h"
#include "DialUpView.h"
@ -42,7 +44,9 @@ int main()
DialUpApplication::DialUpApplication()
: BApplication(DIAL_UP_SIGNATURE)
{
DialUpWindow *window = new DialUpWindow(BRect(150, 50, 450, 435));
BRect rect(150, 50, 450, 435);
DialUpWindow *window = new DialUpWindow(rect);
window->MoveTo(center_on_screen(rect, window));
window->Show();
}

View File

@ -8,8 +8,10 @@
#include "DialUpView.h"
#include "DialUpAddon.h"
#include <cstring>
#include "InterfaceUtils.h"
#include "MessageDriverSettingsUtils.h"
#include "TextRequestDialog.h"
// built-in add-ons
#include "GeneralAddon.h"
@ -37,16 +39,15 @@
#include <File.h>
#include <Path.h>
#include <cstring>
#define MSG_CREATE_NEW 'NEWI'
#define MSG_FINISH_CREATE_NEW 'FNEW'
#define MSG_DELETE_CURRENT 'DELI'
#define MSG_SELECT_INTERFACE 'SELI'
#define MSG_CONNECT_BUTTON 'CONI'
#define LABEL_CREATE_NEW "Create new..."
#define LABEL_DELETE_CURRENT "Delete current"
#define LABEL_CREATE_NEW "Create New..."
#define LABEL_DELETE_CURRENT "Delete Current"
#define LABEL_CONNECT "Connect"
#define LABEL_DISCONNECT "Disconnect"
@ -162,7 +163,7 @@ DialUpView::AttachedToWindow()
fConnectButton->SetTarget(this);
if(fListener.InitCheck() != B_OK)
(new BAlert(ERROR_TITLE, ERROR_NO_PPP_STACK, TEXT_OK))->Go();
(new BAlert(ERROR_TITLE, ERROR_NO_PPP_STACK, TEXT_OK))->Go(NULL);
}
@ -174,12 +175,23 @@ DialUpView::MessageReceived(BMessage *message)
HandleReportMessage(message);
break;
// -------------------------------------------------
case MSG_CREATE_NEW: {
// TODO: open dialog asking for name
AddInterface("New interface", true);
(new TextRequestDialog("New Interface", "Interface Name: "))->Go(
new BInvoker(new BMessage(MSG_FINISH_CREATE_NEW), this));
} break;
case MSG_FINISH_CREATE_NEW: {
int32 which;
message->FindInt32("which", &which);
const char *name = message->FindString("text");
if(which == 1 && name && strlen(name) > 0)
AddInterface(name, true);
if(fCurrentItem)
fCurrentItem->SetMarked(true);
} break;
// -------------------------------------------------
case MSG_DELETE_CURRENT: {
fInterfaceMenu->RemoveItem(fCurrentItem);
@ -231,11 +243,11 @@ DialUpView::LoadSettings(bool isNew)
if(fCurrentItem && !isNew) {
BString name("pppidf/");
name << fCurrentItem->Label();
if(!ReadMessageDriverSettings(name.String(), fSettings))
if(!ReadMessageDriverSettings(name.String(), &fSettings))
return false;
name = "pppidf/profile/";
name << fCurrentItem->Label();
if(!ReadMessageDriverSettings(name.String(), fProfile))
if(!ReadMessageDriverSettings(name.String(), &fProfile))
profilePointer = settingsPointer;
}
@ -256,9 +268,9 @@ DialUpView::LoadSettings(bool isNew)
void
DialUpView::IsModified(bool& settings, bool& profile)
DialUpView::IsModified(bool *settings, bool *profile)
{
settings = profile = false;
*settings = *profile = false;
bool addonSettingsChanged, addonProfileChanged;
// for current addon
@ -268,27 +280,26 @@ DialUpView::IsModified(bool& settings, bool& profile)
if(!addon)
continue;
addon->IsModified(addonSettingsChanged, addonProfileChanged);
addon->IsModified(&addonSettingsChanged, &addonProfileChanged);
if(addonSettingsChanged)
settings = true;
*settings = true;
if(addonProfileChanged)
profile = true;
*profile = true;
}
}
bool
DialUpView::SaveSettings(BMessage& settings, BMessage& profile, bool saveModified)
DialUpView::SaveSettings(BMessage *settings, BMessage *profile, bool saveTemporary)
{
if(!fCurrentItem)
if(!fCurrentItem || !settings || !profile)
return false;
DialUpAddon *addon;
TemplateList<DialUpAddon*> addons;
for(int32 index = 0;
fAddons.FindPointer(DUN_TAB_ADDON_TYPE, index,
reinterpret_cast<void**>(&addon)) == B_OK;
index++) {
reinterpret_cast<void**>(&addon)) == B_OK; index++) {
if(!addon)
continue;
@ -300,12 +311,12 @@ DialUpView::SaveSettings(BMessage& settings, BMessage& profile, bool saveModifie
addons.AddItem(addon, insertIndex);
}
settings.AddInt32("Interface", static_cast<int32>(fWatching));
settings->AddInt32("Interface", static_cast<int32>(fWatching));
if(fCurrentItem)
settings.AddString("InterfaceName", fCurrentItem->Label());
settings->AddString("InterfaceName", fCurrentItem->Label());
for(int32 index = 0; index < addons.CountItems(); index++)
addons.ItemAt(index)->SaveSettings(&settings, &profile, saveModified);
addons.ItemAt(index)->SaveSettings(settings, profile, saveTemporary);
return true;
}
@ -315,12 +326,12 @@ bool
DialUpView::SaveSettingsToFile()
{
bool settingsChanged, profileChanged;
IsModified(settingsChanged, profileChanged);
IsModified(&settingsChanged, &profileChanged);
if(!settingsChanged && !profileChanged)
return true;
BMessage settings, profile;
if(!SaveSettings(settings, profile, false))
if(!SaveSettings(&settings, &profile, false))
return false;
BDirectory settingsDirectory;
@ -637,7 +648,7 @@ void
DialUpView::AddInterface(const char *name, bool isNew = false)
{
if(fInterfaceMenu->FindItem(name)) {
(new BAlert(ERROR_TITLE, ERROR_INTERFACE_EXISTS, TEXT_OK))->Go();
(new BAlert(ERROR_TITLE, ERROR_INTERFACE_EXISTS, TEXT_OK))->Go(NULL);
return;
}
@ -649,7 +660,8 @@ DialUpView::AddInterface(const char *name, bool isNew = false)
fInterfaceMenu->AddItem(item, index);
if(CountInterfaces() == 1)
fInterfaceMenu->SetLabelFromMarked(true);
SelectInterface(CountInterfaces() - 1, isNew);
item->SetMarked(true);
SelectInterface(index, isNew);
}
@ -692,9 +704,10 @@ DialUpView::SelectInterface(int32 index, bool isNew = false)
fTabView->Hide();
fConnectButton->SetEnabled(false);
} else if(!isNew && !LoadSettings(false)) {
(new BAlert(ERROR_TITLE, ERROR_LOADING_FAILED, TEXT_OK))->Go();
(new BAlert(ERROR_TITLE, ERROR_LOADING_FAILED, TEXT_OK))->Go(NULL);
LoadSettings(true);
}
} else if(isNew && !LoadSettings(true))
(new BAlert(ERROR_TITLE, ERROR_LOADING_FAILED, TEXT_OK))->Go(NULL);
}

View File

@ -35,8 +35,8 @@ class DialUpView : public BView {
void WatchInterface(ppp_interface_id ID);
bool LoadSettings(bool isNew);
void IsModified(bool& settings, bool& profile);
bool SaveSettings(BMessage& settings, BMessage& profile, bool saveTemporary);
void IsModified(bool *settings, bool *profile);
bool SaveSettings(BMessage *settings, BMessage *profile, bool saveTemporary);
bool SaveSettingsToFile();
void LoadInterfaces();

View File

@ -12,6 +12,8 @@
#include "InterfaceUtils.h"
#include "MessageDriverSettingsUtils.h"
#include <stl_algobase.h>
// for max()
#include <Box.h>
#include <Button.h>
@ -97,7 +99,7 @@ GeneralAddon::LoadDeviceSettings()
{
int32 index = 0;
BMessage device;
if(!FindMessageParameter(PPP_DEVICE_KEY, *fSettings, device, &index))
if(!FindMessageParameter(PPP_DEVICE_KEY, *fSettings, &device, &index))
return false;
// TODO: tell user that device specification is missing
@ -123,7 +125,7 @@ GeneralAddon::LoadAuthenticationSettings()
int32 itemIndex = 0;
BMessage authentication, item;
if(!FindMessageParameter(PPP_AUTHENTICATOR_KEY, *fProfile, item, &itemIndex))
if(!FindMessageParameter(PPP_AUTHENTICATOR_KEY, *fProfile, &item, &itemIndex))
return true;
// find authenticators (though we load all authenticators, we only use one)
@ -147,7 +149,7 @@ GeneralAddon::LoadAuthenticationSettings()
// load username and password
BMessage parameter;
int32 parameterIndex = 0;
if(FindMessageParameter("User", item, parameter, &parameterIndex)
if(FindMessageParameter("User", item, &parameter, &parameterIndex)
&& parameter.FindString(MDSU_VALUES, &fUsername) == B_OK) {
hasUsername = true;
parameter.AddBool(MDSU_VALID, true);
@ -155,7 +157,7 @@ GeneralAddon::LoadAuthenticationSettings()
}
parameterIndex = 0;
if(FindMessageParameter("Password", item, parameter, &parameterIndex)
if(FindMessageParameter("Password", item, &parameter, &parameterIndex)
&& parameter.FindString(MDSU_VALUES, &fPassword) == B_OK) {
fHasPassword = true;
parameter.AddBool(MDSU_VALID, true);
@ -175,66 +177,62 @@ GeneralAddon::LoadAuthenticationSettings()
bool
GeneralAddon::HasTemporaryProfile() const
{
return !fGeneralView->DoesSavePassword();
return fGeneralView->HasTemporaryProfile();
}
void
GeneralAddon::IsModified(bool& settings, bool& profile) const
GeneralAddon::IsModified(bool *settings, bool *profile) const
{
if(!fSettings) {
settings = profile = false;
*settings = *profile = false;
return;
}
bool deviceSettings, authenticationSettings, deviceProfile, authenticationProfile;
IsDeviceModified(deviceSettings, deviceProfile);
IsAuthenticationModified(authenticationSettings, authenticationProfile);
IsDeviceModified(&deviceSettings, &deviceProfile);
IsAuthenticationModified(&authenticationSettings, &authenticationProfile);
settings = (deviceSettings || authenticationSettings);
profile = (deviceProfile || authenticationProfile);
*settings = (deviceSettings || authenticationSettings);
*profile = (deviceProfile || authenticationProfile);
}
void
GeneralAddon::IsDeviceModified(bool& settings, bool& profile) const
GeneralAddon::IsDeviceModified(bool *settings, bool *profile) const
{
if(fDeviceAddon)
settings = (!fGeneralView->DeviceName() || fGeneralView->IsDeviceModified());
else
settings = fGeneralView->DeviceName();
profile = false;
fGeneralView->IsDeviceModified(settings, profile);
}
void
GeneralAddon::IsAuthenticationModified(bool& settings, bool& profile) const
GeneralAddon::IsAuthenticationModified(bool *settings, bool *profile) const
{
// currently we only support selecting one authenticator
if(fAuthenticatorsCount == 0)
settings = fGeneralView->AuthenticatorName();
*settings = fGeneralView->AuthenticatorName();
else {
BMessage authentication;
if(fSettings->FindMessage(GENERAL_TAB_AUTHENTICATION, &authentication) != B_OK) {
settings = profile = false;
*settings = *profile = false;
return;
// error!
}
BString authenticator;
if(authentication.FindString(GENERAL_TAB_AUTHENTICATORS, &authenticator) != B_OK) {
settings = profile = false;
if(authentication.FindString(GENERAL_TAB_AUTHENTICATORS,
&authenticator) != B_OK) {
*settings = *profile = false;
return;
// error!
}
settings = (!fGeneralView->AuthenticatorName()
*settings = (!fGeneralView->AuthenticatorName()
|| authenticator != fGeneralView->AuthenticatorName());
}
profile = (settings || fUsername != fGeneralView->Username()
*profile = (*settings || fUsername != fGeneralView->Username()
|| (fPassword != fGeneralView->Password() && fHasPassword)
|| fHasPassword != fGeneralView->DoesSavePassword());
}
@ -247,7 +245,8 @@ GeneralAddon::SaveSettings(BMessage *settings, BMessage *profile, bool saveTempo
return false;
// TODO: tell user that a device is needed (if we fail because of this)
if(!fDeviceAddon || !fDeviceAddon->SaveSettings(settings, profile, saveTemporary))
if(!fGeneralView->DeviceAddon() || !fGeneralView->DeviceAddon()->SaveSettings(
settings, profile, saveTemporary))
return false;
if(fGeneralView->AuthenticatorName()) {
@ -333,7 +332,7 @@ GeneralAddon::MarkAuthenticatorAsValid(const BString& moduleName)
int32 index = 0;
BString name;
for(; FindMessageParameter(PPP_AUTHENTICATOR_KEY, *fSettings, authenticator,
for(; FindMessageParameter(PPP_AUTHENTICATOR_KEY, *fSettings, &authenticator,
&index); index++) {
authenticator.FindString("KernelModuleName", &name);
if(name == moduleName) {
@ -389,12 +388,9 @@ GeneralView::GeneralView(GeneralAddon *addon, BRect frame)
fPassword->TextView()->HideTyping(true);
float usernameWidth = StringWidth(fUsername->Label()) + 5;
float passwordWidth = StringWidth(fPassword->Label()) + 5;
if(usernameWidth > passwordWidth)
passwordWidth = usernameWidth;
else
usernameWidth = passwordWidth;
fUsername->SetDivider(usernameWidth);
fPassword->SetDivider(passwordWidth);
float width = max(usernameWidth, passwordWidth);
fUsername->SetDivider(width);
fPassword->SetDivider(width);
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 20;
@ -462,6 +458,7 @@ GeneralView::Reload()
fSavePassword->SetValue(Addon()->HasPassword());
ReloadDeviceView();
UpdateControls();
}
@ -486,18 +483,15 @@ GeneralView::AuthenticatorName() const
}
bool
GeneralView::IsDeviceModified() const
void
GeneralView::IsDeviceModified(bool *settings, bool *profile) const
{
if(fDeviceAddon != Addon()->DeviceAddon())
return true;
else if(fDeviceAddon) {
bool settings, profile;
*settings = *profile = true;
else if(fDeviceAddon)
fDeviceAddon->IsModified(settings, profile);
return settings;
}
return false;
else
*settings = *profile = false;
}
@ -530,6 +524,7 @@ GeneralView::MessageReceived(BMessage *message)
break;
case MSG_SELECT_AUTHENTICATOR:
UpdateControls();
break;
default:
@ -578,6 +573,26 @@ GeneralView::ReloadDeviceView()
}
void
GeneralView::UpdateControls()
{
BMenu *menu = fAuthenticatorField->Menu();
int32 index = menu->IndexOf(menu->FindMarked());
if(index < 0)
fAuthenticatorNone->SetMarked(true);
if(index == 0) {
fUsername->SetEnabled(false);
fPassword->SetEnabled(false);
fSavePassword->SetEnabled(false);
} else {
fUsername->SetEnabled(true);
fPassword->SetEnabled(true);
fSavePassword->SetEnabled(true);
}
}
void
GeneralView::AddDevices()
{
@ -618,7 +633,7 @@ GeneralView::AddAuthenticators()
}
int32 insertAt = FindNextMenuInsertionIndex(fAuthenticatorField->Menu(),
name, 2);
name.String(), 2);
fAuthenticatorField->Menu()->AddItem(new BMenuItem(name.String(), message),
insertAt);
}

View File

@ -56,9 +56,9 @@ class GeneralAddon : public DialUpAddon {
bool LoadAuthenticationSettings();
virtual bool HasTemporaryProfile() const;
virtual void IsModified(bool& settings, bool& profile) const;
void IsDeviceModified(bool& settings, bool& profile) const;
void IsAuthenticationModified(bool& settings, bool& profile) const;
virtual void IsModified(bool *settings, bool *profile) const;
void IsDeviceModified(bool *settings, bool *profile) const;
void IsAuthenticationModified(bool *settings, bool *profile) const;
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary);
@ -96,15 +96,22 @@ class GeneralView : public BView {
bool DoesSavePassword() const
{ return fSavePassword->Value(); }
bool HasTemporaryProfile() const
{ return !DoesSavePassword() || (fDeviceAddon &&
fDeviceAddon->HasTemporaryProfile()); }
DialUpAddon *DeviceAddon() const
{ return fDeviceAddon; }
const char *DeviceName() const;
const char *AuthenticatorName() const;
bool IsDeviceModified() const;
void IsDeviceModified(bool *settings, bool *profile) const;
virtual void AttachedToWindow();
virtual void MessageReceived(BMessage *message);
private:
void ReloadDeviceView();
void UpdateControls();
void AddDevices();
void AddAuthenticators();

View File

@ -11,6 +11,8 @@
#include "IPCPAddon.h"
#include "MessageDriverSettingsUtils.h"
#include <stl_algobase.h>
// for max()
#include <Box.h>
#include <Button.h>
@ -19,6 +21,7 @@
#include <IPCP.h>
// from IPCP addon
#define MSG_CHANGE_SETTINGS 'CHGS'
#define MSG_RESET_SETTINGS 'RSTS'
@ -76,13 +79,14 @@ IPCPAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
fProfile = profile;
if(!settings || !profile || isNew) {
fIPCPWindow->Reload();
// reset all views
return true;
}
BMessage protocol;
// settings
int32 protocolIndex = FindIPCPProtocol(*fSettings, protocol);
int32 protocolIndex = FindIPCPProtocol(*fSettings, &protocol);
if(protocolIndex < 0)
return false;
@ -90,24 +94,22 @@ IPCPAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
fSettings->ReplaceMessage(MDSU_PARAMETERS, protocolIndex, &protocol);
// profile
protocolIndex = FindIPCPProtocol(*fProfile, protocol);
protocolIndex = FindIPCPProtocol(*fProfile, &protocol);
if(protocolIndex < 0)
return false;
// the "Local" side parameter
BMessage local;
int32 localSideIndex = 0;
if(!FindMessageParameter(IPCP_LOCAL_SIDE_KEY, protocol, local, &localSideIndex)) {
protocol.AddBool(MDSU_VALID, true);
fProfile->ReplaceMessage(MDSU_PARAMETERS, protocolIndex, &protocol);
return true;
}
if(!FindMessageParameter(IPCP_LOCAL_SIDE_KEY, protocol, &local, &localSideIndex))
local.MakeEmpty();
// just fall through and pretend we have an empty "Local" side parameter
// now load the supported parameters (the client-relevant subset)
BString name;
BMessage parameter;
int32 index = 0;
if(!FindMessageParameter(IPCP_IP_ADDRESS_KEY, local, parameter, &index)
if(!FindMessageParameter(IPCP_IP_ADDRESS_KEY, local, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fIPAddress) != B_OK)
fIPAddress = "";
else {
@ -119,7 +121,7 @@ IPCPAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
}
index = 0;
if(!FindMessageParameter(IPCP_PRIMARY_DNS_KEY, local, parameter, &index)
if(!FindMessageParameter(IPCP_PRIMARY_DNS_KEY, local, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fPrimaryDNS) != B_OK)
fPrimaryDNS = "";
else {
@ -131,7 +133,7 @@ IPCPAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
}
index = 0;
if(!FindMessageParameter(IPCP_SECONDARY_DNS_KEY, local, parameter, &index)
if(!FindMessageParameter(IPCP_SECONDARY_DNS_KEY, local, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fSecondaryDNS) != B_OK)
fSecondaryDNS = "";
else {
@ -154,18 +156,18 @@ IPCPAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
void
IPCPAddon::IsModified(bool& settings, bool& profile) const
IPCPAddon::IsModified(bool *settings, bool *profile) const
{
// some part of this work is done by the "Protocols" tab, thus we do not need to
// check whether we are a new protocol or not
settings = false;
*settings = false;
if(!fSettings) {
profile = false;
*profile = false;
return;
}
profile = (fIPAddress != fIPCPWindow->IPAddress()
*profile = (fIPAddress != fIPCPWindow->IPAddress()
|| fPrimaryDNS != fIPCPWindow->PrimaryDNS()
|| fSecondaryDNS != fIPCPWindow->SecondaryDNS());
}
@ -245,12 +247,15 @@ IPCPAddon::CreateView(BPoint leftTop)
int32
IPCPAddon::FindIPCPProtocol(BMessage& message, BMessage& protocol) const
IPCPAddon::FindIPCPProtocol(const BMessage& message, BMessage *protocol) const
{
if(!protocol)
return -1;
BString name;
for(int32 index = 0; FindMessageParameter(PPP_PROTOCOL_KEY, message, protocol,
&index); index++)
if(protocol.FindString(MDSU_VALUES, &name) == B_OK
if(protocol->FindString(MDSU_VALUES, &name) == B_OK
&& name == kKernelModuleName)
return index;
@ -291,18 +296,7 @@ IPCPWindow::IPCPWindow(IPCPAddon *addon, BRect frame)
float ipAddressWidth = backgroundView->StringWidth(fIPAddress->Label()) + 5;
float primaryDNSWidth = backgroundView->StringWidth(fPrimaryDNS->Label()) + 5;
float secondaryDNSWidth = backgroundView->StringWidth(fSecondaryDNS->Label()) + 5;
float controlWidth;
if(ipAddressWidth > primaryDNSWidth) {
if(ipAddressWidth > secondaryDNSWidth)
controlWidth = ipAddressWidth;
else
controlWidth = secondaryDNSWidth;
} else {
if(primaryDNSWidth > secondaryDNSWidth)
controlWidth = primaryDNSWidth;
else
controlWidth = secondaryDNSWidth;
}
float controlWidth = max(max(ipAddressWidth, primaryDNSWidth), secondaryDNSWidth);
fIPAddress->SetDivider(controlWidth);
fPrimaryDNS->SetDivider(controlWidth);
@ -329,7 +323,7 @@ IPCPWindow::IPCPWindow(IPCPAddon *addon, BRect frame)
AddChild(backgroundView);
SetDefaultButton(fOKButton);
Run();
// this must be set in order for Reload() to work properly
// this must be called in order for Reload() to work properly
}
@ -337,6 +331,7 @@ void
IPCPWindow::Reload()
{
Lock();
fIPAddress->MakeFocus(true);
fIPAddress->SetText(Addon()->IPAddress());
fPreviousIPAddress = Addon()->IPAddress();
fPrimaryDNS->SetText(Addon()->PrimaryDNS());

View File

@ -45,14 +45,14 @@ class IPCPAddon : public DialUpAddon {
virtual const char *KernelModuleName() const;
virtual bool LoadSettings(BMessage *settings, BMessage *profile, bool isNew);
virtual void IsModified(bool& settings, bool& profile) const;
virtual void IsModified(bool *settings, bool *profile) const;
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary);
virtual bool GetPreferredSize(float *width, float *height) const;
virtual BView *CreateView(BPoint leftTop);
private:
int32 FindIPCPProtocol(BMessage& message, BMessage& protocol) const;
int32 FindIPCPProtocol(const BMessage& message, BMessage *protocol) const;
private:
bool fIsNew;

View File

@ -11,17 +11,32 @@
#include <ListView.h>
#include <Menu.h>
#include <MenuItem.h>
#include <Screen.h>
#include <String.h>
#include <StringItem.h>
#include <Window.h>
BPoint
center_on_screen(BRect rect, BWindow *window = NULL)
{
BRect screenFrame = (BScreen(window).Frame());
BPoint point((screenFrame.Width() - rect.Width()) / 2.0,
(screenFrame.Height() - rect.Height()) / 2.0);
if(!screenFrame.Contains(point))
point.Set(0, 0);
return point;
}
int32
FindNextMenuInsertionIndex(BMenu *menu, const BString& name, int32 index = 0)
FindNextMenuInsertionIndex(BMenu *menu, const char *name, int32 index = 0)
{
BMenuItem *item;
for(; index < menu->CountItems(); index++) {
item = menu->ItemAt(index);
if(item && name.ICompare(item->Label()) <= 0)
if(item && strcasecmp(name, item->Label()) <= 0)
return index;
}
@ -30,13 +45,13 @@ FindNextMenuInsertionIndex(BMenu *menu, const BString& name, int32 index = 0)
int32
FindNextListInsertionIndex(BListView *list, const BString& name)
FindNextListInsertionIndex(BListView *list, const char *name)
{
int32 index = 0;
BStringItem *item;
for(; index < list->CountItems(); index++) {
item = static_cast<BStringItem*>(list->ItemAt(index));
if(item && name.ICompare(item->Text()) <= 0)
if(item && strcasecmp(name, item->Text()) <= 0)
return index;
}
@ -68,7 +83,7 @@ AddAddonsToMenu(const BMessage *source, BMenu *menu, const char *type, uint32 wh
name << ")";
}
int32 insertAt = FindNextMenuInsertionIndex(menu, name);
int32 insertAt = FindNextMenuInsertionIndex(menu, name.String());
menu->AddItem(new BMenuItem(name.String(), message), insertAt);
}
}

View File

@ -14,11 +14,13 @@ class DialUpAddon;
class BListView;
class BMenu;
class BString;
class BWindow;
extern int32 FindNextMenuInsertionIndex(BMenu *menu, const BString& name,
extern BPoint center_on_screen(BRect rect, BWindow *window = NULL);
extern int32 FindNextMenuInsertionIndex(BMenu *menu, const char *name,
int32 index = 0);
extern int32 FindNextListInsertionIndex(BListView *list, const BString& name);
extern int32 FindNextListInsertionIndex(BListView *list, const char *name);
extern void AddAddonsToMenu(const BMessage *source, BMenu *menu, const char *type,
uint32 what);

View File

@ -15,6 +15,7 @@ SimpleTest DialUpPreflet :
# utils
InterfaceUtils.cpp
MessageDriverSettingsUtils.cpp
TextRequestDialog.cpp
# built-in add-ons
GeneralAddon.cpp

View File

@ -16,14 +16,15 @@
bool
FindMessageParameter(const char *name, BMessage& message, BMessage& save,
FindMessageParameter(const char *name, const BMessage& message, BMessage *save,
int32 *startIndex = NULL)
{
// XXX: this should be removed when we can replace BMessage with something better
BString string;
int32 index = startIndex ? *startIndex : 0;
for(; message.FindMessage(MDSU_PARAMETERS, index, &save) == B_OK; index++) {
if(save.FindString(MDSU_NAME, &string) == B_OK && string.ICompare(name) == 0) {
for(; message.FindMessage(MDSU_PARAMETERS, index, save) == B_OK; index++) {
if(save->FindString(MDSU_NAME, &string) == B_OK
&& string.ICompare(name) == 0) {
if(startIndex)
*startIndex = index;
return true;
@ -36,24 +37,24 @@ FindMessageParameter(const char *name, BMessage& message, BMessage& save,
static
bool
AddParameter(const driver_parameter *parameter, BMessage& message)
AddParameter(const driver_parameter *parameter, BMessage *message)
{
if(!parameter)
if(!parameter || !message)
return false;
if(parameter->name)
message.AddString(MDSU_NAME, parameter->name);
message->AddString(MDSU_NAME, parameter->name);
else
return false;
for(int32 index = 0; index < parameter->value_count; index++)
if(parameter->values[index])
message.AddString(MDSU_VALUES, parameter->values[index]);
message->AddString(MDSU_VALUES, parameter->values[index]);
for(int32 index = 0; index < parameter->parameter_count; index++) {
BMessage parameterMessage;
AddParameter(&parameter->parameters[index], parameterMessage);
message.AddMessage(MDSU_PARAMETERS, &parameterMessage);
AddParameter(&parameter->parameters[index], &parameterMessage);
message->AddMessage(MDSU_PARAMETERS, &parameterMessage);
}
return true;
@ -61,9 +62,9 @@ AddParameter(const driver_parameter *parameter, BMessage& message)
bool
ReadMessageDriverSettings(const char *name, BMessage& message)
ReadMessageDriverSettings(const char *name, BMessage *message)
{
if(!name)
if(!name || !message)
return false;
void *handle = load_driver_settings(name);
@ -77,8 +78,8 @@ ReadMessageDriverSettings(const char *name, BMessage& message)
for(int32 index = 0; index < settings->parameter_count; index++) {
BMessage parameter;
AddParameter(&settings->parameters[index], parameter);
message.AddMessage(MDSU_PARAMETERS, &parameter);
AddParameter(&settings->parameters[index], &parameter);
message->AddMessage(MDSU_PARAMETERS, &parameter);
}
unload_driver_settings(handle);

View File

@ -19,10 +19,10 @@ class BFile;
#define MDSU_VALID "Valid"
extern bool FindMessageParameter(const char *name, BMessage& message,
BMessage& save, int32 *startIndex = NULL);
extern bool FindMessageParameter(const char *name, const BMessage& message,
BMessage *save, int32 *startIndex = NULL);
extern bool ReadMessageDriverSettings(const char *name, BMessage& message);
extern bool ReadMessageDriverSettings(const char *name, BMessage *message);
extern bool WriteMessageDriverSettings(BFile& file, const BMessage& message);
#endif

View File

@ -10,7 +10,11 @@
#include "PPPoEAddon.h"
#include "InterfaceUtils.h"
#include "MessageDriverSettingsUtils.h"
#include "TextRequestDialog.h"
#include <stl_algobase.h>
// for max()
#include <Box.h>
#include <Button.h>
@ -21,14 +25,17 @@
#include <StringView.h>
#include <Window.h>
#include <PPPDefs.h>
#include <PPPManager.h>
#include <PPPoE.h>
// from PPPoE addon
#define MSG_SHOW_SERVICE_WINDOW 'SHSW'
#define MSG_CHANGE_SERVICE 'SELD'
#define MSG_RESET_SERVICE 'SELA'
#define MSG_SELECT_INTERFACE 'SELI'
#define MSG_SELECT_OTHER 'SELO'
#define MSG_FINISH_SELECT_OTHER 'FISO'
#define MSG_SHOW_SERVICE_WINDOW 'SHSW'
#define MSG_CHANGE_SERVICE 'CHGS'
#define MSG_RESET_SERVICE 'RESS'
static const char kFriendlyName[] = "DSL, Cable, etc.";
static const char kTechnicalName[] = "PPPoE";
@ -90,7 +97,7 @@ PPPoEAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
BMessage device;
int32 deviceIndex = 0;
if(!FindMessageParameter(PPP_DEVICE_KEY, *fSettings, device, &deviceIndex))
if(!FindMessageParameter(PPP_DEVICE_KEY, *fSettings, &device, &deviceIndex))
return false;
// error: no device
@ -101,7 +108,7 @@ PPPoEAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
BMessage parameter;
int32 index = 0;
if(!FindMessageParameter(PPPoE_INTERFACE_KEY, device, parameter, &index)
if(!FindMessageParameter(PPPoE_INTERFACE_KEY, device, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fInterfaceName) != B_OK)
return false;
// error: no interface
@ -111,7 +118,7 @@ PPPoEAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
}
index = 0;
if(!FindMessageParameter(PPPoE_AC_NAME_KEY, device, parameter, &index)
if(!FindMessageParameter(PPPoE_AC_NAME_KEY, device, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fACName) != B_OK)
fACName = "";
else {
@ -120,7 +127,7 @@ PPPoEAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
}
index = 0;
if(!FindMessageParameter(PPPoE_SERVICE_NAME_KEY, device, parameter, &index)
if(!FindMessageParameter(PPPoE_SERVICE_NAME_KEY, device, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fServiceName) != B_OK)
fServiceName = "";
else {
@ -136,15 +143,16 @@ PPPoEAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
void
PPPoEAddon::IsModified(bool& settings, bool& profile) const
PPPoEAddon::IsModified(bool *settings, bool *profile) const
{
*profile = false;
if(!fSettings) {
settings = profile = false;
*settings = false;
return;
}
profile = false;
settings = (fInterfaceName != fPPPoEView->InterfaceName()
*settings = (fInterfaceName != fPPPoEView->InterfaceName()
|| fACName != fPPPoEView->ACName()
|| fServiceName != fPPPoEView->ServiceName());
}
@ -231,10 +239,13 @@ PPPoEView::PPPoEView(PPPoEAddon *addon, BRect frame)
BRect rect = Bounds();
rect.InsetBy(5, 0);
rect.bottom = 20;
fInterfaceName = new BTextControl(rect, "interface", "Interface Name: ", NULL,
NULL);
fInterfaceName->SetDivider(StringWidth(fInterfaceName->Label()) + 5);
// TODO: add "Query" pop-up menu to allow quickly choosing interface from list
fInterface = new BMenuField(rect, "interface", "Interface: ",
new BPopUpMenu("Select Interface..."));
fInterface->SetDivider(StringWidth(fInterface->Label()) + 5);
fInterface->Menu()->AddSeparatorItem();
fOtherInterface = new BMenuItem("Other:", new BMessage(MSG_SELECT_OTHER));
fInterface->Menu()->AddItem(fOtherInterface);
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 45;
fServiceButton = new BButton(rect, "ServiceButton", "Service",
@ -270,12 +281,9 @@ PPPoEView::PPPoEView(PPPoEAddon *addon, BRect frame)
// set divider of text controls
float acNameWidth = StringWidth(fACName->Label()) + 5;
float serviceNameWidth = StringWidth(fServiceName->Label()) + 5;
if(acNameWidth > serviceNameWidth)
serviceNameWidth = acNameWidth;
else
acNameWidth = serviceNameWidth;
fACName->SetDivider(acNameWidth);
fServiceName->SetDivider(serviceNameWidth);
float width = max(acNameWidth, serviceNameWidth);
fACName->SetDivider(width);
fServiceName->SetDivider(width);
// add buttons to service window
rect = serviceBox->Frame();
@ -297,8 +305,9 @@ PPPoEView::PPPoEView(PPPoEAddon *addon, BRect frame)
fServiceWindow->AddChild(serviceView);
fServiceWindow->SetDefaultButton(fOKButton);
fServiceWindow->Run();
// this must be called in order for Reload() to work properly
AddChild(fInterfaceName);
AddChild(fInterface);
AddChild(fServiceButton);
}
@ -312,10 +321,14 @@ PPPoEView::~PPPoEView()
void
PPPoEView::Reload()
{
fInterfaceName->SetText(Addon()->InterfaceName());
// update interface settings
ReloadInterfaces();
// update service settings (in service window => must be locked)
fServiceWindow->Lock();
fACName->SetText(Addon()->ACName());
fPreviousACName = Addon()->ACName();
fServiceName->MakeFocus(true);
fServiceName->SetText(Addon()->ServiceName());
fPreviousServiceName = Addon()->ServiceName();
fServiceWindow->Unlock();
@ -326,7 +339,7 @@ void
PPPoEView::AttachedToWindow()
{
SetViewColor(Parent()->ViewColor());
fInterfaceName->SetTarget(this);
fInterface->Menu()->SetTargetForItems(this);
fServiceButton->SetTarget(this);
fACName->SetTarget(this);
fServiceName->SetTarget(this);
@ -339,7 +352,53 @@ void
PPPoEView::MessageReceived(BMessage *message)
{
switch(message->what) {
case MSG_SELECT_INTERFACE: {
BMenuItem *item = fInterface->Menu()->FindMarked();
if(item)
fInterfaceName = item->Label();
} break;
case MSG_SELECT_OTHER:
(new TextRequestDialog("InterfaceName", "Interface Name: ",
fInterfaceName.String()))->Go(new BInvoker(
new BMessage(MSG_FINISH_SELECT_OTHER), this));
break;
case MSG_FINISH_SELECT_OTHER: {
int32 which;
message->FindInt32("which", &which);
const char *name = message->FindString("text");
BMenu *menu = fInterface->Menu();
BMenuItem *item;
if(which != 1 || !name || strlen(name) == 0) {
item = menu->FindItem(fInterfaceName.String());
if(item && menu->IndexOf(item) <= menu->CountItems() - 2)
item->SetMarked(true);
else
fOtherInterface->SetMarked(true);
return;
}
fInterfaceName = name;
item = menu->FindItem(fInterfaceName.String());
if(item && menu->IndexOf(item) <= menu->CountItems() - 2) {
item->SetMarked(true);
return;
}
BString label("Other: ");
label << name;
fOtherInterface->SetLabel(label.String());
fOtherInterface->SetMarked(true);
// XXX: this is needed to tell the owning menu to update its label
} break;
case MSG_SHOW_SERVICE_WINDOW:
fServiceWindow->MoveTo(center_on_screen(fServiceWindow->Bounds(),
Window()));
fServiceWindow->Show();
break;
@ -363,3 +422,51 @@ PPPoEView::MessageReceived(BMessage *message)
BView::MessageReceived(message);
}
}
void
PPPoEView::ReloadInterfaces()
{
// delete all items and request a new bunch from the pppoe kernel module
BMenu *menu = fInterface->Menu();
while(menu->CountItems() > 2)
delete menu->RemoveItem((int32) 0);
fOtherInterface->SetLabel("Other:");
PPPManager manager;
char *interfaces = new char[8192];
// reserve enough space for approximately 512 entries
int32 count = manager.ControlModule("pppoe", PPPoE_GET_INTERFACES, interfaces,
8192);
BMenuItem *item;
char *name = interfaces;
int32 insertAt;
for(int32 index = 0; index < count; index++) {
item = new BMenuItem(name, new BMessage(MSG_SELECT_INTERFACE));
insertAt = FindNextMenuInsertionIndex(menu, name);
if(insertAt > menu->CountItems() - 2)
insertAt = menu->CountItems() - 2;
item->SetTarget(this);
menu->AddItem(item, insertAt);
name += strlen(name) + 1;
}
delete interfaces;
if(!Addon()->InterfaceName())
fInterfaceName = "";
else
fInterfaceName = Addon()->InterfaceName();
item = menu->FindItem(fInterfaceName.String());
if(item && menu->IndexOf(item) <= menu->CountItems() - 2)
item->SetMarked(true);
else if(Addon()->InterfaceName()) {
BString label("Other: ");
label << fInterfaceName;
fOtherInterface->SetLabel(label.String());
fOtherInterface->SetMarked(true);
}
}

View File

@ -45,7 +45,7 @@ class PPPoEAddon : public DialUpAddon {
virtual bool LoadSettings(BMessage *settings, BMessage *profile, bool isNew);
virtual void IsModified(bool& settings, bool& profile) const;
virtual void IsModified(bool *settings, bool *profile) const;
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary);
@ -76,7 +76,7 @@ class PPPoEView : public BView {
void Reload();
const char *InterfaceName() const
{ return fInterfaceName->Text(); }
{ return fInterfaceName.String(); }
const char *ACName() const
{ return fACName->Text(); }
const char *ServiceName() const
@ -85,12 +85,19 @@ class PPPoEView : public BView {
virtual void AttachedToWindow();
virtual void MessageReceived(BMessage *message);
private:
void ReloadInterfaces();
private:
PPPoEAddon *fAddon;
BButton *fServiceButton, *fCancelButton, *fOKButton;
BTextControl *fInterfaceName, *fACName, *fServiceName;
BMenuField *fInterface;
BMenuItem *fOtherInterface;
BString fInterfaceName;
BTextControl *fACName, *fServiceName;
BWindow *fServiceWindow;
BString fPreviousACName, fPreviousServiceName;
// for the case that the user presses "Cancel" in the service window
};

View File

@ -25,6 +25,7 @@
#define MSG_ADD_PROTOCOL 'ADDP'
#define MSG_FINISH_ADD_PROTOCOL 'FADD'
#define MSG_REMOVE_PROTOCOL 'REMP'
#define MSG_SHOW_PREFERENCES 'SHOW'
#define MSG_UPDATE_BUTTONS 'UBTN'
@ -65,7 +66,7 @@ ProtocolsAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
// ask protocols to load their settings
BMessage parameter;
for(int32 index = 0; FindMessageParameter(PPP_PROTOCOL_KEY, *fProfile, parameter,
for(int32 index = 0; FindMessageParameter(PPP_PROTOCOL_KEY, *fProfile, &parameter,
&index); index++)
if(!LoadProtocolSettings(parameter))
return false;
@ -120,15 +121,15 @@ ProtocolsAddon::HasTemporaryProfile() const
void
ProtocolsAddon::IsModified(bool& settings, bool& profile) const
ProtocolsAddon::IsModified(bool *settings, bool *profile) const
{
settings = profile = false;
*settings = *profile = false;
if(!fSettings || !fProtocolsView)
return;
if(CountProtocols() != fProtocolsView->CountProtocols()) {
settings = profile = true;
*settings = *profile = true;
return;
}
@ -139,15 +140,15 @@ ProtocolsAddon::IsModified(bool& settings, bool& profile) const
reinterpret_cast<void**>(&protocol)) == B_OK; index++) {
if(!protocol->KernelModuleName() // this is actually an error
|| !fProtocolsView->HasProtocol(protocol->KernelModuleName())) {
settings = profile = true;
*settings = *profile = true;
return;
}
protocol->IsModified(protocolSettingsChanged, protocolProfileChanged);
protocol->IsModified(&protocolSettingsChanged, &protocolProfileChanged);
if(protocolSettingsChanged)
settings = true;
*settings = true;
if(protocolProfileChanged)
profile = true;
*profile = true;
}
}
@ -265,7 +266,8 @@ ProtocolsView::ProtocolsView(ProtocolsAddon *addon, BRect frame)
AddChild(fPreferencesButton);
fProtocolsMenu = new BPopUpMenu("UnregisteredProtocols", false, false);
AddAddonsToMenu(Addon()->Addons(), fProtocolsMenu, DUN_PROTOCOL_ADDON_TYPE, 0);
AddAddonsToMenu(Addon()->Addons(), fProtocolsMenu, DUN_PROTOCOL_ADDON_TYPE,
MSG_FINISH_ADD_PROTOCOL);
}
@ -307,6 +309,7 @@ ProtocolsView::Reload()
void
ProtocolsView::AttachedToWindow()
{
fProtocolsMenu->SetTargetForItems(this);
SetViewColor(Parent()->ViewColor());
fListView->SetTarget(this);
fAddButton->SetTarget(this);
@ -335,10 +338,15 @@ ProtocolsView::MessageReceived(BMessage *message)
{
switch(message->what) {
case MSG_ADD_PROTOCOL: {
BMenuItem *selected = fProtocolsMenu->Go(fAddButton->ConvertToScreen(
fAddButton->Bounds().RightTop()), false, true);
int32 index = RegisterProtocol(fProtocolsMenu->IndexOf(selected));
fProtocolsMenu->Go(fAddButton->ConvertToScreen(
fAddButton->Bounds().RightTop()), true, true, true);
} break;
case MSG_FINISH_ADD_PROTOCOL: {
int32 index;
message->FindInt32("index", &index);
index = RegisterProtocol(index);
// this returns the new index of the item (now for the list view)
UpdateButtons();
if(index > 0)
@ -358,7 +366,10 @@ ProtocolsView::MessageReceived(BMessage *message)
if(selected) {
DialUpAddon *addon = selected->Addon();
addon->CreateView(ConvertToScreen(Bounds().LeftTop()));
float width, height;
addon->GetPreferredSize(&width, &height);
BRect rect(0, 0, width, height);
addon->CreateView(center_on_screen(rect, Window()));
// show the preferences window
}
} break;
@ -448,11 +459,10 @@ ProtocolsView::UnregisterProtocol(int32 index)
return;
const char *label = remove->Text();
BMessage *message = new BMessage(MSG_ADD_PROTOCOL);
// the 'what' field is merely set to get around the compiler warning
BMessage *message = new BMessage(MSG_FINISH_ADD_PROTOCOL);
message->AddPointer("Addon", remove->Addon());
BMenuItem *item = new BMenuItem(label, message);
item->SetTarget(this);
index = FindNextMenuInsertionIndex(fProtocolsMenu, label);
fProtocolsMenu->AddItem(item, index);
delete remove;

View File

@ -41,7 +41,7 @@ class ProtocolsAddon : public DialUpAddon {
bool LoadProtocolSettings(const BMessage& parameter);
virtual bool HasTemporaryProfile() const;
virtual void IsModified(bool& settings, bool& profile) const;
virtual void IsModified(bool *settings, bool *profile) const;
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary);

View File

@ -1,12 +1,8 @@
Short-term TODOs:
- see if we can reuse some code from the original DUN preflet
- add "Extras" tab for changing dial-behaviour (auto-redial, dial-on-demand, etc.)
- add "Revert Changes" button
- load add-ons
- move DEVNOTES into a doxygen file and document the rest of the API
- use dynamic window positioning based on screen size instead of static coordinates
- really delete interface description files when removing an interface
- open dialog asking for interface name when creating a new interface
- IPCP: check for incorrect settings (only IP addresses should be entered)
Long-term TODOs:

View File

@ -0,0 +1,105 @@
//-----------------------------------------------------------------------
// This software is part of the OpenBeOS distribution and is covered
// by the OpenBeOS license.
//
// Copyright (c) 2004 Waldemar Kornewald, Waldemar.Kornewald@web.de
//-----------------------------------------------------------------------
#include "TextRequestDialog.h"
#include "InterfaceUtils.h"
#include <Button.h>
#include <TextControl.h>
#define WINDOW_WIDTH 250
#define WINDOW_HEIGHT 5 + 20 + 10 + 25 + 5
#define WINDOW_RECT BRect(0, 0, WINDOW_WIDTH, WINDOW_HEIGHT)
#define BUTTON_WIDTH 80
const int32 kMsgButton = 'MBTN';
TextRequestDialog::TextRequestDialog(const char *title, const char *request,
const char *text = NULL)
: BWindow(WINDOW_RECT, title, B_MODAL_WINDOW, B_NOT_RESIZABLE | B_NOT_CLOSABLE, 0),
fInvoker(NULL)
{
BRect rect = Bounds();
BView *backgroundView = new BView(rect, "background", B_FOLLOW_ALL_SIDES, 0);
backgroundView->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR));
rect.InsetBy(5, 5);
rect.bottom = rect.top + 20;
fTextControl = new BTextControl(rect, "request", request, text, NULL);
fTextControl->SetDivider(fTextControl->StringWidth(fTextControl->Label()) + 5);
if(text && strlen(text) > 0)
fTextControl->TextView()->SelectAll();
rect.top = rect.bottom + 10;
rect.bottom = rect.top + 25;
rect.left = rect.right - BUTTON_WIDTH;
BMessage message(kMsgButton);
message.AddInt32("which", 1);
BButton *okButton = new BButton(rect, "okButton", "OK", new BMessage(message));
rect.right = rect.left - 10;
rect.left = rect.right - BUTTON_WIDTH;
message.ReplaceInt32("which", 0);
BButton *cancelButton = new BButton(rect, "cancelButton", "Cancel",
new BMessage(message));
backgroundView->AddChild(okButton);
backgroundView->AddChild(cancelButton);
backgroundView->AddChild(fTextControl);
AddChild(backgroundView);
fTextControl->MakeFocus(true);
SetDefaultButton(okButton);
}
TextRequestDialog::~TextRequestDialog()
{
delete fInvoker;
}
void
TextRequestDialog::MessageReceived(BMessage *message)
{
switch(message->what) {
case kMsgButton: {
if(!fInvoker || !fInvoker->Message())
return;
int32 which;
message->FindInt32("which", &which);
BMessage toSend(*fInvoker->Message());
toSend.AddInt32("which", which);
if(which == 1)
toSend.AddString("text", fTextControl->Text());
fInvoker->Invoke(&toSend);
PostMessage(B_QUIT_REQUESTED);
} break;
default:
BWindow::MessageReceived(message);
}
}
bool
TextRequestDialog::QuitRequested()
{
return true;
}
status_t
TextRequestDialog::Go(BInvoker *invoker)
{
fInvoker = invoker;
MoveTo(center_on_screen(Bounds()));
Show();
return B_OK;
}

View File

@ -0,0 +1,31 @@
//-----------------------------------------------------------------------
// This software is part of the OpenBeOS distribution and is covered
// by the OpenBeOS license.
//
// Copyright (c) 2004 Waldemar Kornewald, Waldemar.Kornewald@web.de
//-----------------------------------------------------------------------
#ifndef _TEXT_REQUEST_DIALOG__H
#define _TEXT_REQUEST_DIALOG__H
#include <Window.h>
class TextRequestDialog : public BWindow {
public:
TextRequestDialog(const char *title, const char *request,
const char *text = NULL);
virtual ~TextRequestDialog();
virtual void MessageReceived(BMessage *message);
virtual bool QuitRequested();
status_t Go(BInvoker *invoker);
private:
BTextControl *fTextControl;
BInvoker *fInvoker;
};
#endif