I added a user defined settings in project build settings:
How can I access the value of my_name in my iOS project swift code?
You are misunderstanding the User Defined setting.
If you ant to provide specific value by environment you just use :
for Swift :
Other Swift Flag : -D my_value
For Objc :
preprocessor macro : my_value=1
Then in your code you can do
#if my_value
some code here
#endif
Related
I'm including a Swift source in my CocoaPods library for the first time. For me to get the project to compile, I need to import the generated Swift header into my Objective-C source. This takes two different forms, depending on whether the project is being built as a static library or a dynamic framework:
#ifdef BUILT_AS_FRAMEWORK
#import <UnzipKit/UnzipKit-Swift.h>
#else
// Used when built as a static library
#import "UnzipKit-Swift.h"
#endif
I'm defining BUILT_AS_FRAMEWORK in my Xcode project for development time, but when I lint the library as a dynamic framework, and because I haven't defined that flag in the Podspec, it attempts to resolve the second import, and can't find it.
Is there a way I can define the BUILT_AS_FRAMEWORK preprocessor macro, but only if the consuming Podfile doesn't build it as a static library?
I created issue #9101 in the CocoaPods project for this question.
I was able to use an Xcode environment variable (PACKAGE_TYPE) in conjunction with a pre-compilation Run Script build phase to dynamically produce a header to import, which in turn makes the correct generated Swift Header import.
generate-swift-import-header.sh
#!/bin/sh
[[ "${PACKAGE_TYPE}" = "com.apple.package-type.wrapper.framework" ]] \
&& SWIFTIMPORT="<${PRODUCT_MODULE_NAME}/${PRODUCT_MODULE_NAME}-Swift.h>" \
|| SWIFTIMPORT="\"${PRODUCT_MODULE_NAME}-Swift.h\""
if [ -z "$PODS_TARGET_SRCROOT" ]; then
PODS_TARGET_SRCROOT=${SOURCE_ROOT}
echo "Building in Xcode instead of CocoaPods. Overriding PODS_TARGET_SRCROOT with SOURCE_ROOT"
fi
_Import_text="
#ifndef GeneratedSwiftImport_h
#define GeneratedSwiftImport_h
#import ${SWIFTIMPORT}
#endif /* GeneratedSwiftImport_h */
"
echo "$_Import_text" > ${PODS_TARGET_SRCROOT}/Source/GeneratedSwiftImport.h
Podspec update
s.script_phases = { :name => "Generate UnzipKit Swift Header",
:script => "\"${PODS_TARGET_SRCROOT}\"/Scripts/generate-swift-import-header.sh",
:execution_position => :before_compile }
Library source
I replaced my conditional import with this:
#import "GeneratedSwiftImport.h"
I also ignored the GeneratedSwiftImport.h file in Git.
Because NSLog statements slow down apps, it seems advisable to remove them prior to release. A number of older answers on SO going back to 2010 suggest putting some code in the pch file such as:
#ifndef DEBUG
#define NSLog(...);
#endif
However, Xcode no longer automatically creates a pch file. I gather it is possible to manually create a pch file but this seems like a bit of a kludge. Is manually creating a pch file and adding the above code to it still the recommended way to comment out NSLog statements prior to release or is there a more modern approach?
All the old answers I found (including adding a PCH file) didn't work for Swift. Here's what finally worked for me:
Define the DEBUG flag by adding "-D DEBUG" to "Other Swift Flags" in the build settings.
Add the following global code (I just put it in a file named Globals.swift):
#if !DEBUG
public func NSLog(_ format: String, _ args: CVarArg...) {
}
public func print(_ items: Any..., separator: String = " ", terminator: String = "\n") {
}
#endif
It is still possible to create a pre-compiled header, however this is discouraged, at least by default. To do this, edit the build settings for your target, and define a path to a Prefix Header.
Use a Logging Library
Perhaps you can use a logging library, like CocoaLumberJack, or here is a very simple one, that nonetheless works well.
I am integrating crashlytics for android and ios apps for android using build flavor we can give separate organization key but in ios debug and release scheme i need to run different script because i need to provide different keys to that project.
script
"${PROJECT_DIR}/Fabric.framework/run" 834343231341432432432432432408497cdbfa13ceb728b296e1c595557bb8c389a33693f150f
There's many options for build confg in iOS as well depending on your project.
You could use configuration files :
xcconfig
1 : Create a new xcconfig file ( base.xcconfig) with the following :
KEY = YOUR_DEBUG_KEY
2 : Create a release config file ( release.xcconfig) :
KEY = YOUR_LIVE_KEY
3 : Set the newly created files in project settings :
4 : In the Build Phase :
"${PROJECT_DIR}/Fabric.framework/run" ${KEY}
Another simple way to do it ( if something needs to be changed in the code itself) :
#ifdef DEBUG
// debug config
#else
// release config
#endif
You can edit your sheme to add a script for each configuration.
EDIT: You click on your scheme -> Edit Scheme... -> Click on Build Arrow -> Pre/Post actions -> + -> New Run Script Action
The title says it all. I've searched in the build settings for SWIFT_MODULE_NAME, and nothing came up. I've also searched online, and there are references to this name, but there is no information on how it is defined. Furthermore, I couldn't find any mention of SWIFT_MODULE_NAME in the Apple Docs.
I do know this: it is used in the "Objective-C Generated Interface Header Name" build setting, and can be viewed by double-clicking on the settings value:
$(SWIFT_MODULE_NAME)-Swift.h
It is used to bridge the gap between Objective-C and Swift, and appears only for projects that include Swift files, (along with Objective-C files I presume). As of this posting, Xcode 7.3 is the latest and greatest.
But, where is this value defined, and how do I modify it?
The module name comes from the Product Module Name build setting:
The SWIFT_MODULE_NAME setting is apparently hidden, but you can see its derivation by looking at Xcode.app/Contents/PlugIns/Xcode3Core.ideplugin/Contents/SharedSupport/Developer/Library/Xcode/Plug-ins/XCLanguageSupport.xcplugin/Contents/Resources/Swift.xcspec:
...
{
Name = "SWIFT_MODULE_NAME";
Type = String;
DefaultValue = "$(PRODUCT_MODULE_NAME)";
CommandLineArgs = (
"-module-name",
"$(value)",
);
},
...
SWIFT_MODULE_NAME, PRODUCT_MODULE_NAME, PRODUCT_NAME, EXECUTABLE_NAME
Default values:
EXECUTABLE_NAME = $EXECUTABLE_PREFIX$PRODUCT_NAME$EXECUTABLE_SUFFIX
SWIFT_OBJC_INTERFACE_HEADER_NAME = $(SWIFT_MODULE_NAME)
SWIFT_MODULE_NAME = $(PRODUCT_MODULE_NAME)
PRODUCT_MODULE_NAME = $(PRODUCT_NAME:c99extidentifier)
PRODUCT_NAME = $(TARGET_NAME:c99extidentifier)
Observation:
SWIFT_MODULE_NAME == PRODUCT_MODULE_NAME
c99extidentifier
Xcode is able to substitute a value of variable
c99extidentifier identifier which supports extended characters from C99
//for example
PRODUCT_NAME = My Framework
PRODUCT_MODULE_NAME = $(PRODUCT_NAME:c99extidentifier) = My_Framework
EXECUTABLE_NAME name of binary
Product Module Name(PRODUCT_MODULE_NAME) determines how the import statement will look like. For example when you are creating a Library or a Framework.
Using:
//Objective-C
#import module_name;
//Swift
import module_name
Product Name(PRODUCT_NAME) determines the name of binary. E.g. MyFramework.framework
[TARGET_NAME]
Rule is:
SWIFT_MODULE_NAME should equal to PRODUCT_MODULE_NAME
[Custom .modulemap]
Go to build Settings and click + next to 'Levels'.
See :
replace NEW_SETTING as SWIFT_MODULE_NAME for the name of the setting, and whatever is the module name for .h file (No spaces, please) goes on the right.
Have you checked out this doc: developer.apple.com/library/ios/documentation/Swift/Conceptual/… ? usually it is your product name. You can set change the value in "Product Bundle Identifier" in Build Settings. Note you can not override a product name in a Framework
See the screenshot:
I am using Xcode 7.3, and I am getting an "Ambiguous expansion of macro" warning, for a macro which was defined in Foundation, but which I have undefined and re-defined in my prefix file. I have modules enabled.
To reproduce:
Set "Enable Modules (C and Objective-C)" to Yes in build settings
Use the following prefix file:
#import <Foundation/Foundation.h>
#undef assert
#define assert(e) NSLog(#"hi") // implementation is not important
Use the following main source file:
int main() {
assert(42);
return 0;
}
Then build in Xcode.
It shows an "Ambiguous expansion of macro 'assert'" warning on the line in the source file that uses the "assert" macro. The "Expanding this definition of 'assert'" points to the definition from the system header, not my redefinition. The "Other definition of 'assert'" points to the definition in my prefix file.
This warning does not happen when modules is disabled.
This is a bug in Xcode; we'd appreciate if you could file a bug report at https://bugreport.apple.com and leave the bug # in a comment here. Your options for working around this bug in the meantime are:
You could use a different name than "assert" for this macro.
You could set the GCC_PRECOMPILE_PREFIX_HEADER build setting to NO, since PCH don’t provide a lot of benefit when you already have modules. The prefix header will still work, it just won’t be turned into a PCH.
You could turn off modules.