【问题标题】:SDL2 Mac File HandlingSDL2 Mac 文件处理
【发布时间】:2013-09-12 12:04:48
【问题描述】:

我在 Mac 上通过 SDL2 访问文件时遇到了一个奇怪的问题。我在 OS X Mountain Lion 上使用 XCode 4,并且使用 SDL2 作为框架。我不是从源代码编译 SDL2。我已将框架添加到包中,以及我需要加载的文件。该程序从 XCode 构建和运行良好,但文件不会在编辑器之外加载(即,如果我双击独立的 .app 文件不会加载)。这是我的 .app 包的样子:

MyApp.app/
    Contents/
        Frameworks/
            SDL2.framework/
        MacOS/
            MyApp
        Resources/
            Configure.txt
            MyBMP.bmp
        Info.plist
        PkgInfo

在我的 C 代码中,我尝试过:

SDL_LoadBMP("MyApp.app/Contents/Resources/MyBMP.bmp");

除了这个:

SDL_LoadBMP("MyBMP.bmp");

以及几乎所有介于两者之间的东西。 我也尝试通过以下方式访问文本文件:

FILE* data = fopen("MyApp.app/Contents/Resources/Configure.txt", "r");

FILE* data = fopen("Configure.txt", "r");

没有成功。 在 XCode 编辑器中,只有长的绝对路径有效,而我尝试过的任何方法都没有在独立的 .app 中有效。

其他人是否遇到此问题?我在使用 SDL 1.2 时加载了文件,但由于某种原因,SDL2 似乎没有加载任何文件。 SDL2 在初始化期间是否对活动目录做了一些奇怪的事情?

----------编辑1-------------- 我最近试图弄清楚发生了什么的尝试使用了这段代码:

#include "SDL2/SDL.h"
#include "stdio.h"
#include "stdlib.h"

int main (int argc, char** argv){
    if(SDL_Init(SDL_INIT_EVERYTHING) < 0)
         return EXIT_FAILURE;

    FILE* test = fopen("Test.txt", "w");

    if (!test) 
        return EXIT_FAILURE;

    fprintf(test, "Let's see where this ends up...");
    fclose(test);
    return EXIT_SUCCESS;

    //The rest of my code, which shouldn't ever come into play...
}

从 XCode 4 编辑器运行时,这将按预期工作。在 Debug 文件夹中,就在我的 .app 文件旁边,有一个 Test.txt 文件,其中包含短语“让我们看看这会在哪里结束......”。但是,通过单击独立应用程序运行时,程序会立即结束,并且找不到文本文件。我检查了日志,它只是说程序以代码 1 退出。通过更彻底的分析,fopen() 似乎失败了。有人知道会发生什么吗?

【问题讨论】:

  • 只是在黑暗中野蛮刺伤,但你尝试过吗:FILE* data = fopen("../Resources/Configure.txt", "r");
  • @Zammalad 我试过了,但没用。我会用最近的发现更新这个问题。

标签: c xcode macos file-handling sdl-2


【解决方案1】:

您可以使用以下方法将工作目录设置为应用程序包中的资源目录:

#include "CoreFoundation/CoreFoundation.h"

char path[PATH_MAX];
CFURLRef res = CFBundleCopyResourcesDirectoryURL(CFBundleGetMainBundle());
CFURLGetFileSystemRepresentation(res, TRUE, (UInt8 *)path, PATH_MAX)
CFRelease(res);
chdir(path);

您可能希望将其封装在 #ifdef __APPLE__#endif 之间以实现跨平台兼容性。

【讨论】:

【解决方案2】:

下载 ResourcePath.hpp 的 SFML 库或从 https://github.com/Malaxiz/Third/blob/network/Fifth/ResourcePath.hpp 获取它 https://github.com/Malaxiz/Third/blob/network/Fifth/ResourcePath.mm

#ifdef __APPLE__
#include "CoreFoundation/CoreFoundation.h"
#include "ResourcePath.hpp"
#endif

void CGame::_initRelativePaths() {
// ----------------------------------------------------------------------------
// This makes relative paths work in C++ in Xcode by changing directory to the Resources folder inside the .app bundle
#ifdef __APPLE__
    CFBundleRef mainBundle = CFBundleGetMainBundle();
    CFURLRef resourcesURL = CFBundleCopyResourcesDirectoryURL(mainBundle);
    char path[PATH_MAX];
    if (!CFURLGetFileSystemRepresentation(resourcesURL, TRUE, (UInt8 *)path, PATH_MAX))
    {
        // error!
    }
    CFRelease(resourcesURL);

    chdir(path);
    #endif
    // ---------------------------------------------------------------------------    -
}

在init中运行函数。

参考:https://github.com/Malaxiz/Third/blob/network/Fifth/CGame.cpp#L191

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-08-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-12-01
    • 2019-05-11
    相关资源
    最近更新 更多