Ошибка загрузки UserControl со ссылкой на DLL в режиме конструктора - PullRequest
1 голос
/ 24 июля 2010

У меня есть проект C # с UserControl в нем.

Этот пользовательский элемент управления зависит от конкретной DLL C ++ Mixed mode, которая, в свою очередь, действует как фасад неуправляемой C ++ DLL

                     C#           C++ Mixed            C++ Umnanaged
  [ main app ] ---> [ myUC ] ---> [ OCShell.dll ] ---> [ OCC.dll ]

В представлении «Дизайн» я не могу добавить элемент управления пользователя.Он говорит, что в OCShell существует исключение FileNotFoundException (или одна из его зависимостей).Однако через код все работает нормально.В основном приложении (форма Windows) я могу

myUC uc = new myUC();
this.Controls.Add(uc);

, и это прекрасно работает.Правильный код выполняется правильно.

Я проверил с помощью Dependency Walker и все в порядке.Все правильно копируется в каталог Bin \ Debug \, и каждая из этих библиотек DLL видит друг друга.

Я предполагаю, что редактор представлений дизайна не проверяет правильные пути для этих библиотек DLL и, следовательно, возвращает ошибку.

Я также пытался копировать каждую dll во все возможные каталоги в моем решении, но это тоже не помогло

Ответы [ 2 ]

3 голосов
/ 24 июля 2010

Да, это проблема. Проблема в том, что код выполняется в Visual Studio, а не в вашем приложении. Путь поиска, который используется для поиска зависимых сборок, будет включать только частные каталоги VS (Common7 \ IDE \ PrivateAssemblies и PublicAssemblies), но не каталог сборки вашего проекта. Вы можете заставить его найти OCShell.dll, скопировав его в один из этих каталогов, но неуправляемую DLL нужно будет поместить в каталог, который Window будет искать при поиске DLL. Что, помимо параллельного кэша Windows, для которого требуется манифест, ограничено каталогом в системной переменной среды PATH.

Это не приятные варианты. Лучше всего убедиться, что код в этих DLL не может быть выполнен во время разработки. Вы делаете это, используя свойство DesignMode, обходя вызовы, если оно имеет значение True. Это нужно сделать как минимум в конструкторе и событии Load. Другие события также могут выполняться. Также значительно минимизирует вероятность того, что вы выйдете из строя из-за ошибки в неуправляемом коде. Если это влияет на представление элемента управления во время разработки, то вам может потребоваться написать конструктор, чтобы компенсировать это.

1 голос
/ 10 марта 2015

У меня была такая же проблема. Если у вас есть DLL, которая использует много других DLL и, вероятно, написана на C ++, то для этого часто требуется много других зависимостей. Во время выполнения они решаются идеально, но не в режиме разработки.

Используя ответ Ханса Пассанта, вам нужно ставить этот код перед каждым вызовом функции, связанной с этой DLL.

if ( !DesignerProperties.GetIsInDesignMode(this) ) 

У меня было 2 вызова Connect () и 2 Disconnect () из моей DLL, и после того, как я поместил это перед каждым случаем, Дизайнер теперь мог отлично загрузить макет для UserControl. Спасибо за решение.

...