├── .gitignore ├── .hgignore ├── Configurations ├── Mac │ ├── Application.xcconfig │ ├── Base.xcconfig │ └── Framework.xcconfig ├── Shared │ ├── Project.base.xcconfig │ ├── Project.debug.xcconfig │ └── Project.release.xcconfig └── iOS │ ├── Base.xcconfig │ └── Library.xcconfig ├── Example ├── AppDelegate.h ├── AppDelegate.m ├── Example.pch ├── Example.plist ├── Example.xcodeproj │ ├── project.pbxproj │ ├── project.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcshareddata │ │ │ └── WorkspaceSettings.xcsettings │ └── xcshareddata │ │ └── xcschemes │ │ └── GreenwichExample.xcscheme ├── MainMenu.xib ├── de.lproj │ ├── Localizable.strings │ └── MainMenu.strings ├── en.lproj │ ├── Localizable.strings │ └── MainMenu.strings └── main.m ├── Framework ├── External │ ├── Availability │ │ └── RedAvailability.h │ ├── FRBundleAdditions.h │ ├── FRBundleAdditions.m │ ├── FRExtraHelpController.h │ ├── FRExtraHelpController.m │ ├── FRFileManagerArchivingAdditions.h │ ├── FRFileManagerArchivingAdditions.m │ ├── FRRuntimeAdditions.h │ ├── FRRuntimeAdditions.m │ ├── archiving.c │ ├── archiving.h │ └── libarchive │ │ ├── archive.h │ │ ├── archive_entry.h │ │ ├── libarchive.dylib │ │ └── libarchive.license ├── Greenwich.xcodeproj │ ├── project.pbxproj │ └── project.xcworkspace │ │ └── contents.xcworkspacedata ├── Info │ ├── Localization.plist │ └── Translator.plist ├── PackageReadme.md ├── Proofer │ ├── AppDelegate.h │ ├── AppDelegate.m │ ├── FRProofer.h │ ├── FRProofer.m │ ├── FRSingleNodeParsingDelegate.h │ ├── FRSingleNodeParsingDelegate.m │ ├── FRTranslateArrayResultParsingDelegate.h │ ├── FRTranslateArrayResultParsingDelegate.m │ ├── FRTranslator.h │ ├── FRTranslator.m │ ├── Proofer-Info.plist │ ├── Readme.md │ ├── en.lproj │ │ └── MainMenu.xib │ └── main.m ├── Resources │ ├── Mac │ │ ├── Localization.xib │ │ ├── Translator │ │ │ ├── MainMenu.xib │ │ │ └── en.lproj │ │ │ │ ├── Localizable.strings │ │ │ │ └── MainMenu.strings │ │ ├── de.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ │ ├── en.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ │ ├── es.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ │ ├── fr.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ │ ├── it.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ │ ├── ja.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ │ ├── nl.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ │ ├── no.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ │ └── pt.lproj │ │ │ ├── Localizable.strings │ │ │ └── Localization.strings │ └── iOS │ │ └── en.lproj │ │ └── Localizable.strings ├── Scripts │ ├── actions │ │ ├── addlang │ │ ├── create │ │ ├── migrate │ │ └── verify │ ├── lib │ │ └── scriptlib │ │ │ ├── __init__.py │ │ │ ├── config │ │ │ └── __init__.py │ │ │ └── i18n │ │ │ ├── __init__.py │ │ │ ├── document.py │ │ │ ├── strings.py │ │ │ └── util.py │ └── localization └── Source │ ├── Greenwich.pch │ ├── Mac │ ├── FRLocalizationManager.h │ ├── FRLocalizationManager.m │ ├── FRLocalizationWindowController.h │ ├── FRLocalizationWindowController.m │ ├── FRNibAutomaticLocalization.h │ ├── FRNibAutomaticLocalization.m │ ├── FRTranslationContainer.m │ ├── FRTranslationContainer__.h │ ├── FRTranslationInfo.m │ ├── FRTranslationInfo__.h │ ├── FRUntranslatedCountCell.h │ ├── FRUntranslatedCountCell.m │ ├── Greenwich.h │ └── Translator │ │ ├── FRNetworkClient.h │ │ ├── FRNetworkClient.m │ │ ├── FRTranslator.h │ │ ├── FRTranslator.m │ │ └── main.m │ ├── Shared │ ├── FRConnection.h │ ├── FRConnection.m │ ├── FRLocalizationBundleAdditions.h │ ├── FRLocalizationBundleAdditions.m │ ├── FRLocalizationBundleAdditions__.h │ ├── FRMessages.h │ ├── FRMessages.m │ ├── FRStrings.h │ └── FRStrings.m │ └── iOS │ ├── FRLocalizationManager.h │ ├── FRLocalizationManager.m │ ├── FRNetworkServer.m │ ├── FRNetworkServer__.h │ ├── FRUIAutomaticLocalization.h │ ├── FRUIAutomaticLocalization.m │ ├── Greenwich.h │ └── Greenwich.pch ├── License ├── Readme.md ├── iOS Example ├── Example.pch ├── Example.plist ├── Example.storyboard ├── Example.xcodeproj │ ├── project.pbxproj │ ├── project.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcshareddata │ │ │ └── WorkspaceSettings.xcsettings │ └── xcshareddata │ │ └── xcschemes │ │ ├── Example.xcscheme │ │ └── Translator.xcscheme ├── ExamplePad.storyboard ├── FRAppDelegate.h ├── FRAppDelegate.m ├── FRMainViewController.h ├── FRMainViewController.m ├── de.lproj │ ├── Example.strings │ ├── ExamplePad.strings │ └── Localizable.strings ├── en.lproj │ ├── Example.strings │ ├── ExamplePad.strings │ └── Localizable.strings └── main.m └── package /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | *.pyc 3 | build 4 | xcuserdata 5 | greenwich.build 6 | greenwich_*.tbz 7 | -------------------------------------------------------------------------------- /.hgignore: -------------------------------------------------------------------------------- 1 | syntax: glob 2 | .DS_Store 3 | *.xcodeproj/*.pbxuser 4 | *.xcodeproj/*.perspective* 5 | *.xcodeproj/*.mode* 6 | *.xcodeproj/**.xcuserdatad 7 | *.pyc 8 | 9 | syntax: regexp 10 | ^build$ 11 | ^greenwich.build$ 12 | ^greenwich_(\d+\.)+(dsym\.)?tbz$ 13 | -------------------------------------------------------------------------------- /Configurations/Mac/Application.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #include "Base.xcconfig" 19 | 20 | -------------------------------------------------------------------------------- /Configurations/Mac/Base.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | // \brief Standard settings 19 | // \details These settings are shared by all configurations. They 20 | // are not dynamic. 21 | // ------------------------------------------------------------------ 22 | 23 | CLANG_ENABLE_OBJC_ARC = YES 24 | LD_RUNPATH_SEARCH_PATHS = @loader_path/../Frameworks 25 | GCC_VERSION = com.apple.compilers.llvm.clang.1_0 26 | MACOSX_DEPLOYMENT_TARGET = 10.6 27 | VALID_ARCHS = x86_64 28 | SDKROOT = $(DEVELOPER_SDK_DIR)/MacOSX10.7.sdk 29 | 30 | GREENWICH_NEEDS_LIBARCHIVE = 1 31 | GREENWICH_OTHER_LDFLAGS = $(inherited) -larchive -LExternal/libarchive 32 | GREENWICH_OTHER_CFLAGS = $(inherited) 33 | 34 | // \brief Custom settings 35 | // \details Settings based on the dynamic configurations. If you 36 | // add a new setting, be sure to add a setting in the 37 | // section that enables them at the bottom of this file. 38 | // ------------------------------------------------------------------ 39 | 40 | 41 | GREENWICH_CONFIG_DEBUG_ARCHS = $(NATIVE_ARCH_ACTUAL) 42 | GREENWICH_CONFIG_RELEASE_ARCHS = $(ARCHS_STANDARD_32_64_BIT) 43 | 44 | 45 | // \brief Enabling customized settings 46 | // \details This section allows the above settings to work. It 47 | // uses the names of the different dynamic defines to 48 | // pull the customized settings that it needs. 49 | // ------------------------------------------------------------------ 50 | 51 | ARCHS = $(GREENWICH_CONFIG_$(GREENWICH_CONFIG)_ARCHS) 52 | -------------------------------------------------------------------------------- /Configurations/Mac/Framework.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #include "Base.xcconfig" 19 | 20 | INSTALL_PATH = @rpath 21 | 22 | LD_RUNPATH_SEARCH_PATHS = @loader_path/Frameworks 23 | -------------------------------------------------------------------------------- /Configurations/Shared/Project.base.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | GCC_ENABLE_OBJC_EXCEPTIONS = YES 19 | GCC_C_LANGUAGE_STANDARD = gnu99 20 | GCC_PRECOMPILE_PREFIX_HEADER = YES 21 | GCC_WARN_SHADOW = YES 22 | GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES 23 | GCC_WARN_ABOUT_RETURN_TYPE = YES 24 | GCC_WARN_MISSING_PARENTHESES = YES 25 | GCC_WARN_ABOUT_MISSING_PROTOTYPES = YES 26 | GCC_WARN_ABOUT_MISSING_NEWLINE = YES 27 | GCC_WARN_SIGN_COMPARE = YES 28 | GCC_WARN_TYPECHECK_CALLS_TO_PRINTF = YES 29 | GCC_WARN_UNUSED_FUNCTION = YES 30 | GCC_WARN_UNUSED_LABEL = YES 31 | GCC_WARN_UNUSED_VALUE = YES 32 | GCC_WARN_UNUSED_VARIABLE = YES 33 | GCC_WARN_UNDECLARED_SELECTOR = YES 34 | GCC_INCREASE_PRECOMPILED_HEADER_SHARING = YES 35 | RUN_CLANG_STATIC_ANALYZER = YES 36 | OTHER_CFLAGS = -fblocks 37 | ALWAYS_SEARCH_USER_PATHS = NO 38 | HEADER_SEARCH_PATHS = $(inherited) "$(SRCROOT)/External/Availability" 39 | COPY_PHASE_STRIP = NO 40 | PREBINDING = NO 41 | BUNDLE_IDENTIFIER = com.fadingred.$(PRODUCT_NAME:rfc1034identifier) 42 | 43 | GREENWICH_LOCALIZATION_SYMBOL = FRLocalizedString 44 | GREENWICH_VERSION = 2.0b2 45 | -------------------------------------------------------------------------------- /Configurations/Shared/Project.debug.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #include "Project.base.xcconfig" 19 | 20 | GREENWICH_CONFIG = DEBUG 21 | 22 | GCC_ENABLE_FIX_AND_CONTINUE = YES 23 | GCC_OPTIMIZATION_LEVEL = 0 24 | GCC_PRECOMPILE_PREFIX_HEADER = NO 25 | -------------------------------------------------------------------------------- /Configurations/Shared/Project.release.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #include "Project.base.xcconfig" 19 | 20 | GREENWICH_CONFIG = RELEASE 21 | 22 | GCC_OPTIMIZATION_LEVEL = s 23 | GCC_GENERATE_DEBUGGING_SYMBOLS = YES 24 | DEBUG_INFORMATION_FORMAT = dwarf-with-dsym 25 | DEPLOYMENT_POSTPROCESSING = YES 26 | STRIP_INSTALLED_PRODUCT = YES 27 | SEPARATE_STRIP = YES 28 | COPY_PHASE_STRIP = YES 29 | STRIP_STYLE = non-global 30 | -------------------------------------------------------------------------------- /Configurations/iOS/Base.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | // \brief Standard settings 19 | // \details These settings are shared by all configurations. They 20 | // are not dynamic. 21 | // ------------------------------------------------------------------ 22 | 23 | SDKROOT = iphoneos 24 | TARGETED_DEVICE_FAMILY = 1,2 25 | GCC_VERSION = com.apple.compilers.llvm.clang.1_0 26 | HEADER_SEARCH_PATHS = $(inherited) $(BUILT_PRODUCTS_DIR)/usr/local/include/ 27 | CODE_SIGN_IDENTITY[sdk=iphoneos*] = iPhone Developer 28 | VALIDATE_PRODUCT = YES 29 | CLANG_ENABLE_OBJC_ARC = YES 30 | STRIP_STYLE = debugging 31 | -------------------------------------------------------------------------------- /Configurations/iOS/Library.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #include "Base.xcconfig" 19 | 20 | EXECUTABLE_PREFIX = 21 | EXECUTABLE_SUFFIX = 22 | EXECUTABLE_PATH = $(WRAPPER_PATH)/$(EXECUTABLE_NAME) 23 | 24 | WRAPPER_EXTENSION = framework 25 | WRAPPER_SUFFIX = .$(WRAPPER_EXTENSION) 26 | WRAPPER_PATH = $(PRODUCT_NAME)$(WRAPPER_SUFFIX) 27 | 28 | FULL_PRODUCT_NAME = $(WRAPPER_PATH) 29 | 30 | CONTENTS_FOLDER_PATH = $(WRAPPER_PATH) 31 | PUBLIC_HEADERS_FOLDER_PATH = $(CONTENTS_FOLDER_PATH)/Headers 32 | PRIVATE_HEADERS_FOLDER_PATH = $(CONTENTS_FOLDER_PATH)/PrivateHeaders 33 | UNLOCALIZED_RESOURCES_FOLDER_PATH = $(CONTENTS_FOLDER_PATH) 34 | DWARF_DSYM_FILE_NAME = $(FULL_PRODUCT_NAME).dSYM 35 | 36 | OTHER_LDFLAGS = -ObjC 37 | -------------------------------------------------------------------------------- /Example/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | @interface AppDelegate : NSObject 21 | 22 | @property (assign) IBOutlet NSWindow *window; 23 | @property (assign) IBOutlet NSTextField *codeTextField; 24 | @property (assign) IBOutlet NSTextField *designTextField; 25 | 26 | - (IBAction)translateApplication:(id)sender; 27 | 28 | @end 29 | -------------------------------------------------------------------------------- /Example/AppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | #import "AppDelegate.h" 21 | 22 | @implementation AppDelegate 23 | 24 | @synthesize window = _window; 25 | @synthesize codeTextField = _codeTextField; 26 | @synthesize designTextField = _designTextField; 27 | 28 | - (void)applicationDidFinishLaunching:(NSNotification *)notification { 29 | [[FRLocalizationManager defaultLocalizationManager] installExtraHelpMenu]; 30 | } 31 | 32 | - (void)awakeFromNib { 33 | [self.codeTextField setStringValue:MyLocalizedString(@"Code text", nil)]; 34 | } 35 | 36 | - (void)awakeFromLocalization { 37 | [self.codeTextField sizeToFit]; 38 | [self.designTextField sizeToFit]; 39 | 40 | CGFloat width = fmax(NSWidth(self.codeTextField.frame), NSWidth(self.designTextField.frame)); 41 | CGFloat proposedWidth = width + 40; 42 | NSSize size = [self.window.contentView frame].size; 43 | if (proposedWidth > size.width) { 44 | size.width = proposedWidth; 45 | [self.window setContentSize:size]; 46 | } 47 | } 48 | 49 | - (IBAction)translateApplication:(id)sender { 50 | [[FRLocalizationManager defaultLocalizationManager] showTranslatorWindow:nil]; 51 | } 52 | 53 | @end 54 | -------------------------------------------------------------------------------- /Example/Example.pch: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #ifdef __OBJC__ 19 | #import 20 | #endif 21 | 22 | // using a custom localized string method to show how Greenwich handles this 23 | #define MyLocalizedString NSLocalizedString 24 | -------------------------------------------------------------------------------- /Example/Example.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleExecutable 8 | ${EXECUTABLE_NAME} 9 | CFBundleIconFile 10 | 11 | CFBundleIdentifier 12 | com.fadingred.${PRODUCT_NAME:rfc1034identifier} 13 | CFBundleInfoDictionaryVersion 14 | 6.0 15 | CFBundleName 16 | ${PRODUCT_NAME} 17 | CFBundlePackageType 18 | APPL 19 | CFBundleShortVersionString 20 | 1.0 21 | CFBundleSignature 22 | ???? 23 | CFBundleVersion 24 | 1 25 | LSMinimumSystemVersion 26 | ${MACOSX_DEPLOYMENT_TARGET} 27 | NSHumanReadableCopyright 28 | Copyright © 2012 FadingRed LLC. All rights reserved. 29 | NSMainNibFile 30 | MainMenu 31 | NSPrincipalClass 32 | NSApplication 33 | 34 | 35 | -------------------------------------------------------------------------------- /Example/Example.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Example/Example.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEWorkspaceSharedSettings_AutocreateContextsIfNeeded 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Example/Example.xcodeproj/xcshareddata/xcschemes/GreenwichExample.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 24 | 25 | 30 | 31 | 32 | 33 | 39 | 40 | 41 | 42 | 51 | 52 | 58 | 59 | 60 | 61 | 65 | 66 | 67 | 68 | 69 | 70 | 76 | 77 | 83 | 84 | 85 | 86 | 88 | 89 | 92 | 93 | 94 | -------------------------------------------------------------------------------- /Example/de.lproj/Localizable.strings: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/fadingred/Greenwich/d163573aaf886814e6145c51ff9ebf228fd7a831/Example/de.lproj/Localizable.strings -------------------------------------------------------------------------------- /Example/de.lproj/MainMenu.strings: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/fadingred/Greenwich/d163573aaf886814e6145c51ff9ebf228fd7a831/Example/de.lproj/MainMenu.strings -------------------------------------------------------------------------------- /Example/en.lproj/Localizable.strings: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/fadingred/Greenwich/d163573aaf886814e6145c51ff9ebf228fd7a831/Example/en.lproj/Localizable.strings -------------------------------------------------------------------------------- /Example/en.lproj/MainMenu.strings: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/fadingred/Greenwich/d163573aaf886814e6145c51ff9ebf228fd7a831/Example/en.lproj/MainMenu.strings -------------------------------------------------------------------------------- /Example/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | int main(int argc, char *argv[]) 21 | { 22 | return NSApplicationMain(argc, (const char **)argv); 23 | } 24 | -------------------------------------------------------------------------------- /Framework/External/Availability/RedAvailability.h: -------------------------------------------------------------------------------- 1 | // 2 | // FRAvailability.h 3 | // RedFoundation 4 | // 5 | // Created by Whitney Young on 5/2/11. 6 | // Copyright 2013 FadingRed LLC. All rights reserved. 7 | // 8 | 9 | #ifdef __APPLE__ 10 | #include 11 | #include 12 | #endif 13 | 14 | #if TARGET_OS_IPHONE || TARGET_IPHONE_SIMULATOR 15 | #define RED_TARGET_IOS 1 16 | #elif TARGET_OS_MAC 17 | #define RED_TARGET_MAC 1 18 | #else 19 | #error unknown os target 20 | #endif 21 | -------------------------------------------------------------------------------- /Framework/External/FRBundleAdditions.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface NSBundle (FRBundleAdditions) 19 | 20 | /*! 21 | \brief Find a bundle by identifier 22 | \details This will find a bundle for the given identifier. It is similar to 23 | NSBundle::bundleWithIdentifier, but doesn't just look at loaded 24 | bundles. It will also look for bundles embeded in the main application 25 | bundle and recursively searching for bundles. The results are cached 26 | after the first invocation to keep the method efficient. With iOS this 27 | can be used by frameworks and bundles to find resources they use (since 28 | loadable frameworks and bundles aren't allowed on iOS). 29 | */ 30 | + (id)bundleWithIdentifier:(NSString *)identifier loaded:(BOOL *)isLoaded; 31 | 32 | /*! 33 | \brief Bundle name 34 | \details Trys to look up bundle name first by 35 | CFBundleDisplayName, then by CFBundleName, 36 | and then by CFBundleExecutable. 37 | */ 38 | - (NSString *)name; 39 | 40 | /*! 41 | \brief Bundle version 42 | \details Trys to look up bundle version by 43 | CFBundleVersion. 44 | */ 45 | - (NSString *)version; 46 | 47 | /*! 48 | \brief The application suport directory for the bunlde 49 | \details Gets the application support directory for this bundle 50 | by searching for the correct directory, then appending 51 | the name of the bundle. Will not create the directory. 52 | */ 53 | - (NSString *)applicationSupportDirectory; 54 | 55 | /*! 56 | \brief Alternative private frameworks path 57 | \details Frameworks may store sub-frameworks at a different location from what the standard private 58 | frameworks path returns. It could be stored alongside the executable in the version 59 | directory. This is where Xcode places it during the copy frameworks build phase. Returns nil 60 | if there is no alternative path for this type of bundle. 61 | */ 62 | - (NSString *)alternativePrivateFrameworksPath; 63 | 64 | /*! 65 | \brief Builtin bundles path 66 | \details Contains bundles for resources. Mostly used on iOS. 67 | */ 68 | - (NSString *)builtInBundlesPath; 69 | 70 | @end 71 | -------------------------------------------------------------------------------- /Framework/External/FRBundleAdditions.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #ifndef REDLINKED_BUNDLE_ADDITIONS 19 | 20 | #import "FRBundleAdditions.h" 21 | 22 | @implementation NSBundle (FRBundleAdditions) 23 | 24 | + (id)bundleWithIdentifier:(NSString *)identifier loaded:(BOOL *)isLoaded { 25 | static NSMutableDictionary *cache = nil; 26 | if (cache == nil) { @synchronized(self) { if (cache == nil) { 27 | cache = [[NSMutableDictionary alloc] init]; 28 | NSMutableArray *search = [NSMutableArray arrayWithObject:[NSBundle mainBundle]]; 29 | 30 | void (^iterate_directory)(NSString *) = ^(NSString *directory) { 31 | NSArray *contents = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:directory error:NULL]; 32 | for (NSString *path in contents) { 33 | NSBundle *bundle = [NSBundle bundleWithPath:[directory stringByAppendingPathComponent:path]]; 34 | if (bundle) { 35 | [search addObject:bundle]; 36 | } 37 | } 38 | }; 39 | 40 | while ([search count]) { 41 | NSBundle *bundle = [search objectAtIndex:0]; 42 | iterate_directory([bundle privateFrameworksPath]); 43 | iterate_directory([bundle alternativePrivateFrameworksPath]); 44 | iterate_directory([bundle builtInPlugInsPath]); 45 | iterate_directory([bundle builtInBundlesPath]); 46 | 47 | NSString *bundleID = [bundle objectForInfoDictionaryKey:(id)kCFBundleIdentifierKey]; 48 | if (bundleID) { 49 | [cache setObject:bundle forKey:bundleID]; 50 | } 51 | 52 | [search removeObjectAtIndex:0]; 53 | } 54 | }}} 55 | 56 | id bundle = nil; 57 | if (!bundle) { // look at loaded bundles 58 | bundle = [NSBundle bundleWithIdentifier:identifier]; 59 | if (bundle && isLoaded) { *isLoaded = TRUE; } 60 | } 61 | if (!bundle) { // look at unloaded bundles 62 | bundle = [cache objectForKey:identifier]; 63 | if (bundle && isLoaded) { *isLoaded = FALSE; } 64 | } 65 | return bundle; 66 | } 67 | 68 | - (NSString *)name { 69 | NSString *name = [self objectForInfoDictionaryKey:@"CFBundleDisplayName"]; 70 | if (!name) { name = [self objectForInfoDictionaryKey:@"CFBundleName"]; } 71 | if (!name) { name = [self objectForInfoDictionaryKey:@"CFBundleExecutable"]; } 72 | return name; 73 | } 74 | 75 | - (NSString *)version { 76 | return [self objectForInfoDictionaryKey:@"CFBundleVersion"]; 77 | } 78 | 79 | - (NSString *)applicationSupportDirectory { 80 | NSArray *search = NSSearchPathForDirectoriesInDomains(NSApplicationSupportDirectory, NSUserDomainMask, YES); 81 | return [search count] ? [[search objectAtIndex:0] stringByAppendingPathComponent:[self name]] : nil; 82 | } 83 | 84 | - (NSString *)alternativePrivateFrameworksPath { 85 | NSString *path = nil; 86 | if ([[[self bundlePath] pathExtension] isEqualToString:@"framework"]) { 87 | NSFileManager *fileManager = [NSFileManager defaultManager]; 88 | NSString *executablePath = [self executablePath]; 89 | NSString *executableDirectory = [executablePath stringByDeletingLastPathComponent]; 90 | NSString *executableLink = [fileManager destinationOfSymbolicLinkAtPath:executablePath error:NULL]; 91 | if (executableLink) { 92 | if (![executableLink hasPrefix:@"/"]) { 93 | executableLink = [executableDirectory stringByAppendingPathComponent:executableLink]; 94 | } 95 | executablePath = executableLink; 96 | } 97 | NSString *versionDirectory = [executablePath stringByDeletingLastPathComponent]; 98 | path = [versionDirectory stringByAppendingPathComponent:@"Frameworks"]; 99 | } 100 | return path; 101 | } 102 | 103 | - (NSString *)builtInBundlesPath { 104 | NSString *directory = [[self builtInPlugInsPath] stringByDeletingLastPathComponent]; 105 | return [directory stringByAppendingPathComponent:@"Bundles"]; 106 | } 107 | 108 | @end 109 | 110 | #endif 111 | -------------------------------------------------------------------------------- /Framework/External/FRExtraHelpController.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | /*! 19 | \brief Extra help menu 20 | \details This should be used as the help menu delegate. It will show items 21 | only when the option key is pressed. 22 | */ 23 | @interface FRExtraHelpController : NSObject { 24 | NSMenu *openMenu; 25 | NSMenuItem *separator; 26 | NSMutableArray *items; 27 | CFMachPortRef eventTap; 28 | CFRunLoopSourceRef runLoopSource; 29 | } 30 | 31 | + (id)defaultController; 32 | 33 | /*! 34 | \brief Installs the extra help items 35 | \details Sets up the extra help controller to work with the last 36 | item in the main menu (which it assumes is the help menu). 37 | */ 38 | - (void)install; 39 | 40 | /*! 41 | \brief Add an item 42 | \details Add an extra help item 43 | */ 44 | - (void)addItem:(NSMenuItem *)item; 45 | 46 | /*! 47 | \brief Insert an item 48 | \details Insert an extra help item 49 | */ 50 | - (void)insertItem:(NSMenuItem *)newItem atIndex:(NSInteger)index; 51 | 52 | /*! 53 | \brief Get the item array 54 | \details All of the extra help items 55 | */ 56 | - (NSArray *)itemArray; 57 | 58 | @end 59 | -------------------------------------------------------------------------------- /Framework/External/FRFileManagerArchivingAdditions.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #if defined(REDFOUNDATION_LEOPARD_BASE) // not supported 19 | #else 20 | 21 | @interface NSFileManager (FRFileManagerArchivingAdditions) 22 | 23 | /*! 24 | \brief Compress a file or directory 25 | \details Create a tar/bzip2 compressed version of the source at the destination. 26 | */ 27 | - (BOOL)compressItemAtPath:(NSString *)sourcePath 28 | to:(NSString *)destinationPath 29 | error:(NSError **)error; 30 | 31 | /*! 32 | \brief Compress a files and/or directories 33 | \details Create a tar/bzip2 compressed version of the sources at the destination. 34 | */ 35 | - (BOOL)compressItems:(NSArray *)relativePaths relativeToDirectory:(NSString *)directory 36 | to:(NSString *)destinationPath 37 | error:(NSError **)error; 38 | 39 | /*! 40 | \brief Uncompress a file or directory 41 | \details Create a tar/bzip2 compressed version of the source at the destination. 42 | */ 43 | 44 | - (BOOL)uncompressItemAtPath:(NSString *)sourcePath 45 | to:(NSString *)destinationPath 46 | error:(NSError **)error; 47 | 48 | @end 49 | 50 | #endif 51 | -------------------------------------------------------------------------------- /Framework/External/FRFileManagerArchivingAdditions.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | #import "FRFileManagerArchivingAdditions.h" 21 | #import "archiving.h" 22 | 23 | #if defined(REDFOUNDATION_LEOPARD_BASE) // not supported 24 | #elif defined(REDLINKED_FILE_MANAGER_ARCHIVING_ADDITIONS) // not needed, linked in 25 | #else 26 | 27 | @implementation NSFileManager (FRFileManagerArchivingAdditions) 28 | 29 | - (BOOL)compressItemAtPath:(NSString *)source 30 | to:(NSString *)destination 31 | error:(NSError **)error { 32 | return [self compressItems:[NSArray arrayWithObject:[source lastPathComponent]] 33 | relativeToDirectory:[source stringByDeletingLastPathComponent] 34 | to:destination error:error]; 35 | } 36 | 37 | - (BOOL)compressItems:(NSArray *)relativePathnames relativeToDirectory:(NSString *)directory 38 | to:(NSString *)destination error:(NSError **)error { 39 | 40 | 41 | BOOL success = FALSE; 42 | 43 | mode_t mode = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH; 44 | int flag = O_WRONLY | O_CREAT | O_EXCL; 45 | int write_fd = open([destination fileSystemRepresentation], flag, mode); 46 | if (write_fd < 0) { 47 | if (error) { *error = [NSError errorWithDomain:NSPOSIXErrorDomain code:write_fd userInfo:nil]; } 48 | success = FALSE; 49 | } 50 | else { 51 | size_t count = [relativePathnames count]; 52 | const char **pathnames = malloc(sizeof(char *) * (count + 1)); 53 | [relativePathnames enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) { 54 | pathnames[idx] = strdup([obj fileSystemRepresentation]); 55 | }]; 56 | pathnames[count] = NULL; 57 | 58 | // create the compression task 59 | char *chdir_location = strdup([directory fileSystemRepresentation]); 60 | int status = archive_create_tar_bzip2(write_fd, chdir_location, pathnames); 61 | success = (status == 0); 62 | close(write_fd); 63 | 64 | if (success) { } // nothing to do on success 65 | else { 66 | if (error) { *error = [NSError errorWithDomain:NSPOSIXErrorDomain code:status userInfo:nil]; } 67 | } 68 | 69 | // free memory 70 | for (size_t i = 0; i <= count; i++) { free((char *)pathnames[i]); } 71 | free(pathnames); 72 | free(chdir_location); 73 | } 74 | 75 | return success; 76 | } 77 | 78 | - (BOOL)uncompressItemAtPath:(NSString *)source 79 | to:(NSString *)destination 80 | error:(NSError **)error { 81 | 82 | BOOL success = FALSE; 83 | 84 | int read_fd = open([source fileSystemRepresentation], O_RDONLY); 85 | if (read_fd < 0) { 86 | if (error) { *error = [NSError errorWithDomain:NSPOSIXErrorDomain code:read_fd userInfo:nil]; } 87 | success = FALSE; 88 | } 89 | else { 90 | // get a unique temp directory 91 | char *dirname = NULL; 92 | asprintf(&dirname, "%s/XXXXXX", [NSTemporaryDirectory() fileSystemRepresentation]); 93 | char *chdir_location = mkdtemp(dirname); 94 | 95 | // create the extraction task 96 | int status = archive_extract_tar_bzip2(read_fd, chdir_location); 97 | success = (status == 0); 98 | close(read_fd); 99 | 100 | if (success) { 101 | NSFileManager *manager = [NSFileManager defaultManager]; 102 | NSString *extractPath = [manager stringWithFileSystemRepresentation:chdir_location 103 | length:strlen(chdir_location)]; 104 | NSArray *extractedItems = [self contentsOfDirectoryAtPath:extractPath error:error]; 105 | if ([extractedItems count] == 1) { 106 | NSString *extractedItemName = [extractedItems lastObject]; 107 | NSString *extractedItemPath = [extractPath stringByAppendingPathComponent:extractedItemName]; 108 | if (extractedItemPath) { 109 | success = [self moveItemAtPath:extractedItemPath toPath:destination error:error]; 110 | } 111 | } 112 | else { 113 | success = [self createDirectoryAtPath:destination withIntermediateDirectories:YES 114 | attributes:nil error:error]; 115 | if (success) { 116 | for (NSString *itemName in extractedItems) { 117 | NSString *moveFrom = [extractPath stringByAppendingPathComponent:itemName]; 118 | NSString *moveTo = [destination stringByAppendingPathComponent:itemName]; 119 | success = [self moveItemAtPath:moveFrom toPath:moveTo error:error]; 120 | if (!success) { break; } 121 | } 122 | } 123 | } 124 | } 125 | else { 126 | if (error) { *error = [NSError errorWithDomain:NSPOSIXErrorDomain code:status userInfo:nil]; } 127 | } 128 | 129 | free(chdir_location); 130 | } 131 | 132 | return success; 133 | } 134 | 135 | @end 136 | 137 | #endif 138 | -------------------------------------------------------------------------------- /Framework/External/FRRuntimeAdditions.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | typedef IMP *IMPPointer; 21 | 22 | @interface NSObject (FRRuntimeAdditions) 23 | 24 | /*! 25 | \brief Performs a method swizzle 26 | \details Swizzles original with replacement. 27 | This is a little different from traditional method swizzling, but the concept is the same. The 28 | original method will be replaced by a new method, and you can have the old implementation stored 29 | in an IMP pointer for use in the swizzled method. This works out to be a little safer than method 30 | swizzling since the _cmd argument can be passed through to the original IMP unaltered. 31 | */ 32 | + (BOOL)swizzle:(SEL)original with:(IMP)replacement store:(IMPPointer)store; 33 | 34 | /*! 35 | \brief Performs a class method swizzle 36 | \details Swizzles original with replacement. 37 | \see NSObject::swizzle:with:store: for details. 38 | */ 39 | + (BOOL)swizzleClassMethod:(SEL)original with:(IMP)replacement store:(IMPPointer)store; 40 | 41 | @end 42 | 43 | /*! 44 | \brief Simply calls builtin method 45 | \details This shouldn't really be needed. We're waiting for some comipler fixes for this. 46 | */ 47 | void *object_getClassPointer(__unsafe_unretained id object); 48 | 49 | /*! 50 | \brief Simply calls builtin method 51 | \details This shouldn't really be needed. We're waiting for some comipler fixes for this. 52 | */ 53 | void *objc_getClassPointer(const char *name); 54 | 55 | /*! 56 | \brief Simply calls builtin method 57 | \details This shouldn't really be needed. We're waiting for some comipler fixes for this. 58 | */ 59 | void *objc_allocateClassPairPointer(Class superclass, const char *name, size_t extraBytes); 60 | -------------------------------------------------------------------------------- /Framework/External/FRRuntimeAdditions.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #ifndef REDLINKED_RUNTIME_ADDITIONS 19 | 20 | #import 21 | 22 | #import "FRRuntimeAdditions.h" 23 | 24 | BOOL class_swizzleMethodAndStore(Class class, SEL original, IMP replacement, IMPPointer store); 25 | BOOL class_swizzleMethodAndStore(Class class, SEL original, IMP replacement, IMPPointer store) { 26 | BOOL success = FALSE; 27 | IMP imp = NULL; 28 | Method method = class_getInstanceMethod(class, original); 29 | if (method) { 30 | // ensure the method is defined in this class by trying to add it to the class, get the new method 31 | // pointer if it was actually added (this is now considered the original), then get the imp for the 32 | // original method & replace the method. 33 | const char *type = method_getTypeEncoding(method); 34 | if (class_addMethod(class, original, method_getImplementation(method), type)) { 35 | method = class_getInstanceMethod(class, original); 36 | } 37 | imp = method_getImplementation(method); 38 | success = TRUE; 39 | class_replaceMethod(class, original, replacement, type); 40 | } 41 | if (imp && store) { *store = imp; } 42 | return success; 43 | } 44 | 45 | void *object_getClassPointer(__unsafe_unretained id obj) { return (__bridge void *)object_getClass(obj); } 46 | void *objc_getClassPointer(const char *name) { return (__bridge void *)objc_getClass(name); } 47 | void *objc_allocateClassPairPointer(Class superclass, const char *name, size_t extraBytes) { 48 | return (__bridge void *)objc_allocateClassPair(superclass, name, extraBytes); 49 | } 50 | 51 | @implementation NSObject (FRRuntimeAdditions) 52 | + (BOOL)swizzle:(SEL)original with:(IMP)replacement store:(IMPPointer)store { 53 | return class_swizzleMethodAndStore(self, original, replacement, store); 54 | } 55 | + (BOOL)swizzleClassMethod:(SEL)original with:(IMP)replacement store:(IMPPointer)store { 56 | return class_swizzleMethodAndStore(object_getClass(self), original, replacement, store); 57 | } 58 | @end 59 | 60 | #endif 61 | -------------------------------------------------------------------------------- /Framework/External/archiving.c: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #if defined(REDFOUNDATION_LEOPARD_BASE) // not supported 19 | #elif defined(REDLINKED_ARCHIVING) // not needed, linked in 20 | #else 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | 30 | #import "archiving.h" 31 | 32 | static int append_path_recursively(const char *relative_to, const char *pathname, struct archive *a); 33 | 34 | int archive_create_tar_bzip2(int fd, const char *relative_to, const char **pathnames) { 35 | int error = 0; 36 | 37 | struct archive *a = archive_write_new(); 38 | archive_write_set_compression_bzip2(a); 39 | archive_write_set_format_ustar(a); 40 | archive_write_open_fd(a, fd); 41 | 42 | while (*pathnames) { 43 | append_path_recursively(relative_to, *pathnames, a); 44 | pathnames++; 45 | } 46 | 47 | archive_write_close(a); 48 | archive_write_finish(a); 49 | 50 | return error; 51 | } 52 | 53 | static int append_path_recursively(const char *relative_to, const char *pathname, struct archive *a) { 54 | int error = 0; 55 | 56 | char *fullpath = NULL; 57 | asprintf(&fullpath, "%s/%s", relative_to, pathname); 58 | 59 | struct archive_entry *entry = archive_entry_new(); 60 | archive_entry_set_pathname(entry, pathname); 61 | struct stat st; 62 | stat(fullpath, &st); 63 | archive_entry_copy_stat(entry, &st); 64 | // if we want to add uname/gname, we should do something like: 65 | // archive_entry_copy_uname(entry, uname); 66 | // archive_entry_copy_gname(entry, gname); 67 | archive_write_header(a, entry); 68 | int fd = open(fullpath, O_RDONLY); 69 | ssize_t amt = 0; 70 | static char buffer[16*1024]; 71 | while ((amt = read(fd, buffer, sizeof(buffer))) > 0) { 72 | archive_write_data(a, buffer, amt); 73 | } 74 | close(fd); 75 | archive_entry_free(entry); 76 | 77 | if (S_ISLNK(st.st_mode)) { } // don't recurse into symbolic link dirs 78 | else if (S_ISDIR(st.st_mode)) { 79 | DIR *dir = opendir(fullpath); 80 | struct dirent *dirent = NULL; 81 | while ((dirent = readdir(dir))) { 82 | if (strcmp(dirent->d_name, ".") == 0 || 83 | strcmp(dirent->d_name, "..") == 0) { continue; } 84 | 85 | char *subpath = NULL; 86 | asprintf(&subpath, "%s/%s", pathname, dirent->d_name); 87 | error = append_path_recursively(relative_to, subpath, a); 88 | free(subpath); 89 | 90 | if (error != 0) { break; } 91 | } 92 | } 93 | 94 | free(fullpath); 95 | return error; 96 | } 97 | 98 | int archive_extract_tar_bzip2(int fd, const char *relative_to) { 99 | struct archive *a; 100 | struct archive *ext; 101 | int r = 0; 102 | int flags = 0; 103 | int error = 0; 104 | 105 | a = archive_read_new(); 106 | archive_read_support_format_tar(a); 107 | archive_read_support_compression_bzip2(a); 108 | 109 | ext = archive_write_disk_new(); 110 | archive_write_disk_set_options(ext, flags); 111 | 112 | if ((r = archive_read_open_fd(a, fd, 10240))) { 113 | fprintf(stderr, "archiving: %s", archive_error_string(a)); 114 | error = r; 115 | } 116 | else { 117 | for (;;) { 118 | struct archive_entry *entry; 119 | r = archive_read_next_header(a, &entry); 120 | if (r == ARCHIVE_EOF) { break; } 121 | if (r != ARCHIVE_OK) { 122 | fprintf(stderr, "archiving: %s", archive_error_string(a)); 123 | error = 1; 124 | break; 125 | } 126 | 127 | // update path to the full pathname 128 | const char *pathname = archive_entry_pathname(entry); 129 | char *fullpath = NULL; 130 | asprintf(&fullpath, "%s/%s", relative_to ? relative_to : ".", pathname); 131 | archive_entry_set_pathname(entry, fullpath); 132 | 133 | if (archive_write_header(ext, entry) != ARCHIVE_OK) { 134 | fprintf(stderr, "archiving: %s", archive_error_string(ext)); 135 | } 136 | else { 137 | const void *buff; 138 | size_t size; 139 | off_t offset; 140 | 141 | for (;;) { 142 | r = archive_read_data_block(a, &buff, &size, &offset); 143 | if (r == ARCHIVE_EOF) { r = ARCHIVE_OK; break; } 144 | if (r != ARCHIVE_OK) { 145 | fprintf(stderr, "archiving: %s", archive_error_string(ext)); 146 | break; 147 | } 148 | r = archive_write_data_block(ext, buff, size, offset); 149 | if (r != ARCHIVE_OK) { 150 | fprintf(stderr, "archiving: %s", archive_error_string(ext)); 151 | break; 152 | } 153 | } 154 | if (r != ARCHIVE_OK) { 155 | error = 1; 156 | break; 157 | } 158 | 159 | r = archive_write_finish_entry(ext); 160 | if (r != ARCHIVE_OK) { 161 | fprintf(stderr, "archiving: %s", archive_error_string(ext)); 162 | error = 1; 163 | break; 164 | } 165 | } 166 | 167 | free(fullpath); 168 | } 169 | } 170 | archive_read_close(a); 171 | archive_read_finish(a); 172 | 173 | return error; 174 | } 175 | 176 | #endif 177 | -------------------------------------------------------------------------------- /Framework/External/archiving.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #if defined(REDFOUNDATION_LEOPARD_BASE) // not supported 19 | #else 20 | 21 | /*! 22 | \brief Create a bzip2 compressed archive 23 | \details Create a tar bzip2 archive from the pathnames relative to a given path and write the archive 24 | to a file descriptor. Pathnames should be NULL terminated. 25 | */ 26 | int archive_create_tar_bzip2(int fd, const char *relative_to, const char **pathnames); 27 | 28 | /*! 29 | \brief Extract a bzip2 compressed archive 30 | \details Extracts a tar bzip2 archive by reading from a file descriptor and writing the archive out 31 | relative to a given path. 32 | */ 33 | int archive_extract_tar_bzip2(int fd, const char *relative_to); 34 | 35 | #endif 36 | -------------------------------------------------------------------------------- /Framework/External/libarchive/libarchive.dylib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/fadingred/Greenwich/d163573aaf886814e6145c51ff9ebf228fd7a831/Framework/External/libarchive/libarchive.dylib -------------------------------------------------------------------------------- /Framework/External/libarchive/libarchive.license: -------------------------------------------------------------------------------- 1 | Copyright (c) 2003-2009 Tim Kientzle 2 | All rights reserved. 3 | 4 | Redistribution and use in source and binary forms, with or without 5 | modification, are permitted provided that the following conditions 6 | are met: 7 | 1. Redistributions of source code must retain the above copyright 8 | notice, this list of conditions and the following disclaimer 9 | in this position and unchanged. 10 | 2. Redistributions in binary form must reproduce the above copyright 11 | notice, this list of conditions and the following disclaimer in the 12 | documentation and/or other materials provided with the distribution. 13 | 14 | THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR 15 | IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 16 | OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 17 | IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT, 18 | INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 19 | NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 20 | DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 21 | THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 23 | THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -------------------------------------------------------------------------------- /Framework/Greenwich.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Framework/Info/Localization.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | English 7 | CFBundleExecutable 8 | ${EXECUTABLE_NAME} 9 | CFBundleIdentifier 10 | ${BUNDLE_IDENTIFIER} 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundlePackageType 14 | FMWK 15 | CFBundleSignature 16 | ???? 17 | CFBundleVersion 18 | ${GREENWICH_VERSION} 19 | 20 | 21 | -------------------------------------------------------------------------------- /Framework/Info/Translator.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleExecutable 8 | ${EXECUTABLE_NAME} 9 | CFBundleIconFile 10 | 11 | CFBundleIdentifier 12 | com.fadingred.greenwich.Translator 13 | CFBundleInfoDictionaryVersion 14 | 6.0 15 | CFBundleName 16 | ${PRODUCT_NAME} 17 | CFBundlePackageType 18 | APPL 19 | CFBundleShortVersionString 20 | 1.0 21 | CFBundleSignature 22 | ???? 23 | CFBundleVersion 24 | 1 25 | LSApplicationCategoryType 26 | public.app-category.developer-tools 27 | LSMinimumSystemVersion 28 | ${MACOSX_DEPLOYMENT_TARGET} 29 | NSHumanReadableCopyright 30 | Copyright © 2013 FadingRed. All rights reserved. 31 | NSMainNibFile 32 | MainMenu 33 | NSPrincipalClass 34 | NSApplication 35 | 36 | 37 | -------------------------------------------------------------------------------- /Framework/PackageReadme.md: -------------------------------------------------------------------------------- 1 | For detailed installation instructions, please visit the project page: 2 | https://github.com/fadingred/Greenwich 3 | 4 | The files included in this distribution are separated into three folders: 5 | 6 | - Mac: All files in this directory are required for Mac OS X projects 7 | - iOS: All files in this directory are required for iOS projects 8 | - Tools: These are additional tools that can be used with Greenwich 9 | 10 | The tools include: 11 | 12 | - The standalone translator app. This is used by translators for iOS applications. 13 | - A proofing tool. More info can be found here: 14 | https://github.com/fadingred/Greenwich/blob/master/Framework/Proofer/Readme.md 15 | -------------------------------------------------------------------------------- /Framework/Proofer/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | @class FRProofer; 21 | 22 | @interface AppDelegate : NSObject 23 | 24 | @property (assign) IBOutlet NSWindow *window; 25 | @property (strong, nonatomic) IBOutlet NSTextField *clientIdField; 26 | @property (strong, nonatomic) IBOutlet NSTextField *clientSecretField; 27 | @property (strong, nonatomic) IBOutlet NSButton *proofButton; 28 | @property (strong, nonatomic) IBOutlet NSTextField *pathTextField; 29 | @property (strong, nonatomic) FRProofer *proofer; 30 | 31 | @end 32 | -------------------------------------------------------------------------------- /Framework/Proofer/FRProofer.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @class FRTranslator; 19 | 20 | @interface FRProofer : NSObject 21 | 22 | @property (strong, nonatomic) FRTranslator *translator; 23 | 24 | - (BOOL)setupAccessToken; 25 | - (void)setClientId:(NSString *)clientId clientSecret:(NSString *)clientSecret; 26 | - (void)proofFileFromPath:(NSString *)fromPath toPath:(NSString *)toPath; 27 | 28 | @end 29 | -------------------------------------------------------------------------------- /Framework/Proofer/FRSingleNodeParsingDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | @interface FRSingleNodeParsingDelegate : NSObject 21 | 22 | @property (strong, nonatomic) NSString *result; 23 | 24 | @end 25 | -------------------------------------------------------------------------------- /Framework/Proofer/FRSingleNodeParsingDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRSingleNodeParsingDelegate.h" 19 | 20 | @implementation FRSingleNodeParsingDelegate 21 | 22 | @synthesize result; 23 | 24 | - (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string { 25 | self.result = string; 26 | } 27 | 28 | @end 29 | -------------------------------------------------------------------------------- /Framework/Proofer/FRTranslateArrayResultParsingDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | @interface FRTranslateArrayResultParsingDelegate : NSObject 21 | 22 | @property (nonatomic) BOOL parsing; 23 | @property (nonatomic) BOOL nextCharsAreTranslation; 24 | @property (strong, nonatomic) NSMutableArray *translations; 25 | 26 | @end 27 | -------------------------------------------------------------------------------- /Framework/Proofer/FRTranslateArrayResultParsingDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRTranslateArrayResultParsingDelegate.h" 19 | 20 | @implementation FRTranslateArrayResultParsingDelegate 21 | 22 | @synthesize parsing; 23 | @synthesize nextCharsAreTranslation; 24 | @synthesize translations; 25 | 26 | - (void)parserDidStartDocument:(NSXMLParser *)parser { 27 | NSLog(@"Starting parse..."); 28 | translations = [[NSMutableArray alloc] init]; 29 | parsing = YES; 30 | } 31 | 32 | - (void)parserDidEndDocument:(NSXMLParser *)parser { 33 | NSLog(@"Ending parse..."); 34 | NSLog(@"Translations: %@", translations); 35 | parsing = NO; 36 | } 37 | 38 | - (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI 39 | qualifiedName:(NSString *)qualifiedName attributes:(NSDictionary *)attributeDict { 40 | if ([elementName isEqualToString:@"TranslatedText"]) { nextCharsAreTranslation = YES; } 41 | } 42 | 43 | - (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string { 44 | if (nextCharsAreTranslation) { 45 | [translations addObject:string]; 46 | nextCharsAreTranslation = NO; 47 | } 48 | } 49 | 50 | @end 51 | -------------------------------------------------------------------------------- /Framework/Proofer/FRTranslator.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @class 19 | FRSingleNodeParsingDelegate, FRTranslateArrayResultParsingDelegate; 20 | 21 | @interface FRTranslator : NSObject 22 | 23 | @property (strong, nonatomic) NSString *clientId; 24 | @property (strong, nonatomic) NSString *clientSecret; 25 | 26 | @property (strong, nonatomic) NSString *authToken; 27 | @property (strong, nonatomic) NSString *language; 28 | @property (strong, nonatomic) FRSingleNodeParsingDelegate *singleNodeParser; 29 | @property (strong, nonatomic) FRTranslateArrayResultParsingDelegate *translatedArrayParser; 30 | 31 | - (BOOL)getAccessToken; 32 | - (NSArray *)translateArray:(NSArray *)arrayToTranslate; 33 | - (NSString *)detectLanguageOfString:(NSString *)stringToDetect; 34 | 35 | @end 36 | -------------------------------------------------------------------------------- /Framework/Proofer/Proofer-Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleExecutable 8 | ${EXECUTABLE_NAME} 9 | CFBundleIconFile 10 | 11 | CFBundleIdentifier 12 | com.fadingred.${PRODUCT_NAME:rfc1034identifier} 13 | CFBundleInfoDictionaryVersion 14 | 6.0 15 | CFBundleName 16 | ${PRODUCT_NAME} 17 | CFBundlePackageType 18 | APPL 19 | CFBundleShortVersionString 20 | 1.0 21 | CFBundleSignature 22 | ???? 23 | CFBundleVersion 24 | 1 25 | LSMinimumSystemVersion 26 | ${MACOSX_DEPLOYMENT_TARGET} 27 | NSHumanReadableCopyright 28 | Copyright © 2013 FadingRed. All rights reserved. 29 | NSMainNibFile 30 | MainMenu 31 | NSPrincipalClass 32 | NSApplication 33 | 34 | 35 | -------------------------------------------------------------------------------- /Framework/Proofer/Readme.md: -------------------------------------------------------------------------------- 1 | # Greenwich Proofer 2 | 3 | Proofer is a small application for checking the relative correctness of translations you receive. Translations may be done by volunteers and there is no guarantee of their correctness. Publishing an internationalized version of your application where you have no idea what the text is saying is scary and potentially dangerous. 4 | 5 | After editing translations for an app, Greenwich packages these translations into a `.tbz` file. Open this file with the proofer and select Proof to receive translations of all of the files in the archive. The output will be a directory with an identical structure to the contents of the `.tbz`. However, all of the `.strings` files will have an additional line for each translation. 6 | 7 | Here's an example: 8 | 9 | The original `.strings` file produced by Greenwich looks like this: 10 | 11 | /* No comment provided by engineer. */ 12 | "quarter" = "Quartal"; 13 | 14 | /* No comment provided by engineer. */ 15 | "quarters" = "Quartale"; 16 | 17 | /* No comment provided by engineer. */ 18 | "this month" = "dieser Monat"; 19 | 20 | /* No comment provided by engineer. */ 21 | "this quarter" = "dieses Quartal"; 22 | 23 | After passing through the Proofer the corresponding output file would have this format: 24 | 25 | /* Translation = Original = Proofed */ 26 | "Quartal" = "quarter" = "Quarter" 27 | "Quartale" = "quarters" = "Quarters" 28 | "dieser Monat" = "this month" = "This month" 29 | "dieses Quartal" = "this quarter" = "this quarter" 30 | 31 | The translation provided by the translator is on the left side, followed by the original word in the application that the translator is translating from, and then the translation provided by Microsoft's Translate API at the end. The original and proofed phrases are next to each other to enable ease of comparison. 32 | 33 | Proofer uses Microsoft's translation API to translate the text. Here are the steps for obtaining a Microsoft Translation Access Token: 34 | 35 | 1. If you don't have a Windows Live account, you'll have to make one at live.com. 36 | 1. Go to the [Azure Marketplace](https://datamarket.azure.com/dataset/1899a118-d202-492c-aa16-ba21c33c06cb) and sign up for Microsoft Translator. The free plan will let you translate 2,000,000 characters per month. Click Sign Up for the plan you'd like, enter your information, and accept the terms of use. 37 | 1. [Register an application](https://datamarket.azure.com/developer/applications/) so you can begin using the translation service. 38 | - The Client ID is an arbitrary name for your application that you choose. 39 | - The Name is an arbitrary name of what you'd like to call your application. 40 | - I'm not sure what the Redirect URI is for. 41 | 1. Click _Edit_ on the application to view your information again. You'll need the client ID and the client secret. 42 | 1. Open the proofer and enter the Client ID and Client Secret from the Azure application edit screen. 43 | -------------------------------------------------------------------------------- /Framework/Proofer/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | int main(int argc, char *argv[]) 21 | { 22 | return NSApplicationMain(argc, (const char **)argv); 23 | } 24 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/Translator/en.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Please choose a location to save your translation package"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Save"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Save Location"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/de.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Bitte wählen Sie einen Speicherort für Ihr Übersetzungspaket aus"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Sichern"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Speicherort"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "%@ übersetzen"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/de.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Paket zum Einsenden"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Übersetzer"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/en.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Please choose a location to save your translation package"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Save"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Save Location"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/en.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Package for Submission"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Translator"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/es.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Por favor, elija un lugar donde guardar su paquete de movimientos"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Guardar"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Guardar posición"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/es.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Empaquetar para Enviar"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Traductor"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/fr.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Choisissez un emplacement pour enregistrer votre module de traduction"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Enregistrer"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Enregistrer l'emplacement"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/fr.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Module à soumettre"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Traducteur"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/it.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Please choose a location to save your translation package"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Save"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Save Location"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/it.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Package for Submission"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Translator"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/ja.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Please choose a location to save your translation package"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Save"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Save Location"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/ja.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Package for Submission"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Translator"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/nl.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Gelieve een locatie te kiezen om je vertaalpakket te bewaren"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Bewaar"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Bewaar Locatie"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/nl.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Verpak voor Verzending"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Vertaler"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/no.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Vennligst velg en plassering til å lagre din oversettelsespakke"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Lagre"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Lagre plassering"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/no.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Pakk til innsending"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Oversetter"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/pt.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorizing" = "Authorizing"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Connected" = "Connected"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Not Connected" = "Not Connected"; 9 | 10 | /* No comment provided by engineer. */ 11 | "Please choose a location to save your translation package" = "Por favor escolha um local para guardar o seu pacote de tradução"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Save" = "Guardar"; 15 | 16 | /* No comment provided by engineer. */ 17 | "Save Location" = "Localização para guardar"; 18 | 19 | /* No comment provided by engineer. */ 20 | "Translate %@" = "Translate %@"; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Resources/Mac/pt.lproj/Localization.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Package for Submission" = "Preparar para submissão"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Send to Device" = "Send to Device"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Translator" = "Tradutor"; 9 | 10 | -------------------------------------------------------------------------------- /Framework/Resources/iOS/en.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Authorize" = "Authorize"; 3 | 4 | /* No comment provided by engineer. */ 5 | "Cancel" = "Cancel"; 6 | 7 | /* No comment provided by engineer. */ 8 | "Localization Setup" = "Localization Setup"; 9 | 10 | /* No comment provided by engineer. */ 11 | "New Localizations" = "New Localizations"; 12 | 13 | /* No comment provided by engineer. */ 14 | "Terminate" = "Terminate"; 15 | 16 | /* No comment provided by engineer. */ 17 | "The computer \"%@\" would like to communicate with your device allowing you to localize this application." = "The computer \"%@\" would like to communicate with your device allowing you to localize this application."; 18 | 19 | /* No comment provided by engineer. */ 20 | "You have added new localizations to the application. To see these localization, you will need to terminate the application and then start it again." = "You have added new localizations to the application. To see these localization, you will need to terminate the application and then start it again."; 21 | 22 | -------------------------------------------------------------------------------- /Framework/Scripts/actions/addlang: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # 3 | # Copyright (c) 2013 FadingRed LLC 4 | # 5 | # Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 6 | # documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 7 | # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 8 | # permit persons to whom the Software is furnished to do so, subject to the following conditions: 9 | # 10 | # The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 11 | # Software. 12 | # 13 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 14 | # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 15 | # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 16 | # OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 17 | # 18 | 19 | from subprocess import Popen, PIPE 20 | import sys 21 | import os 22 | 23 | if __name__ == '__main__': 24 | if len(sys.argv) != 2: 25 | sys.stderr.write('Usage: %s lang\n' % sys.argv[0]) 26 | sys.exit(1) 27 | lang = sys.argv[1] 28 | command = Popen([ 29 | 'find', '.', 30 | '-name', 'en.lproj', 31 | '-not', '-path', '*/.hg/*', 32 | '-not', '-path', '*/build/*'], stdout=PIPE, stderr=PIPE) 33 | stdout, stderr = command.communicate() 34 | if command.returncode == 0: 35 | for line in stdout.split('\n'): 36 | if line.strip(): 37 | directory = os.path.dirname(line) 38 | newdir = os.path.join(directory, '%s.lproj' % lang) 39 | if not os.path.exists(newdir): 40 | sys.stdout.write('Creating %s\n' % newdir) 41 | os.mkdir(newdir) 42 | 43 | else: 44 | sys.stderr.write('warning: could not find lproj folders. find returned error %i\n' % command.returncode) 45 | -------------------------------------------------------------------------------- /Framework/Scripts/actions/migrate: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # 3 | # Copyright (c) 2011 FadingRed LLC 4 | # 5 | # Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 6 | # documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 7 | # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 8 | # permit persons to whom the Software is furnished to do so, subject to the following conditions: 9 | # 10 | # The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 11 | # Software. 12 | # 13 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 14 | # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 15 | # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 16 | # OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 17 | # 18 | 19 | from scriptlib.config import OptionParser 20 | from scriptlib.i18n import Strings, Xib 21 | import sys 22 | import os 23 | import codecs 24 | 25 | # global defines 26 | # ---------------------------------------------------------------------- 27 | 28 | LOCALIZE_SYMBOL = os.environ.get('GREENWICH_LOCALIZATION_SYMBOL', 'NSLocalizedString') # localize symbol used in code 29 | 30 | 31 | # main create strings function 32 | # ---------------------------------------------------------------------- 33 | 34 | def migrate_strings(config): 35 | for resources in config.resources.split(':'): 36 | if os.path.exists(resources): 37 | base_path = os.path.join(resources, '%s.lproj' % config.lang) 38 | remove = [] 39 | move = [] 40 | for xibname in os.listdir(base_path): 41 | if xibname.endswith('.xib'): 42 | xib_path = os.path.join(base_path, xibname) 43 | xib = Xib(xibname, config, resources=resources, path=xib_path) 44 | strings = Strings(xibname, config.lang, config) 45 | xib.generate(strings, normalize=False) 46 | 47 | # handle all languages other than the base language of the file by creating 48 | # and integrating changes from xib files in other lproj directories 49 | for langname in os.listdir(resources): 50 | if langname.endswith('.lproj'): 51 | lang = Strings(xibname, langname, config) 52 | if lang.lang != config.lang: 53 | lang_path = os.path.join(resources, langname) 54 | lang_xib_path = os.path.join(lang_path, xibname) 55 | if os.path.exists(lang_xib_path): 56 | lang_xib = Xib(xibname, config, resources=resources, path=lang_xib_path) 57 | lang_xib.generate(lang, normalize=False) 58 | lang.normalize(source=strings) 59 | remove.append(lang_xib_path) 60 | 61 | # normalize strings after handling all languages 62 | strings.normalize() 63 | move.append(xib_path) 64 | 65 | if move or remove: 66 | if config.force: run = True 67 | else: 68 | sys.stdout.write( 69 | 'Strings files were created successfully. This script can also move your main xib\n' \ 70 | 'file into place and remove extra xibs. %i xib files will be moved, and %i deleted.\n\n' % (len(move), len(remove))) 71 | run = (raw_input('Update xib files? [Y/n] ').lower() == 'y') 72 | if run: 73 | for path in remove: 74 | os.unlink(path) 75 | for path in move: 76 | directory, name = os.path.split(path) 77 | directory = os.path.dirname(directory) 78 | os.rename(path, os.path.join(directory, name)) 79 | 80 | 81 | # main function 82 | # ---------------------------------------------------------------------- 83 | 84 | if __name__ == '__main__': 85 | usage = """usage: %%prog [options] 86 | Used to migrate a project from xib files in their lproj folders to a single xib with multiple strings files.""" 87 | parser = OptionParser(usage=usage) 88 | f = 'Force renaming and removal of old xibs' 89 | parser.add_option('-f', '--force', action="store_true", dest='force', default=False, help=f) 90 | migrate_strings(parser.parse_config()[0]) 91 | -------------------------------------------------------------------------------- /Framework/Scripts/actions/verify: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # 3 | # Copyright (c) 2013 FadingRed LLC 4 | # 5 | # Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 6 | # documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 7 | # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 8 | # permit persons to whom the Software is furnished to do so, subject to the following conditions: 9 | # 10 | # The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 11 | # Software. 12 | # 13 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 14 | # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 15 | # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 16 | # OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 17 | # 18 | 19 | from scriptlib.config import OptionParser 20 | import sys 21 | import os 22 | 23 | # main verify strings function 24 | # ---------------------------------------------------------------------- 25 | 26 | def verify_strings(config): 27 | for resources in config.resources.split(':'): 28 | if os.path.exists(resources): 29 | for lang in os.listdir(resources): 30 | if lang.endswith('.lproj'): 31 | directory = os.path.join(resources, lang) 32 | if os.path.exists(directory): 33 | for stringsname in os.listdir(directory): 34 | name, ext = os.path.splitext(stringsname) 35 | nibpath = os.path.join(config.app_resources, '%s.nib' % name) 36 | storyboardpath = os.path.join(config.app_resources, '%s.storyboardc' % name) 37 | if ext == '.strings' and (name == 'Localizable' or os.path.exists(nibpath) or os.path.exists(storyboardpath)) and \ 38 | os.path.exists(os.path.join(config.app_resources, lang, stringsname)) == False: 39 | sys.stderr.write('warning: missing %s strings file in built product for %s\n' % (lang, stringsname,)) 40 | 41 | 42 | # main function 43 | # ---------------------------------------------------------------------- 44 | 45 | if __name__ == '__main__': 46 | usage = """usage: %%prog [options] 47 | Used to verify strings files from resources are in a bundle. 48 | This should be used if you use the create script with the --no-copy option.""" 49 | verify_strings(OptionParser(usage=usage).parse_config()[0]) 50 | -------------------------------------------------------------------------------- /Framework/Scripts/lib/scriptlib/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/fadingred/Greenwich/d163573aaf886814e6145c51ff9ebf228fd7a831/Framework/Scripts/lib/scriptlib/__init__.py -------------------------------------------------------------------------------- /Framework/Scripts/lib/scriptlib/config/__init__.py: -------------------------------------------------------------------------------- 1 | # 2 | # Copyright (c) 2013 FadingRed LLC 3 | # 4 | # Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | # documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | # permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | # 9 | # The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | # Software. 11 | # 12 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | # OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | # 17 | 18 | import optparse 19 | import tempfile 20 | import os 21 | 22 | class OptionParser(optparse.OptionParser): 23 | def parse_config(self): 24 | b = 'the project base directory, '\ 25 | 'can be relative to the working directory, '\ 26 | 'default value: $PROJECT_DIR' 27 | r = 'the location for resources, '\ 28 | 'can be relative to the working directory, '\ 29 | 'default value: #base/Resources' 30 | s = 'the location for source code, '\ 31 | 'can be relative to the working directory, '\ 32 | 'default value: #base/Source' 33 | l = 'the base language, '\ 34 | 'default value: $BASE_LANGUAGE if defined, else "en"' 35 | t = 'the location for temporary (scratch) files, '\ 36 | 'can be relative to the working directory, '\ 37 | 'default value: $CONFIGURATION_TEMP_DIR' 38 | p = 'interface builder plugin directory. '\ 39 | 'default value: $IBC_PLUGIN_SEARCH_PATHS' 40 | a = 'Built application path, '\ 41 | 'default value: $BUILT_PRODUCTS_DIR/$WRAPPER_NAME' 42 | r = 'Built application resources folder, '\ 43 | 'default value: $BUILT_PRODUCTS_DIR/$UNLOCALIZED_RESOURCES_FOLDER_PATH' 44 | 45 | self.add_option('-b', '--base', dest='base', default=None, help=b) 46 | self.add_option('-r', '--resources', dest='resources', default=None, help=r) 47 | self.add_option('-s', '--source', dest='source', default=None, help=s) 48 | self.add_option('-l', '--lang', dest='lang', default=None, help=l) 49 | self.add_option('-t', '--tempdir', dest='tempdir', default=None, help=t) 50 | self.add_option('-p', '--plugindir', dest='plugindir', default=None, help=p) 51 | self.add_option('--app', dest='app', default=None, help=a) 52 | self.add_option('--app-resources', dest='app_resources', default=None, help=r) 53 | 54 | options, args = self.parse_args() 55 | 56 | self.remove_option('-b') 57 | self.remove_option('-r') 58 | self.remove_option('-s') 59 | self.remove_option('-l') 60 | self.remove_option('-t') 61 | self.remove_option('-p') 62 | self.remove_option('--app-resources') 63 | 64 | base = options.base or os.environ.get('PROJECT_DIR', '.') 65 | options.resources = options.resources or os.path.join(base, 'Resources') 66 | options.source = options.source or os.path.join(base, 'Source') 67 | options.lang = options.lang or os.environ.get('BASE_LANGUAGE', 'en') 68 | options.tempdir = options.tempdir or os.environ.get('CONFIGURATION_TEMP_DIR') or tempfile.gettempdir() 69 | options.plugindir = options.plugindir or os.environ.get('IBC_PLUGIN_SEARCH_PATHS') 70 | options.app = options.app or os.path.join( 71 | os.environ.get('BUILT_PRODUCTS_DIR', ''), 72 | os.environ.get('WRAPPER_NAME', '')) 73 | options.app_resources = options.app_resources or os.path.join( 74 | os.environ.get('BUILT_PRODUCTS_DIR', ''), 75 | os.environ.get('UNLOCALIZED_RESOURCES_FOLDER_PATH', '')) 76 | return options, args 77 | -------------------------------------------------------------------------------- /Framework/Scripts/lib/scriptlib/i18n/__init__.py: -------------------------------------------------------------------------------- 1 | # 2 | # Copyright (c) 2013 FadingRed LLC 3 | # 4 | # Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | # documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | # permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | # 9 | # The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | # Software. 11 | # 12 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | # OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | # 17 | 18 | from strings import Strings 19 | from document import Xib, Storyboard 20 | -------------------------------------------------------------------------------- /Framework/Scripts/lib/scriptlib/i18n/document.py: -------------------------------------------------------------------------------- 1 | # 2 | # Copyright (c) 2013 FadingRed LLC 3 | # 4 | # Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | # documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | # permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | # 9 | # The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | # Software. 11 | # 12 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | # OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | # 17 | 18 | from util import * 19 | from hashlib import md5 20 | import subprocess 21 | import codecs 22 | import sys 23 | import os 24 | 25 | class InterfaceDocument(object): 26 | def __init__(self, name, config, resources=None, path=None): 27 | self.name = clean_name(name) 28 | self.config = config 29 | self._resources = resources 30 | self._path = path 31 | self._mtime = None 32 | self._gtime = None 33 | 34 | def path(self): 35 | if self._path: return self._path 36 | resources = self._resources or self.config.resources.split(':')[0] 37 | path = os.path.join(resources, '%s.%s' % (self.name, self.__class__.EXTENSION)) 38 | return path 39 | 40 | def modification_time(self): 41 | if self._mtime == None: 42 | try: self._mtime = os.path.getmtime(self.path()) 43 | except OSError: self._mtime = 0 44 | return self._mtime 45 | 46 | def _generation(self): 47 | tempdir = self.config.tempdir 48 | gendir = os.path.join(tempdir, 'strings_generation') 49 | path = os.path.join(gendir, '%s-%s.time' % (self.name, md5(self.path()).hexdigest())) 50 | return path 51 | 52 | def generation_time(self): 53 | if self._gtime == None: 54 | try: self._gtime = os.path.getmtime(self._generation()) 55 | except OSError: self._gtime = 0 56 | return self._gtime 57 | 58 | def _ensure_dir_for_file(self, path): 59 | directory = os.path.dirname(path) 60 | if not os.path.exists(directory): 61 | os.mkdir(directory) 62 | 63 | def generate(self, strings, normalize=True): 64 | """ 65 | Generate strings file in an expected format and update generation time 66 | """ 67 | strings.ensure_dir() 68 | command = ['ibtool'] 69 | if self.config.plugindir: 70 | command += ['--plugin-dir', self.config.plugindir] 71 | command += ['--generate-strings-file', strings.path(), self.path()] 72 | process = subprocess.Popen(command, stdout=subprocess.PIPE, stderr=subprocess.PIPE) 73 | stdout, stderr = process.communicate() 74 | sys.stdout.write(stdout) 75 | sys.stderr.write(stderr) 76 | result = process.wait() 77 | if result != 0: 78 | sys.stderr.write('warning: error generating strings, see prior output for information\n'); 79 | if normalize: strings.normalize() 80 | generation = self._generation() 81 | self._ensure_dir_for_file(generation) 82 | os.system('touch "%s"' % (generation,)) 83 | self._gtime = None 84 | 85 | class Xib(InterfaceDocument): 86 | EXTENSION = 'xib' 87 | 88 | class Storyboard(InterfaceDocument): 89 | EXTENSION = 'storyboard' 90 | -------------------------------------------------------------------------------- /Framework/Scripts/lib/scriptlib/i18n/util.py: -------------------------------------------------------------------------------- 1 | # 2 | # Copyright (c) 2013 FadingRed LLC 3 | # 4 | # Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | # documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | # permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | # 9 | # The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | # Software. 11 | # 12 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | # OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | # 17 | 18 | import os 19 | 20 | def clean_name(name): 21 | 'Strips off .xib/.storyboard extension from a name if needed' 22 | start, ext = os.path.splitext(name) 23 | if ext == '.xib': return start 24 | elif ext == '.storyboard': return start 25 | else: return name 26 | 27 | def clean_lang(lang): 28 | 'Strips off .lproj extension from a language if needed' 29 | start, ext = os.path.splitext(lang) 30 | if ext == '.lproj': return start 31 | else: return lang 32 | -------------------------------------------------------------------------------- /Framework/Scripts/localization: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | # 3 | # Copyright (c) 2013 FadingRed LLC 4 | # 5 | # Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 6 | # documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 7 | # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 8 | # permit persons to whom the Software is furnished to do so, subject to the following conditions: 9 | # 10 | # The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 11 | # Software. 12 | # 13 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 14 | # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 15 | # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 16 | # OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 17 | # 18 | 19 | # setup the environment 20 | ABSPATH=$(cd "${0%/*}" && echo $PWD/${0##*/}) 21 | export SCRIPTDIR=`dirname "${ABSPATH}"` 22 | export PYTHONPATH="$SCRIPTDIR/lib:$PYTHONPATH" 23 | export PATH="/usr/local/share/python:/usr/local/bin:/usr/local/sbin:$PATH" 24 | 25 | # execute the command 26 | COMMAND=$1 27 | shift 28 | "${SCRIPTDIR}/actions/${COMMAND}" "$@" 29 | exit $? 30 | -------------------------------------------------------------------------------- /Framework/Source/Greenwich.pch: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | // Availability 19 | #import 20 | 21 | // System Frameworks 22 | #ifdef __OBJC__ 23 | #ifdef RED_TARGET_MAC 24 | #import 25 | #endif 26 | #ifdef RED_TARGET_IOS 27 | #import 28 | #endif 29 | #endif 30 | 31 | #ifndef __has_feature 32 | #define __has_feature(x) 0 33 | #endif 34 | 35 | #if !__has_feature(objc_arc) 36 | #define __bridge 37 | #define __bridge_transfer 38 | #define __unsafe_unretained 39 | #endif 40 | 41 | #ifndef GREENWICH_DEFAULT_LANGUAGE 42 | #define GREENWICH_DEFAULT_LANGUAGE @"en" 43 | #endif 44 | 45 | #define FRLog NSLog 46 | #define FRLocalizedString(key, comment) (((NSString *(^)(void))^{ \ 47 | NSBundle *__bundle = nil; \ 48 | if (!__bundle) { __bundle = [NSBundle bundleWithIdentifier:@"com.fadingred.Greenwich"]; } \ 49 | if (!__bundle) { __bundle = [NSBundle bundleWithIdentifier:@"com.fadingred.Greenwich" loaded:NULL]; } \ 50 | if (!__bundle) { __bundle = [NSBundle bundleForClass:[(id)self class]]; } \ 51 | return NSLocalizedStringFromTableInBundle(key, nil, __bundle, comment); \ 52 | })()) 53 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRLocalizationManager.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface FRLocalizationManager : NSObject { 19 | } 20 | 21 | + (id)defaultLocalizationManager; 22 | 23 | /*! 24 | \brief Adds hidden help menu items for translation 25 | \details These menu items can be accessed by holding down the option key 26 | while accessing the help menu. This is the preferred way to allow 27 | translators to access the translator window. 28 | */ 29 | - (void)installExtraHelpMenu; 30 | 31 | /*! 32 | \brief Display the translator interface 33 | \details Shows the main translator interface. 34 | */ 35 | - (IBAction)showTranslatorWindow:(id)sender; 36 | 37 | @end 38 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRLocalizationManager.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRLocalizationManager.h" 19 | #import "FRLocalizationWindowController.h" 20 | #import "FRExtraHelpController.h" 21 | #import "FRBundleAdditions.h" 22 | #import "FRTranslationContainer__.h" 23 | 24 | @implementation FRLocalizationManager 25 | 26 | + (id)defaultLocalizationManager { 27 | static FRLocalizationManager *defaultLocalizationManager = nil; 28 | if (defaultLocalizationManager == nil) { 29 | @synchronized(self) { 30 | if (defaultLocalizationManager == nil) { 31 | defaultLocalizationManager = [[self alloc] init]; 32 | } 33 | } 34 | } 35 | return defaultLocalizationManager; 36 | } 37 | 38 | 39 | #pragma mark - 40 | #pragma mark extra help window 41 | // ---------------------------------------------------------------------------------------------------- 42 | // extra help window 43 | // ---------------------------------------------------------------------------------------------------- 44 | 45 | - (void)installExtraHelpMenu { 46 | NSString *appName = [[NSBundle mainBundle] name]; 47 | NSString *title = [NSString stringWithFormat:FRLocalizedString(@"Translate %@", nil), appName]; 48 | NSMenuItem *item = [[NSMenuItem alloc] initWithTitle:title action:@selector(showTranslatorWindow:) keyEquivalent:@""]; 49 | [item setTarget:self]; 50 | [[FRExtraHelpController defaultController] insertItem:item atIndex:0]; 51 | [[FRExtraHelpController defaultController] install]; 52 | } 53 | 54 | 55 | #pragma mark - 56 | #pragma mark actions 57 | // ---------------------------------------------------------------------------------------------------- 58 | // actions 59 | // ---------------------------------------------------------------------------------------------------- 60 | 61 | - (IBAction)showTranslatorWindow:(id)sender { 62 | static FRLocalizationWindowController *controller = nil; 63 | if (!controller) { 64 | controller = [[FRLocalizationWindowController alloc] init]; 65 | [controller addContainer:[FRTranslationContainer containerForApplicationBundle:[NSBundle mainBundle]]]; 66 | } 67 | [controller showWindow:nil]; 68 | } 69 | 70 | @end 71 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRLocalizationWindowController.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @class 19 | FRTranslationContainer; 20 | 21 | 22 | @interface FRLocalizationWindowController : NSWindowController { 23 | NSTimer *saveTimer; 24 | CGFloat initialLanguagePosition; 25 | 26 | IBOutlet NSArrayController *stringsFiles; 27 | IBOutlet NSArrayController *languages; 28 | IBOutlet NSArrayController *containers; 29 | IBOutlet NSTableView *tableView; 30 | IBOutlet NSTextView *textView; 31 | IBOutlet NSPopUpButton *containersPopup; 32 | IBOutlet NSPopUpButton *languagesPopup; 33 | IBOutlet NSButton *sendToDeviceButton; 34 | IBOutlet NSTextField *connectionMessageTextField; 35 | } 36 | 37 | - (void)addContainer:(FRTranslationContainer *)container; 38 | 39 | - (void)setConnectionActive:(BOOL)connectionActive; 40 | - (void)setConnectionMessageString:(NSString *)string; 41 | 42 | - (IBAction)packageStringsFiles:(id)sender; 43 | - (IBAction)sendToDevice:(id)sender; 44 | 45 | @end 46 | 47 | NSString * const FRLocalizationErrorDomain; 48 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRNibAutomaticLocalization.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface NSNib (FRNibAutomaticLocalization) 19 | 20 | @end 21 | 22 | @interface NSObject (FRNibAutomaticLocalization) 23 | 24 | /*! 25 | \brief Similar to awake from nib 26 | \details Classes can implement this to handle setup after localization. This 27 | method will be called on all top level objects as well as the nib 28 | owner after a nib has been loaded. 29 | */ 30 | - (void)awakeFromLocalization; 31 | 32 | @end 33 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRTranslationContainer.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRTranslationContainer__.h" 19 | #import "FRTranslationInfo__.h" 20 | 21 | #import "FRBundleAdditions.h" 22 | #import "FRLocalizationBundleAdditions.h" 23 | #import "FRLocalizationBundleAdditions__.h" 24 | 25 | static NSString * const FRLocalizationIgnoreBundlesKey = @"FRLocalizationIgnoreBundles"; 26 | 27 | @implementation FRTranslationContainer 28 | 29 | @synthesize name; 30 | 31 | + (void)initialize { 32 | if (self == [FRTranslationContainer class]) { 33 | NSArray *ignoreBundles = [NSArray arrayWithObjects:@"Sparkle", nil]; 34 | [[NSUserDefaults standardUserDefaults] registerDefaults: 35 | [NSDictionary dictionaryWithObjectsAndKeys: 36 | ignoreBundles, FRLocalizationIgnoreBundlesKey, nil]]; 37 | } 38 | } 39 | 40 | + (id)containerForApplicationBundle:(NSBundle *)bundle { 41 | FRTranslationContainer *continer = [[self alloc] init]; 42 | continer->applicationBundle = bundle; 43 | return continer; 44 | } 45 | 46 | + (id)containerForSyncedApplicationResources:(NSURL *)aURL { 47 | FRTranslationContainer *continer = [[self alloc] init]; 48 | continer->resourcesURL = aURL; 49 | return continer; 50 | } 51 | 52 | - (NSArray *)translateBundlesForLanguage:(NSString *)language { 53 | NSArray *languages = [NSArray arrayWithObjects:language, nil]; 54 | if (applicationBundle) { 55 | NSMutableArray *result = [NSMutableArray array]; 56 | NSSet *ignoreBundles = [NSSet setWithArray: 57 | [[NSUserDefaults standardUserDefaults] objectForKey:FRLocalizationIgnoreBundlesKey]]; 58 | [applicationBundle enumerateContainedBundlesUsingBlock:^(NSBundle *bundle, BOOL *skipDescendants, BOOL *stop) { 59 | if ([ignoreBundles containsObject:[bundle name]]) { 60 | *skipDescendants = TRUE; 61 | } 62 | else { 63 | NSBundle *translateBundle = 64 | [bundle bundleUsingContentsForTranslationsWithIdentifier:[bundle bundleIdentifier] 65 | updatingStringsForLanguages:languages error:NULL]; 66 | if (translateBundle) { 67 | [result addObject:translateBundle]; 68 | } 69 | } 70 | }]; 71 | return result; 72 | } 73 | else if (resourcesURL) { 74 | NSMutableArray *result = [NSMutableArray array]; 75 | NSFileManager *manager = [NSFileManager defaultManager]; 76 | for (NSString *fileName in [manager contentsOfDirectoryAtPath:[resourcesURL path] error:NULL]) { 77 | if ([fileName isEqualToString:@"Greenwich.details"]) { continue; } 78 | NSBundle *bundle = [NSBundle bundleWithURL:[resourcesURL URLByAppendingPathComponent:fileName]]; 79 | NSBundle *translateBundle = 80 | [bundle bundleUsingContentsForTranslationsWithIdentifier:[[bundle bundlePath] lastPathComponent] 81 | updatingStringsForLanguages:languages error:NULL]; 82 | 83 | if (translateBundle) { 84 | [result addObject:translateBundle]; 85 | } 86 | } 87 | return result; 88 | } 89 | else { return nil; } 90 | } 91 | 92 | - (NSArray *)launagues { 93 | NSMutableSet *languages = [NSMutableSet set]; 94 | if (applicationBundle) { 95 | NSArray *lprojPaths = [applicationBundle pathsForResourcesOfType:@"lproj" inDirectory:nil]; 96 | for (NSString *path in lprojPaths) { 97 | NSString *language = [[path lastPathComponent] stringByDeletingPathExtension]; 98 | if (![language isEqualToString:GREENWICH_DEFAULT_LANGUAGE]) { 99 | [languages addObject:language]; 100 | } 101 | } 102 | } 103 | else if (resourcesURL) { 104 | NSFileManager *manager = [NSFileManager defaultManager]; 105 | for (NSURL *url in [manager enumeratorAtPath:[resourcesURL path]]) { 106 | NSString *baseName = [url lastPathComponent]; 107 | if ([baseName hasSuffix:@".lproj"]) { 108 | [languages addObject:[baseName stringByDeletingPathExtension]]; 109 | 110 | } 111 | } 112 | } 113 | return [languages allObjects]; 114 | } 115 | 116 | - (NSArray *)infoItemsForLanguage:(NSString *)language error:(NSError **)error { 117 | error = error ? error : &(NSError * __autoreleasing){ nil }; 118 | 119 | NSArray *translateBundles = [self translateBundlesForLanguage:language]; 120 | NSMutableArray *content = [NSMutableArray array]; 121 | BOOL success = TRUE; 122 | 123 | for (NSBundle *bundle in translateBundles) { 124 | NSArray *paths = [[NSFileManager defaultManager] subpathsOfDirectoryAtPath:[bundle bundlePath] error:error]; 125 | if (paths) { 126 | for (NSString *path in paths) { 127 | NSString *directoryPath = [path stringByDeletingLastPathComponent]; 128 | NSString *directoryName = [[directoryPath lastPathComponent] stringByDeletingPathExtension]; 129 | NSString *fileExtension = [path pathExtension]; 130 | if ([directoryName isEqualToString:language] && [fileExtension isEqualToString:@"strings"]) { 131 | NSString *infoPath = [[bundle bundlePath] stringByAppendingPathComponent:path]; 132 | FRTranslationInfo *info = [FRTranslationInfo infoWithLanguage:language path:infoPath]; 133 | [content addObject:info]; 134 | } 135 | } 136 | } 137 | else { success = FALSE; break; } 138 | } 139 | 140 | return success ? content : nil; 141 | } 142 | 143 | - (BOOL)isSynced { 144 | return (resourcesURL != nil); 145 | } 146 | 147 | @end 148 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRTranslationContainer__.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface FRTranslationContainer : NSObject { 19 | @private; 20 | NSBundle *applicationBundle; 21 | NSURL *resourcesURL; 22 | } 23 | 24 | /*! 25 | \brief Create a container for an application 26 | \details The container will determine localizable resources 27 | by scanning the application bundle. 28 | */ 29 | + (id)containerForApplicationBundle:(NSBundle *)bundle; 30 | 31 | /*! 32 | \brief Create a container for an application 33 | \details The container will determine localizable resources 34 | by scanning the contents of the directory at the 35 | given URL. 36 | */ 37 | + (id)containerForSyncedApplicationResources:(NSURL *)resourcesURL; 38 | 39 | /*! 40 | \brief The container name 41 | \details Get or set the container name 42 | */ 43 | @property (retain) NSString *name; 44 | 45 | /*! 46 | \brief Accesses the languages 47 | \details This will look up languages for the container. 48 | It could be very slow. 49 | */ 50 | - (NSArray *)launagues; 51 | 52 | /*! 53 | \brief Accesses the languages 54 | \details This will look up or create translation info objects for the given 55 | language in this container. 56 | It could be very slow. 57 | */ 58 | - (NSArray *)infoItemsForLanguage:(NSString *)language error:(NSError **)error; 59 | 60 | /*! 61 | \brief Check if this container is synced 62 | \details This is a synced container if it was created as such. These containers 63 | need the extra abilities in the UI so that they can send info back and 64 | forth to the sync source. 65 | */ 66 | - (BOOL)isSynced; 67 | 68 | @end 69 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRTranslationInfo__.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface FRTranslationInfo : NSObject { 19 | FSEventStreamRef stream; 20 | BOOL untranslatedKnown; 21 | NSUInteger untranslatedCount; 22 | NSString *language; 23 | NSString *path; 24 | NSString *translationPath; 25 | NSString *fileName; 26 | NSString *displayName; 27 | NSString *bundleIdentifier; 28 | NSString *bundleName; 29 | NSMutableDictionary *displayInfo; 30 | } 31 | 32 | + (id)infoWithLanguage:(NSString *)language path:(NSString *)path; 33 | 34 | @property (readonly) NSString *path; 35 | 36 | @property (readonly) NSString *fileName; 37 | @property (readonly) NSString *displayName; 38 | @property (readonly) NSString *bundleIdentifier; 39 | @property (readonly) NSString *bundleName; 40 | @property (readonly) NSString *language; 41 | @property (readonly) NSUInteger untranslatedCount; 42 | 43 | @property (readonly) NSDictionary *displayInfo; 44 | 45 | @end 46 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRUntranslatedCountCell.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface FRUntranslatedCountCell : NSTextFieldCell { 19 | NSUInteger untranslated; 20 | } 21 | 22 | @property NSUInteger untranslated; 23 | 24 | @end 25 | -------------------------------------------------------------------------------- /Framework/Source/Mac/FRUntranslatedCountCell.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRUntranslatedCountCell.h" 19 | 20 | #define UNTRANSLATED_CIRCLE_PADDING 3 21 | #define UNTRANSLATED_CIRCLE_MINWIDTH 24 22 | #define UNTRANSLATED_TEXT_PADDING 12 23 | #define UNTRANSLATED_TEXT_SHRINK 2 24 | 25 | #define UNTRANSLATED_STANDARD_COLOR ([NSColor colorWithCalibratedRed:0.60 green:0.66 blue:0.78 alpha:1.00]) 26 | #define UNTRANSLATED_INACTIVE_COLOR ([NSColor colorWithCalibratedRed:0.67 green:0.67 blue:0.67 alpha:1.00]) 27 | #define UNTRANSLATED_HIGHLIGHT_COLOR ([NSColor whiteColor]) 28 | 29 | static const CGFloat kInactiveOpacity = 0.6; 30 | 31 | 32 | @implementation FRUntranslatedCountCell 33 | 34 | @synthesize untranslated; 35 | 36 | - (NSAttributedString *)untranslatedAttributedString { 37 | if (untranslated) { 38 | NSColor *color = nil; 39 | if ([self interiorBackgroundStyle] == NSBackgroundStyleLowered || 40 | [self interiorBackgroundStyle] == NSBackgroundStyleDark) { 41 | if (![[[self controlView] window] isKeyWindow]) { color = UNTRANSLATED_INACTIVE_COLOR; } 42 | else { color = UNTRANSLATED_STANDARD_COLOR; } 43 | } 44 | else { color = UNTRANSLATED_HIGHLIGHT_COLOR; } 45 | 46 | NSFont *font = [NSFont fontWithName:@"Helvetica-Bold" size:[[self font] pointSize] - UNTRANSLATED_TEXT_SHRINK]; 47 | NSMutableParagraphStyle *style = [[NSParagraphStyle defaultParagraphStyle] mutableCopy]; 48 | [style setAlignment:NSCenterTextAlignment]; 49 | 50 | NSString *string = [NSString stringWithFormat:@"%tu", untranslated]; 51 | NSDictionary *attributes = [NSDictionary dictionaryWithObjectsAndKeys: 52 | font, NSFontAttributeName, 53 | color, NSForegroundColorAttributeName, 54 | style, NSParagraphStyleAttributeName, nil]; 55 | 56 | return [[NSAttributedString alloc] initWithString:string attributes:attributes]; 57 | } 58 | else { return nil; } 59 | } 60 | 61 | - (NSRect)untranslatedRectForString:(NSAttributedString *)string frame:(NSRectPointer)cellFrame { 62 | if (untranslated) { 63 | float width = [string size].width + UNTRANSLATED_TEXT_PADDING * 2; 64 | if (width < UNTRANSLATED_CIRCLE_MINWIDTH) { width = UNTRANSLATED_CIRCLE_MINWIDTH; } 65 | 66 | NSRect rect; 67 | NSDivideRect(*cellFrame, &rect, cellFrame, width, NSMaxXEdge); 68 | return NSInsetRect(rect, UNTRANSLATED_CIRCLE_PADDING, UNTRANSLATED_CIRCLE_PADDING); 69 | } else { return NSZeroRect; } 70 | } 71 | 72 | - (void)drawInteriorWithFrame:(NSRect)cellFrame inView:(NSView *)controlView { 73 | 74 | if (untranslated) { 75 | NSAttributedString *string = [self untranslatedAttributedString]; 76 | NSRect rect = [self untranslatedRectForString:string frame:&cellFrame]; 77 | 78 | NSColor *color = nil; 79 | if ([self interiorBackgroundStyle] == NSBackgroundStyleLowered || 80 | [self interiorBackgroundStyle] == NSBackgroundStyleDark) { color = UNTRANSLATED_HIGHLIGHT_COLOR; } 81 | else if (![[controlView window] isKeyWindow]) { color = UNTRANSLATED_INACTIVE_COLOR; } 82 | else { color = UNTRANSLATED_STANDARD_COLOR; } 83 | 84 | [color set]; 85 | [[NSBezierPath bezierPathWithRoundedRect:rect 86 | xRadius:rect.size.height/2.0 87 | yRadius:rect.size.width] fill]; 88 | 89 | NSRect stringRect = rect; 90 | stringRect.size = NSMakeSize(rect.size.width, [string size].height); 91 | stringRect.origin.x += (rect.size.height - stringRect.size.height) / 2.0; 92 | stringRect.origin.y += (rect.size.width - stringRect.size.width) / 2.0; 93 | [string drawInRect:stringRect]; 94 | } 95 | 96 | [super drawInteriorWithFrame:cellFrame inView:controlView]; 97 | } 98 | 99 | @end 100 | -------------------------------------------------------------------------------- /Framework/Source/Mac/Greenwich.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | #import 21 | #import 22 | #import 23 | -------------------------------------------------------------------------------- /Framework/Source/Mac/Translator/FRNetworkClient.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRConnection.h" 19 | 20 | @protocol 21 | FRNetworkClientDelegate; 22 | 23 | @interface FRNetworkClient : NSObject { 24 | NSNetServiceBrowser *browser; 25 | NSNetService *service; 26 | FRConnection *connection; 27 | } 28 | 29 | @property (assign, nonatomic) id delegate; 30 | @property (readonly, nonatomic) FRConnection *activeConnection; 31 | 32 | @end 33 | 34 | @protocol FRNetworkClientDelegate 35 | @optional; 36 | 37 | /*! 38 | \brief 39 | \details 40 | */ 41 | - (void)networkClient:(FRNetworkClient *)client 42 | didCreateConnection:(FRConnection *)connection; 43 | 44 | /*! 45 | \brief 46 | \details 47 | */ 48 | - (void)networkClient:(FRNetworkClient *)client 49 | receivedMessage:(NSDictionary *)message 50 | fromConnection:(FRConnection *)connection; 51 | 52 | /*! 53 | \brief 54 | \details 55 | */ 56 | - (void)networkClient:(FRNetworkClient *)client 57 | didCloseConnection:(FRConnection *)connection; 58 | 59 | @end 60 | -------------------------------------------------------------------------------- /Framework/Source/Mac/Translator/FRNetworkClient.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRNetworkClient.h" 19 | 20 | @implementation FRNetworkClient 21 | @synthesize delegate; 22 | 23 | - (id)init { 24 | if ((self = [super init])) { 25 | browser = [[NSNetServiceBrowser alloc] init]; 26 | [browser setDelegate:self]; 27 | [browser searchForServicesOfType:@"_greenwich._tcp" inDomain:@""]; 28 | } 29 | return self; 30 | } 31 | 32 | - (void)resolveServiceAndMakeConnection:(NSNetService *)aService { 33 | if (!service) { 34 | service = aService; 35 | [service setDelegate:self]; 36 | [service resolveWithTimeout:5.0]; 37 | } 38 | } 39 | 40 | - (void)startConnectionForService:(NSNetService *)aService { 41 | if (!connection && (aService == service)) { 42 | connection = [[FRConnection alloc] initWithHost:[service hostName] port:[service port]]; 43 | connection.delegate = self; 44 | [connection connect]; 45 | 46 | if ([self.delegate respondsToSelector:@selector(networkClient:didCreateConnection:)]) { 47 | [self.delegate networkClient:self didCreateConnection:connection]; 48 | } 49 | } 50 | } 51 | 52 | 53 | #pragma mark - 54 | #pragma mark properties 55 | // ---------------------------------------------------------------------------------------------------- 56 | // properties 57 | // ---------------------------------------------------------------------------------------------------- 58 | 59 | - (FRConnection *)activeConnection { 60 | return connection; 61 | } 62 | 63 | #pragma mark - 64 | #pragma mark connection delegate 65 | // ---------------------------------------------------------------------------------------------------- 66 | // connection delegate 67 | // ---------------------------------------------------------------------------------------------------- 68 | 69 | - (void)connectionFailed:(FRConnection *)aConnection { 70 | if ([self.delegate respondsToSelector:@selector(networkClient:didCloseConnection:)]) { 71 | [self.delegate networkClient:self didCloseConnection:aConnection]; 72 | } 73 | connection = nil; 74 | service = nil; 75 | } 76 | 77 | - (void)connectionTerminated:(FRConnection *)aConnection { 78 | if ([self.delegate respondsToSelector:@selector(networkClient:didCloseConnection:)]) { 79 | [self.delegate networkClient:self didCloseConnection:aConnection]; 80 | } 81 | connection = nil; 82 | service = nil; 83 | } 84 | 85 | - (void)connection:(FRConnection *)aConnection receivedMessage:(NSDictionary *)message { 86 | if ([self.delegate respondsToSelector:@selector(networkClient:receivedMessage:fromConnection:)]) { 87 | [self.delegate networkClient:self receivedMessage:message fromConnection:aConnection]; 88 | } 89 | } 90 | 91 | 92 | #pragma mark - 93 | #pragma mark net services browser delegate 94 | // ---------------------------------------------------------------------------------------------------- 95 | // net services browser delegate 96 | // ---------------------------------------------------------------------------------------------------- 97 | 98 | - (void)handleError:(NSNumber *)error withBrowser:(NSNetServiceBrowser *)theBrowser { 99 | FRLog(@"An error occurred with service browser, error code = %@", error); 100 | } 101 | 102 | - (void)netServiceBrowserWillSearch:(NSNetServiceBrowser *)theBrowser {} 103 | - (void)netServiceBrowserDidStopSearch:(NSNetServiceBrowser *)theBrowser {} 104 | 105 | - (void)netServiceBrowser:(NSNetServiceBrowser *)theBrowser 106 | didNotSearch:(NSDictionary *)errorDict { 107 | [self handleError:[errorDict objectForKey:NSNetServicesErrorCode] withBrowser:theBrowser]; 108 | } 109 | 110 | - (void)netServiceBrowser:(NSNetServiceBrowser *)theBrowser 111 | didFindService:(NSNetService *)aNetService 112 | moreComing:(BOOL)moreComing { 113 | [self resolveServiceAndMakeConnection:aNetService]; 114 | } 115 | 116 | - (void)netServiceBrowser:(NSNetServiceBrowser *)theBrowser 117 | didRemoveService:(NSNetService *)aNetService 118 | moreComing:(BOOL)moreComing { 119 | if (aNetService == service) { service = nil; } 120 | } 121 | 122 | #pragma mark - 123 | #pragma mark net services delegate 124 | // ---------------------------------------------------------------------------------------------------- 125 | // net services delegate 126 | // ---------------------------------------------------------------------------------------------------- 127 | 128 | - (void)handleError:(NSNumber *)error withService:(NSNetService *)theService { 129 | FRLog(@"An error occurred with service %@.%@.%@, error code = %@", 130 | [theService name], 131 | [theService type], 132 | [theService domain], 133 | error); 134 | } 135 | 136 | - (void)netServiceDidResolveAddress:(NSNetService *)netService { 137 | [self startConnectionForService:netService]; 138 | } 139 | 140 | - (void)netService:(NSNetService *)netService didNotResolve:(NSDictionary *)errorDict { 141 | [self handleError:[errorDict objectForKey:NSNetServicesErrorCode] withService:netService]; 142 | } 143 | 144 | @end 145 | -------------------------------------------------------------------------------- /Framework/Source/Mac/Translator/FRTranslator.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @class 19 | FRNetworkClient; 20 | 21 | @interface FRTranslator : NSObject { 22 | FRNetworkClient *client; 23 | NSMutableSet *knownContainers; 24 | } 25 | 26 | @end 27 | -------------------------------------------------------------------------------- /Framework/Source/Mac/Translator/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | int main(int argc, char *argv[]) 21 | { 22 | return NSApplicationMain(argc, (const char **)argv); 23 | } 24 | -------------------------------------------------------------------------------- /Framework/Source/Shared/FRConnection.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // Copyright (c) 2009 Peter Bakhyryev , ByteClub LLC 4 | // 5 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 6 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 7 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 8 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 9 | // 10 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 11 | // Software. 12 | // 13 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 14 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 15 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 16 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 17 | // 18 | 19 | #import 20 | 21 | @protocol 22 | FRConnectionDelegate; 23 | 24 | @interface FRConnection : NSObject { 25 | CFReadStreamRef readStream; 26 | NSMutableData *readBuffer; 27 | BOOL readOpen; 28 | CFWriteStreamRef writeStream; 29 | NSMutableData *writeBuffer; 30 | BOOL writeOpen; 31 | } 32 | 33 | - (id)initWithSocketHandle:(int)socketHandle; 34 | - (id)initWithHost:(NSString *)host port:(uint16_t)port; 35 | 36 | @property (assign, nonatomic) id delegate; 37 | 38 | - (BOOL)connect; 39 | - (void)close; 40 | 41 | - (void)sendMessage:(NSDictionary *)message; 42 | 43 | @end 44 | 45 | @protocol FRConnectionDelegate 46 | - (void)connectionFailed:(FRConnection *)connection; 47 | - (void)connectionTerminated:(FRConnection *)connection; 48 | - (void)connection:(FRConnection *)connection receivedMessage:(NSDictionary *)message; 49 | @end 50 | -------------------------------------------------------------------------------- /Framework/Source/Shared/FRLocalizationBundleAdditions.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface NSBundle (FRLocalizationBundleAdditions) 19 | 20 | /*! 21 | \brief Get the bundle contining user translations for a given identifier 22 | \details Returns nil if the user has not worked on any translations. 23 | */ 24 | + (id)bundleForTranslationsWithIdentifier:(NSString *)identifier; 25 | 26 | @end 27 | -------------------------------------------------------------------------------- /Framework/Source/Shared/FRLocalizationBundleAdditions__.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface NSBundle (FRLocalizationBundleAdditionsInternal) 19 | 20 | /*! 21 | \brief Get the bundle contining user translations 22 | \details This will create and merge strings files for the given langauges. It will create the bundle 23 | if any launage is specified, but will not create it if no languages are given. Error will be 24 | set when this method returns nil and a real error occurred (not just that the bundle was not 25 | created). 26 | */ 27 | - (id)bundleUsingContentsForTranslationsWithIdentifier:(NSString *)bundleIdentifier 28 | updatingStringsForLanguages:(NSArray *)languages 29 | error:(NSError **)error; 30 | 31 | /*! 32 | \brief Get all sub-bundles of a bundle 33 | \details Search for all sub bundles of a given bundle. Will return an array containing anything that 34 | appears to be a bundle because it has defined a bundle identifier in the proper place. 35 | */ 36 | - (NSArray *)containedBundles; 37 | 38 | /*! 39 | \brief Enumerate all sub-bundles of a bundle 40 | \details Search for all sub bundles of a given bundle. Will call block for anything that 41 | appears to be a bundle because it has defined a bundle identifier in the proper place. 42 | */ 43 | - (void)enumerateContainedBundlesUsingBlock:(void(^)(NSBundle *bundle, BOOL *skipDescendants, BOOL *stop))block; 44 | 45 | @end 46 | -------------------------------------------------------------------------------- /Framework/Source/Shared/FRMessages.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #define safe __unsafe_unretained 19 | 20 | /*! 21 | \brief Authentication message 22 | \details Sent from the Mac app to the iOS server to authenticate. After authentication, 23 | the iOS app will continue by sending a localization resources message. 24 | */ 25 | extern const struct FRAuthenticationMessage { 26 | safe NSString *messageID; 27 | struct { 28 | safe NSString *deviceName; 29 | safe NSString *deviceIdentifier; 30 | } keys; 31 | } FRAuthenticationMessage; 32 | 33 | /*! 34 | \brief Resources message 35 | \details Sent from the iOS server back to the Mac app and includes information on all localizable 36 | strings files. 37 | */ 38 | extern const struct FRLocalizationResourcesMessage { 39 | safe NSString *messageID; 40 | struct { 41 | safe NSString *applicationIdentifier; 42 | safe NSString *applicationName; 43 | safe NSString *resources; 44 | struct { 45 | safe NSString *bundleIdentifier; 46 | safe NSString *language; 47 | safe NSString *name; 48 | safe NSString *data; 49 | } resource; 50 | } keys; 51 | } FRLocalizationResourcesMessage; 52 | 53 | /*! 54 | \brief Changes message 55 | \details Sent from the Mac client app back to the iOS server indicating the localizations 56 | that the user has performed. 57 | */ 58 | extern const struct FRLocalizationChangesMessage { 59 | safe NSString *messageID; 60 | struct { 61 | safe NSString *resources; 62 | struct { 63 | safe NSString *bundleIdentifier; 64 | safe NSString *language; 65 | safe NSString *name; 66 | safe NSString *data; 67 | } resource; 68 | } keys; 69 | } FRLocalizationChangesMessage; 70 | 71 | #undef safe 72 | -------------------------------------------------------------------------------- /Framework/Source/Shared/FRMessages.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRMessages.h" 19 | 20 | const struct FRAuthenticationMessage FRAuthenticationMessage = { 21 | .messageID = @"FRAuthenticationMessageID", 22 | .keys = { 23 | .deviceName = @"deviceName", 24 | .deviceIdentifier = @"deviceIdentifier", 25 | } 26 | }; 27 | 28 | const struct FRLocalizationResourcesMessage FRLocalizationResourcesMessage = { 29 | .messageID = @"FRLocalizationResourcesMessageID", 30 | .keys = { 31 | .applicationIdentifier = @"applicationIdentifier", 32 | .applicationName = @"applicationName", 33 | .resources = @"resources", 34 | .resource = { 35 | .bundleIdentifier = @"bundleIdentifier", 36 | .language = @"language", 37 | .name = @"name", 38 | .data = @"data", 39 | }, 40 | }, 41 | }; 42 | 43 | const struct FRLocalizationChangesMessage FRLocalizationChangesMessage = { 44 | .messageID = @"FRLocalizationChangesMessageID", 45 | .keys = { 46 | .resources = @"resources", 47 | .resource = { 48 | .bundleIdentifier = @"bundleIdentifier", 49 | .language = @"language", 50 | .name = @"name", 51 | .data = @"data", 52 | }, 53 | }, 54 | }; 55 | -------------------------------------------------------------------------------- /Framework/Source/Shared/FRStrings.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | enum { 21 | FRStringsFormatQuoted, 22 | FRStringsFormatPropertyList, 23 | }; 24 | typedef NSUInteger FRStringsFormat; 25 | 26 | @interface FRStrings : NSObject { 27 | NSMutableDictionary *strings; 28 | NSMutableArray *order; 29 | } 30 | 31 | /*! 32 | \brief Create a new strings file 33 | \details Create with the contents of a path 34 | */ 35 | - (id)initWithContentsOfFile:(NSString *)path usedFormat:(FRStringsFormat *)format error:(NSError **)error; 36 | 37 | /*! 38 | \brief Create a new strings file 39 | \details Create with the given data 40 | */ 41 | - (id)initWithData:(NSData *)data usedFormat:(FRStringsFormat *)format error:(NSError **)error; 42 | 43 | /*! 44 | \brief Write the strings file 45 | \details Write the stings file in the given format 46 | */ 47 | - (BOOL)writeToFile:(NSString *)path format:(FRStringsFormat)format error:(NSError **)error; 48 | 49 | /*! 50 | \brief Get the contents in a given format 51 | \details Gets the contents in the given format. Each format will return different type of object: 52 | - FRStringsFormatQuoted: NSString 53 | - FRStringsFormatPropertyList: NSDictionary 54 | */ 55 | - (id)contentsInFormat:(FRStringsFormat)format; 56 | 57 | /*! 58 | \brief Enumerate the strings 59 | \details Enumerate the strings (in order if possible) 60 | */ 61 | - (NSEnumerator *)stringsEnumerator; 62 | 63 | /*! 64 | \brief Count of strings 65 | \details Count of strings 66 | */ 67 | - (NSUInteger)count; 68 | 69 | /*! 70 | \brief String at index 71 | \details String at index 72 | */ 73 | - (NSString *)stringAtIndex:(NSUInteger)index; 74 | 75 | /*! 76 | \brief Comments for a string 77 | \details Comments for a string 78 | */ 79 | - (NSArray *)commentsForString:(NSString *)string; 80 | 81 | /*! 82 | \brief Set comments for a string 83 | \details Set comments for a string 84 | */ 85 | - (void)setComments:(NSArray *)comment forString:(NSString *)string; 86 | 87 | /*! 88 | \brief Translation for a string 89 | \details Translation for a string 90 | */ 91 | - (NSString *)translationForString:(NSString *)string; 92 | 93 | /*! 94 | \brief Set translation for a string 95 | \details Set translation for a string 96 | */ 97 | - (void)setTranslation:(NSString *)translation forString:(NSString *)string; 98 | 99 | @end 100 | -------------------------------------------------------------------------------- /Framework/Source/iOS/FRLocalizationManager.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @class 19 | FRNetworkServer; 20 | 21 | @interface FRLocalizationManager : NSObject { 22 | FRNetworkServer *server; 23 | NSString *generatedAuthorizationCode; 24 | } 25 | 26 | + (id)defaultLocalizationManager; 27 | 28 | @end 29 | -------------------------------------------------------------------------------- /Framework/Source/iOS/FRNetworkServer.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | #import 20 | 21 | #import "FRNetworkServer__.h" 22 | 23 | static void callback(CFSocketRef socket, CFSocketCallBackType type, CFDataRef address, const void *data, void *info); 24 | 25 | @interface FRNetworkServer () 26 | - (BOOL)setupServer; 27 | @end 28 | 29 | @implementation FRNetworkServer 30 | @synthesize delegate; 31 | 32 | - (id)init { 33 | if ((self = [super init])) { 34 | [self performSelector:@selector(setupServer) withObject:nil afterDelay:0]; 35 | } 36 | return self; 37 | } 38 | 39 | - (BOOL)setupServer { 40 | BOOL success = TRUE; 41 | uint16_t port = 0; 42 | CFSocketRef socket = NULL; 43 | 44 | // create socket object 45 | if (success) { 46 | CFSocketContext context = {0, (__bridge void *)self, NULL, NULL, NULL}; 47 | socket = CFSocketCreate(kCFAllocatorDefault, PF_INET, SOCK_STREAM, IPPROTO_TCP, kCFSocketAcceptCallBack, 48 | (CFSocketCallBack)&callback, &context); 49 | if (!socket) { success = FALSE; } 50 | } 51 | 52 | // setup listening socket 53 | if (success) { 54 | setsockopt(CFSocketGetNative(socket), SOL_SOCKET, SO_REUSEADDR, (void *)&(int){0}, sizeof(int)); 55 | 56 | struct sockaddr_in address = { 57 | .sin_len = sizeof(struct sockaddr_in), 58 | .sin_family = AF_INET, 59 | .sin_port = 0, 60 | .sin_addr.s_addr = htonl(INADDR_ANY), 61 | }; 62 | 63 | NSData *data = [NSData dataWithBytes:&address length:sizeof(address)]; 64 | if (CFSocketSetAddress(socket, (__bridge CFDataRef)data) != kCFSocketSuccess) { 65 | success = FALSE; 66 | } 67 | } 68 | 69 | // get assigned port 70 | if (success) { 71 | NSData *data = (__bridge_transfer NSData *)CFSocketCopyAddress(socket); 72 | struct sockaddr_in address; 73 | memcpy(&address, [data bytes], [data length]); 74 | port = ntohs(address.sin_port); 75 | } 76 | 77 | // schedule with run loop 78 | if (success) { 79 | CFRunLoopRef currentRunLoop = CFRunLoopGetCurrent(); 80 | CFRunLoopSourceRef runLoopSource = CFSocketCreateRunLoopSource(kCFAllocatorDefault, socket, 0); 81 | CFRunLoopAddSource(currentRunLoop, runLoopSource, kCFRunLoopCommonModes); 82 | CFRelease(runLoopSource); 83 | } 84 | 85 | // setup service 86 | if (success) { 87 | service = [[NSNetService alloc] initWithDomain:@"" type:@"_greenwich._tcp" name:@"Greenwich" port:port]; 88 | if (!service) { success = FALSE; } 89 | } 90 | 91 | // publish service 92 | if (success) { 93 | [service setDelegate:self]; 94 | [service publish]; 95 | 96 | } 97 | 98 | // cleanup 99 | if (socket != NULL) { 100 | CFRelease(socket); 101 | socket = NULL; 102 | } 103 | 104 | return success; 105 | } 106 | 107 | static void callback(CFSocketRef socket, CFSocketCallBackType type, CFDataRef address, const void *data, void *info) { 108 | if (type != kCFSocketAcceptCallBack) { return; } 109 | 110 | FRNetworkServer *server = (__bridge FRNetworkServer *)info; 111 | int sock = *(CFSocketNativeHandle *)data; 112 | 113 | if (!server->connection) { 114 | server->connection = nil; 115 | server->connection = [[FRConnection alloc] initWithSocketHandle:sock]; 116 | server->connection.delegate = server; 117 | 118 | if (server->connection) { [server->connection connect]; } 119 | else { close(sock); } 120 | 121 | if ([server.delegate respondsToSelector:@selector(networkServer:didCreateConnection:)]) { 122 | [server.delegate networkServer:server didCreateConnection:server->connection]; 123 | } 124 | } 125 | else { close(sock); } 126 | } 127 | 128 | #pragma mark - 129 | #pragma mark connection delegate 130 | // ---------------------------------------------------------------------------------------------------- 131 | // connection delegate 132 | // ---------------------------------------------------------------------------------------------------- 133 | 134 | - (void)connectionFailed:(FRConnection *)aConnection { 135 | if ([self.delegate respondsToSelector:@selector(networkServer:didCloseConnection:)]) { 136 | [self.delegate networkServer:self didCloseConnection:aConnection]; 137 | } 138 | connection = nil; 139 | } 140 | 141 | - (void)connectionTerminated:(FRConnection *)aConnection { 142 | if ([self.delegate respondsToSelector:@selector(networkServer:didCloseConnection:)]) { 143 | [self.delegate networkServer:self didCloseConnection:aConnection]; 144 | } 145 | connection = nil; 146 | } 147 | 148 | - (void)connection:(FRConnection *)aConnection receivedMessage:(NSDictionary *)message { 149 | if ([self.delegate respondsToSelector:@selector(networkServer:receivedMessage:fromConnection:)]) { 150 | [self.delegate networkServer:self 151 | receivedMessage:message 152 | fromConnection:aConnection]; 153 | } 154 | } 155 | 156 | #pragma mark - 157 | #pragma mark net services delegate 158 | // ---------------------------------------------------------------------------------------------------- 159 | // net services delegate 160 | // ---------------------------------------------------------------------------------------------------- 161 | 162 | - (void)handleError:(NSNumber *)error withService:(NSNetService *)theService { 163 | FRLog(@"An error occurred with service %@.%@.%@, error code = %@", 164 | [theService name], 165 | [theService type], 166 | [theService domain], 167 | error); 168 | } 169 | 170 | @end 171 | -------------------------------------------------------------------------------- /Framework/Source/iOS/FRNetworkServer__.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRConnection.h" 19 | 20 | @protocol 21 | FRNetworkServerDelegate; 22 | 23 | @interface FRNetworkServer : NSObject { 24 | NSNetService *service; 25 | FRConnection *connection; 26 | } 27 | 28 | @property (assign, nonatomic) id delegate; 29 | 30 | @end 31 | 32 | @protocol FRNetworkServerDelegate 33 | @optional; 34 | 35 | /*! 36 | \brief 37 | \details 38 | */ 39 | - (void)networkServer:(FRNetworkServer *)server 40 | didCreateConnection:(FRConnection *)connection; 41 | 42 | /*! 43 | \brief 44 | \details 45 | */ 46 | - (void)networkServer:(FRNetworkServer *)server 47 | receivedMessage:(NSDictionary *)message 48 | fromConnection:(FRConnection *)connection; 49 | 50 | /*! 51 | \brief 52 | \details 53 | */ 54 | - (void)networkServer:(FRNetworkServer *)server 55 | didCloseConnection:(FRConnection *)connection; 56 | 57 | @end 58 | -------------------------------------------------------------------------------- /Framework/Source/iOS/FRUIAutomaticLocalization.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface UINib (FRNibAutomaticLocalization) 19 | 20 | @end 21 | 22 | @interface UIStoryboard (FRStoryboardAutomaticLocalization) 23 | 24 | @end 25 | 26 | @interface NSObject (FRNibAutomaticLocalization) 27 | 28 | /*! 29 | \brief Similar to view did load 30 | \details Classes can implement this to handle setup after localization. This 31 | method will be called on all top level objects as well as the nib 32 | owner after a nib has been loaded. You must call the super class 33 | implementation at some point during your implementation. 34 | */ 35 | - (void)awakeFromLocalization; 36 | 37 | @end 38 | -------------------------------------------------------------------------------- /Framework/Source/iOS/Greenwich.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2013 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | #import 20 | #import 21 | -------------------------------------------------------------------------------- /Framework/Source/iOS/Greenwich.pch: -------------------------------------------------------------------------------- 1 | // 2 | // Prefix header for all source files of the 'Greenwich (iOS)' target in the 'Greenwich (iOS)' project 3 | // 4 | 5 | #ifdef __OBJC__ 6 | #import 7 | #endif 8 | -------------------------------------------------------------------------------- /License: -------------------------------------------------------------------------------- 1 | Copyright (c) 2012 FadingRed LLC 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 4 | documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 5 | rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 6 | permit persons to whom the Software is furnished to do so, subject to the following conditions: 7 | 8 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 9 | Software. 10 | 11 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 12 | WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 13 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 14 | OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 15 | -------------------------------------------------------------------------------- /Readme.md: -------------------------------------------------------------------------------- 1 | # Greenwich 2 | 3 | Greenwich is a framework for easily allowing users to translate Cocoa applications. 4 | [Download now!](http://fadingred.github.com/greenwich/files/greenwich.tbz) 5 | 6 | ## Overview 7 | 8 | Greenwich allows users to translate your Cocoa applications quickly and conveniently using a 9 | simple interface that is packaged directly within the application: 10 | 11 | ![Translator](http://fadingred.github.com/greenwich/media/images/translator.png) 12 | 13 | As a translator works through the strings in your application, she can simply relaunch the 14 | application at any time to see the changes directly in the app. This significantly improves 15 | the feedback loop for translators and will result in better, faster translations. 16 | 17 | Greenwich has been built both for translators and for developers. As a developer, you'll no 18 | longer have to think about localization again. Greenwich has scripts that integrate directly 19 | into your build process — strings will be extracted from both your xib files and your 20 | source code as you go. Set it up once, and forget about it. Your strings files will always be 21 | kept up to date, and Greenwich will do most of the heavy lifting for you. Enough talk, let's 22 | get this thing set up already! 23 | 24 | ## Setup & Usage 25 | 26 | Setup and usage for [iOS](http://fadingred.github.com/greenwich/setup/#ios) and 27 | [Mac](http://fadingred.github.com/greenwich/setup/#mac) are documented on the 28 | [setup page](http://fadingred.github.com/greenwich/setup/). 29 | 30 | ## Compatibility 31 | 32 | Greenwich is currently compatible with Cocoa applications running on Mac OS X 10.6+ on x86_64 and iOS 5.0+. For 33 | Mac OS X applications targeting i386, please use a 1.x version of Greenwich. 34 | 35 | 36 | ## License 37 | 38 | Greenwich is distributed under the [MIT License](http://www.opensource.org/licenses/mit-license.php). Enjoy! 39 | -------------------------------------------------------------------------------- /iOS Example/Example.pch: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | #ifndef __IPHONE_5_0 21 | #warning "This project uses features only available in iOS SDK 5.0 and later." 22 | #endif 23 | 24 | #ifdef __OBJC__ 25 | #import 26 | #import 27 | #endif 28 | 29 | // using a custom localized string method to show how Greenwich handles this 30 | #define MyLocalizedString NSLocalizedString 31 | -------------------------------------------------------------------------------- /iOS Example/Example.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleDisplayName 8 | ${PRODUCT_NAME} 9 | CFBundleExecutable 10 | ${EXECUTABLE_NAME} 11 | CFBundleIconFiles 12 | 13 | CFBundleIdentifier 14 | com.fadingred.greenwich.ios.Example 15 | CFBundleInfoDictionaryVersion 16 | 6.0 17 | CFBundleName 18 | ${PRODUCT_NAME} 19 | CFBundlePackageType 20 | APPL 21 | CFBundleShortVersionString 22 | 1.0 23 | CFBundleSignature 24 | ???? 25 | CFBundleVersion 26 | 1.0 27 | LSRequiresIPhoneOS 28 | 29 | UIMainStoryboardFile 30 | Example 31 | UIMainStoryboardFile~ipad 32 | ExamplePad 33 | UIRequiredDeviceCapabilities 34 | 35 | armv7 36 | 37 | UISupportedInterfaceOrientations 38 | 39 | UIInterfaceOrientationPortrait 40 | UIInterfaceOrientationLandscapeLeft 41 | UIInterfaceOrientationLandscapeRight 42 | 43 | UISupportedInterfaceOrientations~ipad 44 | 45 | UIInterfaceOrientationPortrait 46 | UIInterfaceOrientationPortraitUpsideDown 47 | UIInterfaceOrientationLandscapeLeft 48 | UIInterfaceOrientationLandscapeRight 49 | 50 | 51 | 52 | -------------------------------------------------------------------------------- /iOS Example/Example.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 23 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | -------------------------------------------------------------------------------- /iOS Example/Example.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /iOS Example/Example.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEWorkspaceSharedSettings_AutocreateContextsIfNeeded 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /iOS Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 24 | 25 | 30 | 31 | 32 | 33 | 39 | 40 | 41 | 42 | 51 | 52 | 58 | 59 | 60 | 61 | 65 | 66 | 67 | 68 | 69 | 70 | 76 | 77 | 83 | 84 | 85 | 86 | 88 | 89 | 92 | 93 | 94 | -------------------------------------------------------------------------------- /iOS Example/Example.xcodeproj/xcshareddata/xcschemes/Translator.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 4 | 7 | 8 | 14 | 20 | 21 | 22 | 23 | 24 | 29 | 30 | 31 | 32 | 38 | 39 | 40 | 41 | 50 | 51 | 57 | 58 | 59 | 60 | 61 | 62 | 68 | 69 | 75 | 76 | 77 | 78 | 80 | 81 | 84 | 85 | 86 | -------------------------------------------------------------------------------- /iOS Example/ExamplePad.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 25 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | -------------------------------------------------------------------------------- /iOS Example/FRAppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface FRAppDelegate : UIResponder 19 | 20 | @property (strong, nonatomic) UIWindow *window; 21 | 22 | @end 23 | -------------------------------------------------------------------------------- /iOS Example/FRAppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRAppDelegate.h" 19 | 20 | @implementation FRAppDelegate 21 | 22 | @synthesize window = _window; 23 | 24 | - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { 25 | [FRLocalizationManager defaultLocalizationManager]; 26 | 27 | return YES; 28 | } 29 | 30 | @end 31 | -------------------------------------------------------------------------------- /iOS Example/FRMainViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | @interface FRMainViewController : UIViewController 19 | 20 | @property (retain, nonatomic) IBOutlet UILabel *codeLabel; 21 | @property (retain, nonatomic) IBOutlet UILabel *designLabel; 22 | 23 | @end 24 | -------------------------------------------------------------------------------- /iOS Example/FRMainViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import "FRMainViewController.h" 19 | 20 | @implementation FRMainViewController 21 | 22 | @synthesize codeLabel; 23 | @synthesize designLabel; 24 | 25 | - (void)viewDidLoad { 26 | [super viewDidLoad]; 27 | [self.codeLabel setText:MyLocalizedString(@"Code string", nil)]; 28 | } 29 | 30 | - (void)awakeFromLocalization { 31 | [super awakeFromLocalization]; 32 | [self.designLabel sizeToFit]; 33 | } 34 | 35 | - (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation 36 | { 37 | return UIInterfaceOrientationPortrait == toInterfaceOrientation || UIUserInterfaceIdiomPad == [[UIDevice currentDevice] userInterfaceIdiom]; 38 | } 39 | 40 | @end 41 | -------------------------------------------------------------------------------- /iOS Example/de.lproj/Example.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Design String" = "Design String"; 3 | 4 | -------------------------------------------------------------------------------- /iOS Example/de.lproj/ExamplePad.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Design String" = "Design String"; 3 | 4 | -------------------------------------------------------------------------------- /iOS Example/de.lproj/Localizable.strings: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/fadingred/Greenwich/d163573aaf886814e6145c51ff9ebf228fd7a831/iOS Example/de.lproj/Localizable.strings -------------------------------------------------------------------------------- /iOS Example/en.lproj/Example.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Design String" = "Design String"; 3 | 4 | -------------------------------------------------------------------------------- /iOS Example/en.lproj/ExamplePad.strings: -------------------------------------------------------------------------------- 1 | /* No comment provided by engineer. */ 2 | "Design String" = "Design String"; 3 | 4 | -------------------------------------------------------------------------------- /iOS Example/en.lproj/Localizable.strings: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/fadingred/Greenwich/d163573aaf886814e6145c51ff9ebf228fd7a831/iOS Example/en.lproj/Localizable.strings -------------------------------------------------------------------------------- /iOS Example/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) 2012 FadingRed LLC 3 | // 4 | // Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 5 | // documentation files (the "Software"), to deal in the Software without restriction, including without limitation the 6 | // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to 7 | // permit persons to whom the Software is furnished to do so, subject to the following conditions: 8 | // 9 | // The above copyright notice and this permission notice shall be included in all copies or substantial portions of the 10 | // Software. 11 | // 12 | // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 13 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 14 | // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 15 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | // 17 | 18 | #import 19 | 20 | #import "FRAppDelegate.h" 21 | 22 | int main(int argc, char *argv[]) 23 | { 24 | @autoreleasepool { 25 | return UIApplicationMain(argc, argv, nil, NSStringFromClass([FRAppDelegate class])); 26 | } 27 | } 28 | --------------------------------------------------------------------------------