void FileTypeWindow::_AdoptType(BMessage* message) { entry_ref ref; if (message == NULL || message->FindRef("refs", &ref) != B_OK) return; BNode node(&ref); status_t status = node.InitCheck(); char type[B_MIME_TYPE_LENGTH]; if (status == B_OK) { // get type from file BNodeInfo nodeInfo(&node); status = nodeInfo.InitCheck(); if (status == B_OK) { if (nodeInfo.GetType(type) != B_OK) type[0] = '\0'; } } if (status != B_OK) { error_alert(B_TRANSLATE("Could not open file"), status); return; } fCommonType = type; fTypeControl->SetText(type); _AdoptType(); }
void FileTypesWindow::_AdoptPreferredApplication(BMessage* message, bool sameAs) { if (fCurrentType.Type() == NULL) return; BString preferred; if (retrieve_preferred_app(message, sameAs, fCurrentType.Type(), preferred) != B_OK) return; status_t status = fCurrentType.SetPreferredApp(preferred.String()); if (status != B_OK) error_alert("Could not set preferred application", status); }
void ExtensionWindow::MessageReceived(BMessage* message) { switch (message->what) { case kMsgExtensionUpdated: { bool enabled = fExtensionControl->Text() != NULL && fExtensionControl->Text()[0] != '\0'; if (enabled) { // There is some text, but we only accept it, if it // changed the previous extension enabled = strcmp(fExtensionControl->Text(), fExtension.String()); } if (fAcceptButton->IsEnabled() != enabled) fAcceptButton->SetEnabled(enabled); break; } case kMsgAccept: { const char* newExtension = fExtensionControl->Text(); // omit the leading dot if (newExtension[0] == '.') newExtension++; status_t status = replace_extension(fMimeType, newExtension, fExtension.String()); if (status != B_OK) error_alert("Could not change file extensions", status); PostMessage(B_QUIT_REQUESTED); break; } default: BWindow::MessageReceived(message); break; } }
void ApplicationTypesWindow::_RemoveUninstalled() { // Note: this runs in the looper's thread, which isn't that nice int32 removed = 0; volatile bool quit = false; BWindow* progressWindow = new ProgressWindow( B_TRANSLATE("Removing uninstalled application types"), fTypeListView->FullListCountItems(), &quit); progressWindow->AddToSubset(this); progressWindow->Show(); for (int32 i = fTypeListView->FullListCountItems(); i-- > 0 && !quit;) { MimeTypeItem* item = dynamic_cast<MimeTypeItem*> (fTypeListView->FullListItemAt(i)); progressWindow->PostMessage(B_UPDATE_STATUS_BAR); if (item == NULL) continue; // search for application on all volumes bool found = false; BVolumeRoster volumeRoster; BVolume volume; while (volumeRoster.GetNextVolume(&volume) == B_OK) { if (!volume.KnowsQuery()) continue; BQuery query; query.PushAttr("BEOS:APP_SIG"); query.PushString(item->Type()); query.PushOp(B_EQ); query.SetVolume(&volume); query.Fetch(); entry_ref ref; if (query.GetNextRef(&ref) == B_OK) { found = true; break; } } if (!found) { BMimeType mimeType(item->Type()); mimeType.Delete(); removed++; // We're blocking the message loop that received the MIME changes, // so we dequeue all waiting messages from time to time if (removed % 10 == 0) UpdateIfNeeded(); } } progressWindow->PostMessage(B_QUIT_REQUESTED); static BMessageFormat format(B_TRANSLATE("{0, plural, " "one{# Application type could be removed} " "other{# Application types could be removed}}")); BString message; format.Format(message, removed); error_alert(message, B_OK, B_INFO_ALERT); }
void FileTypesWindow::MessageReceived(BMessage* message) { switch (message->what) { case B_SIMPLE_DATA: type_code type; if (message->GetInfo("refs", &type) == B_OK && type == B_REF_TYPE) { be_app->PostMessage(message); } break; case kMsgToggleIcons: { BMenuItem* item; if (message->FindPointer("source", (void **)&item) != B_OK) break; item->SetMarked(!fTypeListView->IsShowingIcons()); fTypeListView->ShowIcons(item->IsMarked()); // update settings BMessage update(kMsgSettingsChanged); update.AddBool("show_icons", item->IsMarked()); be_app_messenger.SendMessage(&update); break; } case kMsgToggleRule: { BMenuItem* item; if (message->FindPointer("source", (void **)&item) != B_OK) break; item->SetMarked(fRuleControl->IsHidden()); _ShowSnifferRule(item->IsMarked()); // update settings BMessage update(kMsgSettingsChanged); update.AddBool("show_rule", item->IsMarked()); be_app_messenger.SendMessage(&update); break; } case kMsgTypeSelected: { int32 index; if (message->FindInt32("index", &index) == B_OK) { MimeTypeItem* item = (MimeTypeItem*)fTypeListView->ItemAt(index); if (item != NULL) { BMimeType type(item->Type()); _SetType(&type); } else _SetType(NULL); } break; } case kMsgAddType: { if (fNewTypeWindow == NULL) { fNewTypeWindow = new NewFileTypeWindow(this, fCurrentType.Type()); fNewTypeWindow->Show(); } else fNewTypeWindow->Activate(); break; } case kMsgNewTypeWindowClosed: fNewTypeWindow = NULL; break; case kMsgRemoveType: { if (fCurrentType.Type() == NULL) break; BAlert* alert; if (fCurrentType.IsSupertypeOnly()) { alert = new BPrivate::OverrideAlert("FileTypes Request", "Removing a super type cannot be reverted.\n" "All file types that belong to this super type " "will be lost!\n\n" "Are you sure you want to do this? To remove the whole " "group, hold down the Shift key and press \"Remove\".", "Remove", B_SHIFT_KEY, "Cancel", 0, NULL, 0, B_WIDTH_AS_USUAL, B_STOP_ALERT); } else { alert = new BAlert("FileTypes Request", "Removing a file type cannot be reverted.\n" "Are you sure you want to remove it?", "Remove", "Cancel", NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT); } if (alert->Go()) break; status_t status = fCurrentType.Delete(); if (status != B_OK) fprintf(stderr, "Could not remove file type: %s\n", strerror(status)); break; } case kMsgSelectNewType: { const char* type; if (message->FindString("type", &type) == B_OK) fTypeListView->SelectNewType(type); break; } // File Recognition group case kMsgExtensionSelected: { int32 index; if (message->FindInt32("index", &index) == B_OK) { BStringItem* item = (BStringItem*)fExtensionListView->ItemAt(index); fRemoveExtensionButton->SetEnabled(item != NULL); } break; } case kMsgExtensionInvoked: { if (fCurrentType.Type() == NULL) break; int32 index; if (message->FindInt32("index", &index) == B_OK) { BStringItem* item = (BStringItem*)fExtensionListView->ItemAt(index); if (item == NULL) break; BWindow* window = new ExtensionWindow(this, fCurrentType, item->Text()); window->Show(); } break; } case kMsgAddExtension: { if (fCurrentType.Type() == NULL) break; BWindow* window = new ExtensionWindow(this, fCurrentType, NULL); window->Show(); break; } case kMsgRemoveExtension: { int32 index = fExtensionListView->CurrentSelection(); if (index < 0 || fCurrentType.Type() == NULL) break; BMessage extensions; if (fCurrentType.GetFileExtensions(&extensions) == B_OK) { extensions.RemoveData("extensions", index); fCurrentType.SetFileExtensions(&extensions); } break; } case kMsgRuleEntered: { // check rule BString parseError; if (BMimeType::CheckSnifferRule(fRuleControl->Text(), &parseError) != B_OK) { parseError.Prepend("Recognition rule is not valid:\n\n"); error_alert(parseError.String()); } else fCurrentType.SetSnifferRule(fRuleControl->Text()); break; } // Description group case kMsgTypeEntered: { fCurrentType.SetShortDescription(fTypeNameControl->Text()); break; } case kMsgDescriptionEntered: { fCurrentType.SetLongDescription(fDescriptionControl->Text()); break; } // Preferred Application group case kMsgPreferredAppChosen: { const char* signature; if (message->FindString("signature", &signature) != B_OK) signature = NULL; fCurrentType.SetPreferredApp(signature); break; } case kMsgSelectPreferredApp: { BMessage panel(kMsgOpenFilePanel); panel.AddString("title", "Select preferred application"); panel.AddInt32("message", kMsgPreferredAppOpened); panel.AddMessenger("target", this); be_app_messenger.SendMessage(&panel); break; } case kMsgPreferredAppOpened: _AdoptPreferredApplication(message, false); break; case kMsgSamePreferredAppAs: { BMessage panel(kMsgOpenFilePanel); panel.AddString("title", "Select same preferred application as"); panel.AddInt32("message", kMsgSamePreferredAppAsOpened); panel.AddMessenger("target", this); be_app_messenger.SendMessage(&panel); break; } case kMsgSamePreferredAppAsOpened: _AdoptPreferredApplication(message, true); break; // Extra Attributes group case kMsgAttributeSelected: { int32 index; if (message->FindInt32("index", &index) == B_OK) { AttributeItem* item = (AttributeItem*)fAttributeListView->ItemAt(index); fRemoveAttributeButton->SetEnabled(item != NULL); } break; } case kMsgAttributeInvoked: { if (fCurrentType.Type() == NULL) break; int32 index; if (message->FindInt32("index", &index) == B_OK) { AttributeItem* item = (AttributeItem*)fAttributeListView->ItemAt(index); if (item == NULL) break; BWindow* window = new AttributeWindow(this, fCurrentType, item); window->Show(); } break; } case kMsgAddAttribute: { if (fCurrentType.Type() == NULL) break; BWindow* window = new AttributeWindow(this, fCurrentType, NULL); window->Show(); break; } case kMsgRemoveAttribute: { int32 index = fAttributeListView->CurrentSelection(); if (index < 0 || fCurrentType.Type() == NULL) break; BMessage attributes; if (fCurrentType.GetAttrInfo(&attributes) == B_OK) { const char* kAttributeNames[] = { "attr:public_name", "attr:name", "attr:type", "attr:editable", "attr:viewable", "attr:extra", "attr:alignment", "attr:width", "attr:display_as" }; for (uint32 i = 0; i < sizeof(kAttributeNames) / sizeof(kAttributeNames[0]); i++) { attributes.RemoveData(kAttributeNames[i], index); } fCurrentType.SetAttrInfo(&attributes); } break; } case B_META_MIME_CHANGED: { const char* type; int32 which; if (message->FindString("be:type", &type) != B_OK || message->FindInt32("be:which", &which) != B_OK) break; if (fCurrentType.Type() == NULL) break; if (!strcasecmp(fCurrentType.Type(), type)) { if (which != B_MIME_TYPE_DELETED) _SetType(&fCurrentType, which); else _SetType(NULL); } else { // this change could still affect our current type if (which == B_MIME_TYPE_DELETED #ifdef __ANTARES__ || which == B_SUPPORTED_TYPES_CHANGED #endif || which == B_PREFERRED_APP_CHANGED) _UpdatePreferredApps(&fCurrentType); } break; } default: BWindow::MessageReceived(message); } }
void AttributeWindow::MessageReceived(BMessage* message) { switch (message->what) { case kMsgAttributeUpdated: case kMsgAlignmentChosen: case kMsgTypeChosen: _CheckDisplayAs(); _CheckAcceptable(); break; case kMsgDisplayAsChosen: fSpecialControl->SetEnabled(!_DefaultDisplayAs()->IsMarked()); _CheckAcceptable(); break; case kMsgVisibilityChanged: { bool enabled = fVisibleCheckBox->Value() != B_CONTROL_OFF; fDisplayAsMenuField->SetEnabled(enabled); fWidthControl->SetEnabled(enabled); fAlignmentMenuField->SetEnabled(enabled); fEditableCheckBox->SetEnabled(enabled); _CheckDisplayAs(); _CheckAcceptable(); break; } case kMsgAccept: { BMessage attributes; status_t status = fMimeType.GetAttrInfo(&attributes); if (status == B_OK) { // replace the entry, and remove any equivalent entries BList list; const char* newAttribute = fAttributeControl->Text(); list.AddItem(_NewItemFromCurrent()); const char* attribute; for (int32 i = 0; attributes.FindString("attr:name", i, &attribute) == B_OK; i++) { if (!strcmp(fAttribute.Name(), attribute) || !strcmp(newAttribute, attribute)) { // remove this item continue; } AttributeItem* item = create_attribute_item(attributes, i); if (item != NULL) list.AddItem(item); } list.SortItems(compare_attributes); // Copy them to a new message (their memory is still part of the // original BMessage) BMessage newAttributes; for (int32 i = 0; i < list.CountItems(); i++) { AttributeItem* item = (AttributeItem*)list.ItemAt(i); newAttributes.AddString("attr:name", item->Name()); newAttributes.AddString("attr:public_name", item->PublicName()); newAttributes.AddInt32("attr:type", (int32)item->Type()); newAttributes.AddString("attr:display_as", item->DisplayAs()); newAttributes.AddInt32("attr:alignment", item->Alignment()); newAttributes.AddInt32("attr:width", item->Width()); newAttributes.AddBool("attr:viewable", item->Visible()); newAttributes.AddBool("attr:editable", item->Editable()); delete item; } status = fMimeType.SetAttrInfo(&newAttributes); } if (status != B_OK) error_alert("Could not change attributes", status); PostMessage(B_QUIT_REQUESTED); break; } default: BWindow::MessageReceived(message); break; } }
status_t retrieve_preferred_app(BMessage* message, bool sameAs, const char* forType, BString& preferredApp) { entry_ref ref; if (message == NULL || message->FindRef("refs", &ref) != B_OK) return B_BAD_VALUE; BFile file(&ref, B_READ_ONLY); status_t status = file.InitCheck(); char preferred[B_MIME_TYPE_LENGTH]; if (status == B_OK) { if (sameAs) { // get preferred app from file BNodeInfo nodeInfo(&file); status = nodeInfo.InitCheck(); if (status == B_OK) { if (nodeInfo.GetPreferredApp(preferred) != B_OK) preferred[0] = '\0'; if (!preferred[0]) { // get MIME type from file char type[B_MIME_TYPE_LENGTH]; if (nodeInfo.GetType(type) == B_OK) { BMimeType mimeType(type); mimeType.GetPreferredApp(preferred); } } } } else { // get application signature BAppFileInfo appInfo(&file); status = appInfo.InitCheck(); if (status == B_OK && appInfo.GetSignature(preferred) != B_OK) preferred[0] = '\0'; } } if (status != B_OK) { error_alert(B_TRANSLATE("File could not be opened"), status, B_STOP_ALERT); return status; } if (!preferred[0]) { error_alert(sameAs ? B_TRANSLATE("Could not retrieve preferred application of this " "file") : B_TRANSLATE("Could not retrieve application signature")); return B_ERROR; } // Check if the application chosen supports this type BMimeType mimeType(forType); bool found = false; BMessage applications; if (mimeType.GetSupportingApps(&applications) == B_OK && is_application_in_message(applications, preferred)) found = true; applications.MakeEmpty(); if (!found && mimeType.GetWildcardApps(&applications) == B_OK && is_application_in_message(applications, preferred)) found = true; if (!found) { // warn user BMimeType appType(preferred); char description[B_MIME_TYPE_LENGTH]; if (appType.GetShortDescription(description) != B_OK) description[0] = '\0'; char warning[512]; snprintf(warning, sizeof(warning), B_TRANSLATE("The application " "\"%s\" does not support this file type.\n" "Are you sure you want to set it anyway?"), description[0] ? description : preferred); BAlert* alert = new BAlert(B_TRANSLATE("FileTypes request"), warning, B_TRANSLATE("Set Preferred Application"), B_TRANSLATE("Cancel"), NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT); if (alert->Go() == 1) return B_ERROR; } preferredApp = preferred; return B_OK; }