ALTERNATYWY:
Łatwe kopiowanie / wklejanie najnowszej wersji (ale instrukcje instalacji mogą ulec zmianie - patrz poniżej!)
Biblioteka Karla wymaga znacznie więcej wysiłku, aby skonfigurować, ale o wiele ładniejsze długoterminowe rozwiązanie (konwertuje bibliotekę do frameworka).
Skorzystaj z tego, a następnie popraw go, aby dodać obsługę kompilacji archiwów - patrz komentarz @ Frederika na temat zmian, których używa, aby ładnie działał w trybie archiwizacji.
OSTATNIE ZMIANY: 1. Dodano obsługę systemu iOS 10.x (przy zachowaniu obsługi starszych platform)
Informacje o tym, jak używać tego skryptu z projektem osadzonym w innym projekcie (chociaż zdecydowanie nie polecam tego robić, nigdy - Apple ma kilka błędów show-stopper w Xcode, jeśli osadzasz projekty między sobą, z Xcode 3.x do Xcode 4.6.x)
Dodatkowy skrypt pozwalający na automatyczne dołączanie pakietów (tj. Dołączanie plików PNG, PLIST itp. Z biblioteki!) - patrz poniżej (przewiń w dół)
teraz obsługuje iPhone5 (używając obejścia Apple do błędów w lipo). UWAGA: instrukcje instalacji uległy zmianie (prawdopodobnie mogę to uprościć, zmieniając skrypt w przyszłości, ale nie chcę teraz ryzykować)
Sekcja „kopiuj nagłówki” uwzględnia teraz ustawienie kompilacji dla lokalizacji nagłówków publicznych (dzięki uprzejmości Frederika Wallnera)
Dodano wyraźne ustawienie SYMROOT (może trzeba też ustawić OBJROOT?), Dzięki Dougowi Dickinsonowi
SCRIPT (to jest to, co musisz skopiować / wkleić)
Aby uzyskać instrukcje użytkowania / instalacji, patrz poniżej
##########################################
#
# c.f. /programming/3520977/build-fat-static-library-device-simulator-using-xcode-and-sdk-4
#
# Version 2.82
#
# Latest Change:
# - MORE tweaks to get the iOS 10+ and 9- working
# - Support iOS 10+
# - Corrected typo for iOS 1-10+ (thanks @stuikomma)
#
# Purpose:
# Automatically create a Universal static library for iPhone + iPad + iPhone Simulator from within XCode
#
# Author: Adam Martin - http://twitter.com/redglassesapps
# Based on: original script from Eonil (main changes: Eonil's script WILL NOT WORK in Xcode GUI - it WILL CRASH YOUR COMPUTER)
#
set -e
set -o pipefail
#################[ Tests: helps workaround any future bugs in Xcode ]########
#
DEBUG_THIS_SCRIPT="false"
if [ $DEBUG_THIS_SCRIPT = "true" ]
then
echo "########### TESTS #############"
echo "Use the following variables when debugging this script; note that they may change on recursions"
echo "BUILD_DIR = $BUILD_DIR"
echo "BUILD_ROOT = $BUILD_ROOT"
echo "CONFIGURATION_BUILD_DIR = $CONFIGURATION_BUILD_DIR"
echo "BUILT_PRODUCTS_DIR = $BUILT_PRODUCTS_DIR"
echo "CONFIGURATION_TEMP_DIR = $CONFIGURATION_TEMP_DIR"
echo "TARGET_BUILD_DIR = $TARGET_BUILD_DIR"
fi
#####################[ part 1 ]##################
# First, work out the BASESDK version number (NB: Apple ought to report this, but they hide it)
# (incidental: searching for substrings in sh is a nightmare! Sob)
SDK_VERSION=$(echo ${SDK_NAME} | grep -o '\d\{1,2\}\.\d\{1,2\}$')
# Next, work out if we're in SIM or DEVICE
if [ ${PLATFORM_NAME} = "iphonesimulator" ]
then
OTHER_SDK_TO_BUILD=iphoneos${SDK_VERSION}
else
OTHER_SDK_TO_BUILD=iphonesimulator${SDK_VERSION}
fi
echo "XCode has selected SDK: ${PLATFORM_NAME} with version: ${SDK_VERSION} (although back-targetting: ${IPHONEOS_DEPLOYMENT_TARGET})"
echo "...therefore, OTHER_SDK_TO_BUILD = ${OTHER_SDK_TO_BUILD}"
#
#####################[ end of part 1 ]##################
#####################[ part 2 ]##################
#
# IF this is the original invocation, invoke WHATEVER other builds are required
#
# Xcode is already building ONE target...
#
# ...but this is a LIBRARY, so Apple is wrong to set it to build just one.
# ...we need to build ALL targets
# ...we MUST NOT re-build the target that is ALREADY being built: Xcode WILL CRASH YOUR COMPUTER if you try this (infinite recursion!)
#
#
# So: build ONLY the missing platforms/configurations.
if [ "true" == ${ALREADYINVOKED:-false} ]
then
echo "RECURSION: I am NOT the root invocation, so I'm NOT going to recurse"
else
# CRITICAL:
# Prevent infinite recursion (Xcode sucks)
export ALREADYINVOKED="true"
echo "RECURSION: I am the root ... recursing all missing build targets NOW..."
echo "RECURSION: ...about to invoke: xcodebuild -configuration \"${CONFIGURATION}\" -project \"${PROJECT_NAME}.xcodeproj\" -target \"${TARGET_NAME}\" -sdk \"${OTHER_SDK_TO_BUILD}\" ${ACTION} RUN_CLANG_STATIC_ANALYZER=NO" BUILD_DIR=\"${BUILD_DIR}\" BUILD_ROOT=\"${BUILD_ROOT}\" SYMROOT=\"${SYMROOT}\"
xcodebuild -configuration "${CONFIGURATION}" -project "${PROJECT_NAME}.xcodeproj" -target "${TARGET_NAME}" -sdk "${OTHER_SDK_TO_BUILD}" ${ACTION} RUN_CLANG_STATIC_ANALYZER=NO BUILD_DIR="${BUILD_DIR}" BUILD_ROOT="${BUILD_ROOT}" SYMROOT="${SYMROOT}"
ACTION="build"
#Merge all platform binaries as a fat binary for each configurations.
# Calculate where the (multiple) built files are coming from:
CURRENTCONFIG_DEVICE_DIR=${SYMROOT}/${CONFIGURATION}-iphoneos
CURRENTCONFIG_SIMULATOR_DIR=${SYMROOT}/${CONFIGURATION}-iphonesimulator
echo "Taking device build from: ${CURRENTCONFIG_DEVICE_DIR}"
echo "Taking simulator build from: ${CURRENTCONFIG_SIMULATOR_DIR}"
CREATING_UNIVERSAL_DIR=${SYMROOT}/${CONFIGURATION}-universal
echo "...I will output a universal build to: ${CREATING_UNIVERSAL_DIR}"
# ... remove the products of previous runs of this script
# NB: this directory is ONLY created by this script - it should be safe to delete!
rm -rf "${CREATING_UNIVERSAL_DIR}"
mkdir "${CREATING_UNIVERSAL_DIR}"
#
echo "lipo: for current configuration (${CONFIGURATION}) creating output file: ${CREATING_UNIVERSAL_DIR}/${EXECUTABLE_NAME}"
xcrun -sdk iphoneos lipo -create -output "${CREATING_UNIVERSAL_DIR}/${EXECUTABLE_NAME}" "${CURRENTCONFIG_DEVICE_DIR}/${EXECUTABLE_NAME}" "${CURRENTCONFIG_SIMULATOR_DIR}/${EXECUTABLE_NAME}"
#########
#
# Added: StackOverflow suggestion to also copy "include" files
# (untested, but should work OK)
#
echo "Fetching headers from ${PUBLIC_HEADERS_FOLDER_PATH}"
echo " (if you embed your library project in another project, you will need to add"
echo " a "User Search Headers" build setting of: (NB INCLUDE THE DOUBLE QUOTES BELOW!)"
echo ' "$(TARGET_BUILD_DIR)/usr/local/include/"'
if [ -d "${CURRENTCONFIG_DEVICE_DIR}${PUBLIC_HEADERS_FOLDER_PATH}" ]
then
mkdir -p "${CREATING_UNIVERSAL_DIR}${PUBLIC_HEADERS_FOLDER_PATH}"
# * needs to be outside the double quotes?
cp -r "${CURRENTCONFIG_DEVICE_DIR}${PUBLIC_HEADERS_FOLDER_PATH}"* "${CREATING_UNIVERSAL_DIR}${PUBLIC_HEADERS_FOLDER_PATH}"
fi
fi
ZAINSTALUJ INSTRUKCJE
- Utwórz statyczny projekt lib
- Wybierz cel
- Na karcie „Ustawienia kompilacji” ustaw „Kompiluj tylko architekturę aktywną” na „NIE” (dla wszystkich elementów)
- Na karcie „Fazy kompilacji” wybierz opcję „Dodaj ... Nowa faza kompilacji ... Nowa faza kompilacji skryptu uruchamiania”
- Skopiuj / wklej skrypt (powyżej) w polu
... wykorzystanie BONUS OPCJONALNE:
- OPCJONALNIE: jeśli masz nagłówki w bibliotece, dodaj je do fazy „Kopiuj nagłówki”
- OPCJONALNIE: ... i przeciągnij / upuść je z sekcji „Projekt” do sekcji „Publiczne”
- OPCJONALNIE: ... i będą one automatycznie eksportowane za każdym razem, gdy budujesz aplikację, do podkatalogu katalogu „debug-universal” (będą one w usr / local / include)
- OPCJONALNIE: UWAGA: jeśli spróbujesz również przeciągnąć / upuścić projekt do innego projektu Xcode, ujawnia to błąd w Xcode 4, w którym nie można utworzyć pliku .IPA, jeśli masz publiczne nagłówki w swoim projekcie przeciągania / upuszczania. Obejście: nie osadzaj projektów xcode (zbyt wiele błędów w kodzie Apple!)
Jeśli nie możesz znaleźć pliku wyjściowego, oto obejście:
Dodaj następujący kod na samym końcu skryptu (dzięki uprzejmości Frederika Wallnera): otwórz „$ {CREATING_UNIVERSAL_DIR}”
Apple usuwa wszystkie dane wyjściowe po 200 wierszach. Wybierz swój cel, aw fazie uruchamiania skryptu MUSISZ odznaczyć: „Pokaż zmienne środowiskowe w dzienniku kompilacji”
jeśli używasz niestandardowego katalogu „build output” dla XCode4, wtedy XCode umieszcza wszystkie „nieoczekiwane” pliki w niewłaściwym miejscu.
- Zbuduj projekt
- Kliknij ostatnią ikonę po prawej stronie w lewym górnym obszarze Xcode4.
- Wybierz najwyższy element (jest to „najnowsza wersja”. Apple powinien wybrać go automatycznie, ale nie pomyśleli o tym)
- w głównym oknie przewiń w dół. Ostatni wiersz powinien brzmieć: lipo: dla bieżącej konfiguracji (debugowania) tworzenie pliku wyjściowego: /Users/blah/Library/Developer/Xcode/DerivedData/AppName-ashwnbutvodmoleijzlncudsekyf/Build/Products/Debug-universal/libTargetName.a
... to jest lokalizacja twojej Uniwersalnej Kompilacji.
Jak dołączyć do projektu pliki „bez kodu źródłowego” (PNG, PLIST, XML itp.)
- Zrób wszystko powyżej, sprawdź, czy działa
- Utwórz nową fazę Run Script, która pojawi się PO PIERWSZEJ (skopiuj / wklej poniższy kod)
- Utwórz nowy cel w Xcode, typu „pakiet”
- W swoim PROJEKCIE GŁÓWNYM w „Fazach kompilacji” dodaj nowy pakiet jako coś, od czego „zależy” (górna sekcja, naciśnij przycisk plus, przewiń w dół, znajdź plik „.bundle” w swoich produktach)
- W swoim NOWYM CELU GRANICZNYM w „Fazach kompilacji” dodaj sekcję „Kopiuj zasoby pakietu” i przeciągnij / upuść do niego wszystkie pliki PNG itp.
Skrypt do automatycznego kopiowania wbudowanych pakietów do tego samego folderu, co biblioteka statyczna FAT:
echo "RunScript2:"
echo "Autocopying any bundles into the 'universal' output folder created by RunScript1"
CREATING_UNIVERSAL_DIR=${SYMROOT}/${CONFIGURATION}-universal
cp -r "${BUILT_PRODUCTS_DIR}/"*.bundle "${CREATING_UNIVERSAL_DIR}"