Я делаю свою собственную библиотеку игр, которая использует SFML с VS2013. Я хочу повторно использовать код, установив библиотеку как DLL. Однако у меня возникают проблемы при использовании моей собственной DLL.
Вот подробное описание моей ситуации:
Вот часть кода в игровом цикле, где window - это sf::RenderWindow, а rect - это объект, определенный в моей DLL, который просто представляет собой sf::RectangleShape с определенными свойствами (маленький синий прямоугольник в точке (0,0)).
window.clear(sf::Color::White);
window.draw(rect);
window.display();
Однако после window.draw(rect) весь экран станет черным, даже несмотря на то, что приведенное выше утверждение должно очистить его как белый, а rect занимает лишь небольшое место в верхнем левом углу.
С моим классом не должно быть проблем, так как если я вставлю объявление и определение класса непосредственно в основной исходный файл (конечно, удалив такие вещи, как __declspec(dllexport)), все будет работать хорошо.
Все функции в моей DLL, которые не используют SFML, работают корректно при загрузке из DLL.
SFML статически компонуется как в проекте DLL, так и в проекте, который его использует.
Я просмотрел и следил за MSDN, чтобы настроить свои проекты.
Итак, как это исправить? Я предполагаю, что проблема должна заключаться в том, что я пропустил некоторые шаги, которые позволяют DLL использовать другую библиотеку, но я не нашел соответствующих тем (возможно, я использовал неправильные ключевые слова...)
Ответ 1 · рейтинг 4 · Lukas
Если вы действительно статически свяжете SFML с вашей DLL, у вас возникнет проблема, потому что теперь ваше приложение finally содержит копию SFML, а ваша DLL содержит копию SFML. Таким образом, выделенный SFML материал в DLL не обязательно будет доступен в приложении и наоборот.
В качестве решения вы можете связать только все динамическое или все статическое в конечном приложении. Это означает, что вы либо используете динамические библиотеки SFML, либо также связываете свою статическую библиотеку и связываетесь только со статической SFML в своем приложении, а не в своей библиотеке.
Поскольку вы используете VS 2013, вам также придется пересобрать сам SFML, и если вы используете последнюю версию, статическая привязка изменилась (полное обсуждение). Итак, вот несколько рисунков ASCII о том, как это будет работать с SFML 2.0 или 2.1.
winmm gdi32 opengl
/ \ | /
/ \ | /
v v v v
sfml-system-s sfml-window-s
| | | |
| +---------------+
| | | |
| +---------+ | |
| | | |
v v v v
example.exe <--- yourlib.dll
С SFML из исходного кода (цель 2.3) это будет выглядеть примерно так.
sfml-system-s sfml-window-s winmm gdi32 opengl
| | | | |
+------------+ +-------+ | | |
| | | +-----------------+ | |
| +-----------+ | +-----------------------+ |
| | | | | | +----------------------------+
| | | | | | |
v v v v v v v
yourlib.dll -> example.exe
Однако, по сути, вы хотите следующее:
sfml-system-s sfml-window-s winmm gdi32 opengl yourlib-s
| | | | | |
| +-------+ | | | |
| | +-----------------+ | | |
| | | +-----------------------+ | |
| | | | +----------------------------+ |
| | | | | +----------------------------------+
| | | | | |
v v v v v v
example.exe
Динамическая компоновка по сути работает уже как последняя диаграмма (только другая), поэтому динамическая компоновка отлично работает "из коробки".
В Интернете есть много информации о том, как работают ссылки и т. д. Одним из примеров может быть это сообщение на форуме.