ASP.NET libwebp.dll как сохранить изображение WebP на диск

Я создал libwebp.dll для WebP, используя эти инструкции (я скачал этот исходный код)

Я добавил файл libwebp.dll в папку bin моего проекта.

Затем я добавил этот код (найден здесь):

Private Declare Function WebPEncodeBGRA Lib "libwebp.dll" (ByVal rgba As IntPtr, ByVal width As Integer, ByVal height As Integer, ByVal stride As Integer, ByVal quality_factor As Single, ByRef output As IntPtr) As Integer
Private Declare Function WebPFree Lib "libwebp.dll" (ByVal p As IntPtr) As Integer

Private Sub Encode()
    Dim source As Bitmap = New Bitmap(Server.MapPath("images\") + "audio.png")
    Dim data As BitmapData = source.LockBits(New Rectangle(0, 0, source.Width, source.Height), ImageLockMode.ReadOnly, System.Drawing.Imaging.PixelFormat.Format32bppArgb)
    Dim webp_data As IntPtr
    Dim i As Integer = WebPEncodeBGRA(data.Scan0, source.Width, source.Height, data.Stride, 80, webp_data)

    WebPFree(webp_data)
End Sub

Я получаю сообщение об ошибке:

Была предпринята попытка загрузить программу с неверным форматом. (Исключение из HRESULT: 0x8007000B)

Что я также сделал (после комментариев Дая ниже):

  • Я создал dll для 64-битной архитектуры следующим образом: toolchain-architectur">см. также здесь)
  • Я проверил IIS для рассматриваемого пула приложений, и для его свойства Enable32-Bit Applications установлено значение False.
  • Я использую Windows 10 64 бит
  • И Environment.Is64BitProcess, и Environment.Is64BitOperatingSystem в коде программной части оцениваются как True

Как я могу закодировать изображение и сохранить закодированное изображение на диск в формате WebP?

Для тестирования на своем компьютере:
Загрузите скомпилированный и заархивированный файл libwebp. dll здесь. Это файл изображения, который я использую:

введите описание изображения здесь


person Flo    schedule 28.04.2018    source источник
comment
Ошибка вызвана попыткой загрузить 32-разрядную DLL в 64-разрядный хост-процесс или наоборот. Я предполагаю, что ваш веб-сервер работает как 64-битный, но вы создали только 32-битную версию libwebp.dll.   -  person Dai    schedule 30.04.2018
comment
Возможно, все наоборот: IIS работает как 32-битный и не может загрузить вашу 64-битную DLL.   -  person Dai    schedule 30.04.2018
comment
Я только что проверил настройки пула приложений в IIS для рассматриваемого пула приложений, и у него свойство Enable32-Bit Applications установлено на False, так что я думаю, что это тоже не так...   -  person Flo    schedule 30.04.2018


Ответы (2)


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

поэтому я меняю и смотрит, что это работает.

    <DllImport("libwebp.dll", CallingConvention:=CallingConvention.Cdecl)>
Private Shared Function WebPEncodeBGRA(ByVal rgba As IntPtr, ByVal width As Integer, ByVal height As Integer, ByVal stride As Integer, ByVal quality_factor As Single, <Out> ByRef output As IntPtr) As Integer
End Function


<DllImport("libwebp.dll", CallingConvention:=CallingConvention.Cdecl)>
Private Shared Function WebPFree(ByVal p As IntPtr) As Integer
End Function

и импортировать

Imports System.Runtime.InteropServices

Я использую dll из Загрузите libwebp-0.6.0.zip из Эти инструкции 'libwebp-0.6.0.zip\x64\bin' и все работает.

Когда я пытаюсь прикрепить вашу dll из Загрузите скомпилированную и заархивированную libwebp.dll здесь. Это файл изображения, который я использую:

получил точно такое же исключение, похоже не 64

для изображения я не уверен, возможно, вам нужно перевернуть его

            'data.strinde = webp_data 'not sure what is webp_data ewxacly, but you can check
        'data.Scan0 = webp_data 'not sure what is webp_data ewxacly, but you can check
        source.UnlockBits(data)
        source.Save(Server.MapPath("images\") + "audio.png")
person Norbert Ziemniak    schedule 02.05.2018
comment
Спасибо, dll 0.6.0, кажется, помогает пройти первую ошибку. Вы сохраняете переменную source, но нужно сохранить переменную webp_data, как мне это сделать? А ты умеешь компилировать 1.0.0 libwebp.dll для x64? Я бы предпочел не использовать бета-версию 0.6.0, и я не знаю, почему она не компилируется правильно. - person Flo; 02.05.2018
comment
Привет! Еще раз спасибо за вашу помощь в этом. Теперь я получаю сообщение об ошибке There is insufficient system memory in resource pool 'internal' to run this query., я предполагаю, что это потому, что я не очищаю память. Я вижу, что метод WebPFree в вашем коде пуст, знаете ли вы, что я должен ввести туда, чтобы очистить память? - person Flo; 18.05.2018

Как я могу закодировать изображение и сохранить закодированное изображение на диск в формате WebP?

После процесса преобразования вам необходимо организовать неуправляемую память, чтобы вы могли использовать данные в управляемом коде.

Public Sub Encode()
    Dim source As Bitmap = New Bitmap(Server.MapPath("images\audio.png"))
    'Hold bitmap data
    Dim bmpData As BitmapData = source.LockBits(New Rectangle(0, 0, source.Width, source.Height), ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb)

    'Create a pointer for webp data
    Dim webpDataSrc As IntPtr

    'Store resulting webp data length after conversion
    Dim webpDataLen As Integer = WebPEncodeBGRA(bmpData.Scan0, source.Width, source.Height, bmpData.Stride, 80, webpDataSrc)

    'Create a managed byte array with the size you just have
    Dim webpDataBin As Byte() = New Byte(webpDataLen - 1){}

    'Copy from unmanaged memory to managed byte array you created
    System.Runtime.InteropServices.Marshal.Copy(webpDataSrc, webpDataBin, 0, webpDataLen)

    'Write byte array to a file
    System.IO.File.WriteAllBytes(Server.MapPath("images\audio.webp"), webpDataBin)

    'Free
    WebPFree(webpDataSrc)

    source.Dispose()
End Sub

Кстати, команда nmake /f Makefile.vc CFG=release-dynamic RTLIBCFG=dynamic OBJDIR=output ARCH=x64, которую вы использовали, в порядке. Я также мог скомпилировать библиотеку (версия 1.0.0) с помощью этой команды. Однако я на 100 % уверен, что сжатая здесь libwebp.dll является 32-разрядной. , а не 64-битная.

Убедитесь, что вы запускаете правильную среду для создания 64-битных двоичных файлов.

person Kul-Tigin    schedule 07.05.2018
comment
Хорошо... это, кажется, сохраняет изображение webp! Последний шаг: в какой среде вы начали создавать 64-битный двоичный файл? Я попробовал x64 Native Tools Command Prompt for Visual Studio 2017, я также попробовал свою обычную командную строку Windows, которая работает в 64-битном режиме, и я попробовал Windows Powershell. Ни один из них не работает для меня. - person Flo; 07.05.2018
comment
@Flo Та же среда и та же команда с тобой. Вот снимок экрана выходного каталога с выходными данными dumpbin: img.imgur.com/5BXzyuN.png - person Kul-Tigin; 07.05.2018
comment
Хорошо... это сводит меня с ума... не могли бы вы поделиться со мной скомпилированной 64-битной dll, которая у вас есть? Затем я могу закрыть эту тему и назначить награду, а затем выяснить, почему она не работает на моей машине... заранее спасибо! - person Flo; 07.05.2018
comment
Хммм... Я хотел разделить награду между вами и другим автором, но это невозможно на SO. Поскольку другой постер был первым и предоставил ключевую часть, кодировку в webp, которая не удалась, я собираюсь наградить его наградой и начать другую награду для вас, чтобы наградить вас 50 баллами ... надеюсь, вы понимаете :-) - person Flo; 07.05.2018
comment
@Flo Все в порядке, но мне совсем не нужна дополнительная награда. Спасибо. - person Kul-Tigin; 07.05.2018
comment
D'oh... оказалось, что дополнительная награда была выше, чем была изначально... круто, что ты не против, спасибо за помощь! :-) - person Flo; 07.05.2018