#include "ExpanderSettings.h"
#include <ByteOrder.h>
#include <Directory.h>
#include <Screen.h>
#include <FindDirectory.h>
#include <Entry.h>
#include <stdlib.h>
#include <string.h>
#include <Path.h>
template<typename T> bool
read_data(BFile& file, T& value)
{
return file.Read(&value, sizeof(T)) == (ssize_t)sizeof(T);
}
ExpanderSettings::ExpanderSettings()
:
fMessage(kMsgExpanderSettings),
fUpdated(false)
{
fMessage.AddBool("automatically_expand_files", false);
fMessage.AddBool("close_when_done", true);
fMessage.AddInt8("destination_folder", 0x63);
entry_ref ref;
fMessage.AddRef("destination_folder_use", &ref);
fMessage.AddBool("open_destination_folder", true);
fMessage.AddBool("show_contents_listing", false);
fMessage.AddPoint("window_position", BPoint(50, 50));
BFile file;
if (Open(&file, B_READ_ONLY) != B_OK)
return;
bool unknown;
bool automaticallyExpandFiles;
bool closeWhenDone;
int8 destinationFolder;
bool openDestinationFolder;
bool showContentsListing;
BPoint position;
char name[B_FILE_NAME_LENGTH] = {'\0'};
int32 nameSize;
if (read_data(file, unknown)
&& read_data(file, automaticallyExpandFiles)
&& read_data(file, closeWhenDone)
&& read_data(file, destinationFolder)
&& read_data(file, unknown)
&& read_data(file, ref.device)
&& read_data(file, ref.directory)
&& read_data(file, nameSize)
&& (nameSize <= 0 || file.Read(name, nameSize) == nameSize)
&& read_data(file, openDestinationFolder)
&& read_data(file, showContentsListing)
&& read_data(file, position)) {
if (nameSize > 0 && nameSize < B_FILE_NAME_LENGTH) {
name[nameSize] = '\0';
ref.set_name(name);
}
BScreen screen;
if (screen.Frame().Contains(position))
fMessage.ReplacePoint("window_position", position);
fMessage.ReplaceBool("automatically_expand_files",
automaticallyExpandFiles);
fMessage.ReplaceBool("close_when_done", closeWhenDone);
if (destinationFolder == 0x66
|| destinationFolder == 0x63
|| destinationFolder == 0x65) {
fMessage.ReplaceInt8("destination_folder", destinationFolder);
}
BEntry entry(&ref);
if (entry.Exists())
fMessage.ReplaceRef("destination_folder_use", &ref);
fMessage.ReplaceBool("open_destination_folder", openDestinationFolder);
fMessage.ReplaceBool("show_contents_listing", showContentsListing);
}
}
ExpanderSettings::~ExpanderSettings()
{
if (!fUpdated)
return;
BFile file;
if (Open(&file, B_CREATE_FILE | B_WRITE_ONLY) != B_OK)
return;
bool automaticallyExpandFiles;
bool closeWhenDone;
int8 destinationFolder;
entry_ref ref;
bool openDestinationFolder;
bool showContentsListing;
BPoint position;
bool unknown = 1;
if (fMessage.FindPoint("window_position", &position) == B_OK
&& fMessage.FindBool("automatically_expand_files",
&automaticallyExpandFiles) == B_OK
&& fMessage.FindBool("close_when_done", &closeWhenDone) == B_OK
&& fMessage.FindInt8("destination_folder", &destinationFolder) == B_OK
&& fMessage.FindRef("destination_folder_use", &ref) == B_OK
&& fMessage.FindBool("open_destination_folder",
&openDestinationFolder) == B_OK
&& fMessage.FindBool("show_contents_listing",
&showContentsListing) == B_OK) {
file.Write(&unknown, sizeof(unknown));
file.Write(&automaticallyExpandFiles, sizeof(automaticallyExpandFiles));
file.Write(&closeWhenDone, sizeof(closeWhenDone));
file.Write(&destinationFolder, sizeof(destinationFolder));
unknown = 0;
file.Write(&unknown, sizeof(unknown));
file.Write(&ref.device, sizeof(ref.device));
file.Write(&ref.directory, sizeof(ref.directory));
int32 nameSize = 0;
if (ref.name)
nameSize = strlen(ref.name);
file.Write(&nameSize, sizeof(nameSize));
file.Write(ref.name, nameSize);
file.Write(&openDestinationFolder, sizeof(openDestinationFolder));
file.Write(&showContentsListing, sizeof(showContentsListing));
file.Write(&position, sizeof(position));
}
}
status_t
ExpanderSettings::GetSettingsDirectoryPath(BPath& _path)
{
status_t error = find_directory(B_USER_SETTINGS_DIRECTORY, &_path);
return error == B_OK ? _path.Append("expander") : error;
}
status_t
ExpanderSettings::Open(BFile* file, int32 mode)
{
BPath path;
status_t error = GetSettingsDirectoryPath(path);
if (error != B_OK)
return error;
if ((mode & B_CREATE_FILE) != 0) {
error = create_directory(path.Path(), 0755);
if (error != B_OK)
return error;
}
error = path.Append("settings");
if (error != B_OK)
return error;
return file->SetTo(path.Path(), mode);
}
void
ExpanderSettings::UpdateFrom(BMessage* message)
{
bool automaticallyExpandFiles;
bool closeWhenDone;
int8 destinationFolder;
entry_ref ref;
bool openDestinationFolder;
bool showContentsListing;
BPoint position;
if (message->FindPoint("window_position", &position) == B_OK)
fMessage.ReplacePoint("window_position", position);
if (message->FindBool("automatically_expand_files",
&automaticallyExpandFiles) == B_OK) {
fMessage.ReplaceBool("automatically_expand_files",
automaticallyExpandFiles);
}
if (message->FindBool("close_when_done", &closeWhenDone) == B_OK)
fMessage.ReplaceBool("close_when_done", closeWhenDone);
if (message->FindInt8("destination_folder", &destinationFolder) == B_OK)
fMessage.ReplaceInt8("destination_folder", destinationFolder);
if (message->FindRef("destination_folder_use", &ref) == B_OK)
fMessage.ReplaceRef("destination_folder_use", &ref);
if (message->FindBool("open_destination_folder",
&openDestinationFolder) == B_OK)
fMessage.ReplaceBool("open_destination_folder", openDestinationFolder);
if (message->FindBool("show_contents_listing",
&showContentsListing) == B_OK) {
fMessage.ReplaceBool("show_contents_listing", showContentsListing);
}
fUpdated = true;
}