Help me I'm blind.

Get help with using AutoHotkey (v1.1 and older) and its commands and hotkeys
ahk7
Posts: 575
Joined: 06 Nov 2013, 16:35

Re: Help me I'm blind.

Post by ahk7 » 09 Sep 2021, 13:27

So does the variable text contain the OCR-ed text? If so you can save it a file using the FileAppend command like so

FileAppend, %text%, %A_Now%.txt

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 13 Sep 2021, 03:11

Dear ahk7,
Thank you very much for your useful advice. I must deeply study all scripts especially long scripts which control The scanner because it does not create a file at all. It is An example that must be finished to work correctly. But author of The script is elite Autohotkey programmer, because he has even created device manager WIA based script.

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 03 Mar 2022, 09:15

Dear specialists,
I would like to have code, which would be able to play and record live Internet radio stream in supported format at The same time. Mr @Malcev has created some code, but I have very probably did not understood it correctly to put The necessary lines together. So as A result, app only play live stream, but do not record it at The same time.

Here is my code. Very advanced programmers knowledge will be required to get it to work correctly.

Code: Select all

; Generated by Auto-GUI 3.0.1
#SingleInstance Force
#NoEnv
SetWorkingDir %A_ScriptDir%
SetBatchLines -1
proc := RegisterCallback("DownloadProc")
hStream := DllCall("bass.dll\BASS_StreamCreateURL", "Str","","UInt", 0, "UInt", A_IsUnicode ? BASS_UNICODE := 0x80000000 : 0, "Ptr", proc, "Ptr", 0, "UInt")
DownloadProc(buffer, length, user) 
{
	if !file
		file := FileOpen("afile.mp3", "w") 
	if !buffer
		file := 0 ; FileObj.Close() invoked automatically by the destructor
	else
	{
		numBytesWritten := file.RawWrite(buffer+0, length)
		if !numBytesWritten
			throw "wrote 0 bytes, there was some problem"
}


}



Gui Font, s9, Segoe UI
Gui Add, Button, gStart x3 y3 w80 h23, &Record and play

Gui Show, w620 h420, Live stream recorder
Return

Start:
DllCall("LoadLibrary", "Str", A_ScriptDir . "\bass.dll")
	DllCall("bass.dll\BASS_Free")
	if (DllCall("bass.dll\BASS_Init", "Int", -1, "UInt", 44100, "UInt", 0, "Ptr", A_ScriptHwnd, "Ptr", 0))
Hstream := DllCall("bass.dll\BASS_StreamCreateURL", "Str","http://icecast8.play.cz/cro1-128.mp3","UInt", 0, "UInt", A_IsUnicode ? BASS_UNICODE := 0x80000000 : 0, "Ptr", 0, "Ptr", 0, "UInt")
	DllCall("bass.dll\BASS_ChannelPlay", "UInt", hStream, "Int", 0)

Hstream = BASS_StreamCreateURL("", 0, 0, MyDownloadProc, 0);

Return

GuiEscape:
GuiClose:
    ExitApp

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 09 Mar 2022, 12:39

I have tried to do my best to have joined two scripts. One which scan in 300 DPI resolution and Grayscale image and second script which perform OCR on The scanned bitmap. Unfortunately, I do not know how to get variable value with scanned bitmap.

Code: Select all

;                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   #NoEnv
FormatID := {BMP: "{B96B3CAB-0728-11D3-9D7B-0000F81EF32E}", PNG: "{B96B3CAF-0728-11D3-9D7B-0000F81EF32E}"
           , GIF: "{B96B3CB0-0728-11D3-9D7B-0000F81EF32E}", JPG: "{B96B3CAE-0728-11D3-9D7B-0000F81EF32E}"
           , TIF: "{B96B3CB1-0728-11D3-9D7B-0000F81EF32E}"}
DevTypes := {0: "UnspecifiedDeviceType"
           , 1: "ScannerDeviceType"
           , 2: "CameraDeviceType"
           , 3: "VideoDeviceType"}
ImgTypes := {0: "WIA_INTENT_NONE"
           , 1: "WIA_INTENT_IMAGE_TYPE_COLOR"
           , 2: "WIA_INTENT_IMAGE_TYPE_GRAYSCALE"
           , 4: "WIA_INTENT_IMAGE_TYPE_TEXT"}
WIA_IPS_PAGE_SIZE := "3097" ; Page Size
WIA_PAGE_A4     := 0 ; 8267 x 11692
WIA_PAGE_LETTER := 1 ; 8500 x 11000
WIA_PAGE_CUSTOM := 2 ; (current extent settings)
WIA_IPS_CUR_INTENT := "6146" ; Current Intent
WIA_INTENT_NONE                 := 0x00000000
WIA_INTENT_IMAGE_TYPE_COLOR     := 0x00000001 ; RGB
WIA_INTENT_IMAGE_TYPE_GRAYSCALE := 0x00000002 ; grayscale
WIA_INTENT_IMAGE_TYPE_TEXT      := 0x00000004 ; black & white
WIA_INTENT_MINIMIZE_SIZE        := 0x00010000
WIA_INTENT_MAXIMIZE_QUALITY     := 0x00020000
WIA_INTENT_BEST_PREVIEW         := 0x00040000
; ----------------------------------------------------------------------------------------------------------------------
; Image output format
FileExt := "BMP"              ; BMP, GIF, JPG, PNG, TIF
; Device name, if required
DeviceName := ""
; Some device and image properties you may set
DevProps := {}
DevProps["3097"] := ""     ; page size (e.g. 0 = A4, 1 = letter, 2 = custom (current extend settings)
ImgProps := {}
ImgProps["3097"] := ""     ; page size (e.g. 0 = A4, 1 = letter, 2 = custom (current extend settings)
ImgProps["6146"] := 2      ; 1 = RGB color, 2 = grayscale, 4 = black & white
ImgProps["6147"] := "300"     ; horizontal resolution (DPI)
ImgProps["6148"] := "300"     ; vertical resolution (DPI)
ImgProps["6149"] := ""     ; horizontal start position in pixels
ImgProps["6150"] := ""     ; vertical start position in pixels
ImgProps["6151"] := ""     ; horizontal extend (width) in pixels
ImgProps["6152"] := ""     ; vertical extend (height) in pixels
; ----------------------------------------------------------------------------------------------------------------------
; Check the output format
If (FileExt = "")
   FileExt := "BMP"
If !FormatID.Haskey(FileExt) {
   MsgBox, 36, Scan, % "Output format " . FileExt . " is not supported!`n`n"
                     . "Supported formats are  BMP, GIF, JPG, PNG, TIF.`n"
                     . "The image will be scanned as BMP.`n`n"
                     . "Do you want to continue?"
   IfMsgBox, Yes
      FileExt := "BMP"
   Else
      ExitApp
}
; ----------------------------------------------------------------------------------------------------------------------
DevManager := ComObjCreate("WIA.Devicemanager")
DevCount := DevManager.DeviceInfos.Count
I := 0
Device := 0
While (I < DevCount) {
   DevInfo := DevManager.DeviceInfos(++I)
   If (DevInfo.Type = 1) { ; it's a scanner
      If (DeviceName = "") || (DeviceName = DevInfo.Properties("Name").Value) {
         Device := DevInfo.Connect
         Break
      }
   }
}
If !(Device) {
   MsgBox, Could not find a scanner device!
   ExitApp
}
Name := Device.Properties("Name").Value
Item := Device.Items(1)
; ----------------------------------------------------------------------------------------------------------------------
; Set the properties
For Prop, Value In DevProps
   If (Value <> "")
      Device.Properties(Format("{:04}", Prop)).Value := Value
For Prop, Value In ImgProps
   If (Value <> "")
      Item.Properties(Format("{:04}", Prop)).Value := Value
; Item.Properties("3097").Value := 100 ; A4

Image := Item.Transfer("{B96B3CAB-0728-11D3-9D7B-0000F81EF32E}") ; scan as BMP
PicObj := WIA_GetImageBitmap(Image)
hBitmap := PicObj.Handle

; ======================================================================================================================
WIA_GetImageBitmap(ImgObj) {
   ; To retrieve the HBITMAP handle for the returned object use object.Handle
   Return (ComObjType(ImgObj, "Name") = "strana.bmp") ? ImgObj.Filedata.Picture : False
}
pIRandomAccessStream := hBitmapToRandomAccessStream(hBitmap)
DllCall("DeleteObject", "Ptr", hBitmap)
text := ocr(pIRandomAccessStream, "cs")
MsgBox, % text
Return

HBitmapToRandomAccessStream(hBitmap) {
   static IID_IRandomAccessStream := "{905A0FE1-BC53-11DF-8C49-001E4FC686DA}"
        , IID_IPicture            := "{7BF80980-BF32-101A-8BBB-00AA00300CAB}"
        , PICTYPE_BITMAP := 1
        , BSOS_DEFAULT   := 0
        
   DllCall("Ole32\CreateStreamOnHGlobal", "Ptr", 0, "UInt", true, "PtrP", pIStream, "UInt")
   
   VarSetCapacity(PICTDESC, sz := 8 + A_PtrSize*2, 0)
   NumPut(sz, PICTDESC)
   NumPut(PICTYPE_BITMAP, PICTDESC, 4)
   NumPut(hBitmap, PICTDESC, 8)
   riid := CLSIDFromString(IID_IPicture, GUID1)
   DllCall("OleAut32\OleCreatePictureIndirect", "Ptr", &PICTDESC, "Ptr", riid, "UInt", false, "PtrP", pIPicture, "UInt")
   ; IPicture::SaveAsFile
   DllCall(NumGet(NumGet(pIPicture+0) + A_PtrSize*15), "Ptr", pIPicture, "Ptr", pIStream, "UInt", true, "UIntP", size, "UInt")
   riid := CLSIDFromString(IID_IRandomAccessStream, GUID2)
   DllCall("ShCore\CreateRandomAccessStreamOverStream", "Ptr", pIStream, "UInt", BSOS_DEFAULT, "Ptr", riid, "PtrP", pIRandomAccessStream, "UInt")
   ObjRelease(pIPicture)
   ObjRelease(pIStream)
   Return pIRandomAccessStream
}

CLSIDFromString(IID, ByRef CLSID) {
   VarSetCapacity(CLSID, 16, 0)
   if res := DllCall("ole32\CLSIDFromString", "WStr", IID, "Ptr", &CLSID, "UInt")
      throw Exception("CLSIDFromString failed. Error: " . Format("{:#x}", res))
   Return &CLSID
}


ocr(file, lang := "FirstFromAvailableLanguages")
{
   static OcrEngineStatics, OcrEngine, MaxDimension, LanguageFactory, Language, CurrentLanguage, BitmapDecoderStatics, GlobalizationPreferencesStatics
   if (OcrEngineStatics = "")
   {
      CreateClass("Windows.Globalization.Language", ILanguageFactory := "{9B0252AC-0C27-44F8-B792-9793FB66C63E}", LanguageFactory)
      CreateClass("Windows.Graphics.Imaging.BitmapDecoder", IBitmapDecoderStatics := "{438CCB26-BCEF-4E95-BAD6-23A822E58D01}", BitmapDecoderStatics)
      CreateClass("Windows.Media.Ocr.OcrEngine", IOcrEngineStatics := "{5BFFA85A-3384-3540-9940-699120D428A8}", OcrEngineStatics)
      DllCall(NumGet(NumGet(OcrEngineStatics+0)+6*A_PtrSize), "ptr", OcrEngineStatics, "uint*", MaxDimension)   ; MaxImageDimension
   }
   if (file = "ShowAvailableLanguages")
   {
      if (GlobalizationPreferencesStatics = "")
         CreateClass("Windows.System.UserProfile.GlobalizationPreferences", IGlobalizationPreferencesStatics := "{01BF4326-ED37-4E96-B0E9-C1340D1EA158}", GlobalizationPreferencesStatics)
      DllCall(NumGet(NumGet(GlobalizationPreferencesStatics+0)+9*A_PtrSize), "ptr", GlobalizationPreferencesStatics, "ptr*", LanguageList)   ; get_Languages
      DllCall(NumGet(NumGet(LanguageList+0)+7*A_PtrSize), "ptr", LanguageList, "int*", count)   ; count
      loop % count
      {
         DllCall(NumGet(NumGet(LanguageList+0)+6*A_PtrSize), "ptr", LanguageList, "int", A_Index-1, "ptr*", hString)   ; get_Item
         DllCall(NumGet(NumGet(LanguageFactory+0)+6*A_PtrSize), "ptr", LanguageFactory, "ptr", hString, "ptr*", LanguageTest)   ; CreateLanguage
         DllCall(NumGet(NumGet(OcrEngineStatics+0)+8*A_PtrSize), "ptr", OcrEngineStatics, "ptr", LanguageTest, "int*", bool)   ; IsLanguageSupported
         if (bool = 1)
         {
            DllCall(NumGet(NumGet(LanguageTest+0)+6*A_PtrSize), "ptr", LanguageTest, "ptr*", hText)
            buffer := DllCall("Combase.dll\WindowsGetStringRawBuffer", "ptr", hText, "uint*", length, "ptr")
            text .= StrGet(buffer, "UTF-16") "`n"
         }
         ObjRelease(LanguageTest)
      }
      ObjRelease(LanguageList)
      return text
   }
   if (lang != CurrentLanguage) or (lang = "FirstFromAvailableLanguages")
   {
      if (OcrEngine != "")
      {
         ObjRelease(OcrEngine)
         if (CurrentLanguage != "FirstFromAvailableLanguages")
            ObjRelease(Language)
      }
      if (lang = "FirstFromAvailableLanguages")
         DllCall(NumGet(NumGet(OcrEngineStatics+0)+10*A_PtrSize), "ptr", OcrEngineStatics, "ptr*", OcrEngine)   ; TryCreateFromUserProfileLanguages
      else
      {
         CreateHString(lang, hString)
         DllCall(NumGet(NumGet(LanguageFactory+0)+6*A_PtrSize), "ptr", LanguageFactory, "ptr", hString, "ptr*", Language)   ; CreateLanguage
         DeleteHString(hString)
         DllCall(NumGet(NumGet(OcrEngineStatics+0)+9*A_PtrSize), "ptr", OcrEngineStatics, ptr, Language, "ptr*", OcrEngine)   ; TryCreateFromLanguage
      }
      if (OcrEngine = 0)
      {
         msgbox Can not use language "%lang%" for OCR, please install language pack.
         ExitApp
      }
      CurrentLanguage := lang
   }
   IRandomAccessStream := file
   DllCall(NumGet(NumGet(BitmapDecoderStatics+0)+14*A_PtrSize), "ptr", BitmapDecoderStatics, "ptr", IRandomAccessStream, "ptr*", BitmapDecoder)   ; CreateAsync
   WaitForAsync(BitmapDecoder)
   BitmapFrame := ComObjQuery(BitmapDecoder, IBitmapFrame := "{72A49A1C-8081-438D-91BC-94ECFC8185C6}")
   DllCall(NumGet(NumGet(BitmapFrame+0)+12*A_PtrSize), "ptr", BitmapFrame, "uint*", width)   ; get_PixelWidth
   DllCall(NumGet(NumGet(BitmapFrame+0)+13*A_PtrSize), "ptr", BitmapFrame, "uint*", height)   ; get_PixelHeight
   if (width > MaxDimension) or (height > MaxDimension)
   {
      msgbox Image is to big - %width%x%height%.`nIt should be maximum - %MaxDimension% pixels
      ExitApp
   }
   BitmapFrameWithSoftwareBitmap := ComObjQuery(BitmapDecoder, IBitmapFrameWithSoftwareBitmap := "{FE287C9A-420C-4963-87AD-691436E08383}")
   DllCall(NumGet(NumGet(BitmapFrameWithSoftwareBitmap+0)+6*A_PtrSize), "ptr", BitmapFrameWithSoftwareBitmap, "ptr*", SoftwareBitmap)   ; GetSoftwareBitmapAsync
   WaitForAsync(SoftwareBitmap)
   DllCall(NumGet(NumGet(OcrEngine+0)+6*A_PtrSize), "ptr", OcrEngine, ptr, SoftwareBitmap, "ptr*", OcrResult)   ; RecognizeAsync
   WaitForAsync(OcrResult)
   DllCall(NumGet(NumGet(OcrResult+0)+6*A_PtrSize), "ptr", OcrResult, "ptr*", LinesList)   ; get_Lines
   DllCall(NumGet(NumGet(LinesList+0)+7*A_PtrSize), "ptr", LinesList, "int*", count)   ; count
   loop % count
   {
      DllCall(NumGet(NumGet(LinesList+0)+6*A_PtrSize), "ptr", LinesList, "int", A_Index-1, "ptr*", OcrLine)
      DllCall(NumGet(NumGet(OcrLine+0)+7*A_PtrSize), "ptr", OcrLine, "ptr*", hText) 
      buffer := DllCall("Combase.dll\WindowsGetStringRawBuffer", "ptr", hText, "uint*", length, "ptr")
      text .= StrGet(buffer, "UTF-16") "`n"
      ObjRelease(OcrLine)
   }
   Close := ComObjQuery(IRandomAccessStream, IClosable := "{30D5A829-7FA4-4026-83BB-D75BAE4EA99E}")
   DllCall(NumGet(NumGet(Close+0)+6*A_PtrSize), "ptr", Close)   ; Close
   ObjRelease(Close)
   Close := ComObjQuery(SoftwareBitmap, IClosable := "{30D5A829-7FA4-4026-83BB-D75BAE4EA99E}")
   DllCall(NumGet(NumGet(Close+0)+6*A_PtrSize), "ptr", Close)   ; Close
   ObjRelease(Close)
   ObjRelease(IRandomAccessStream)
   ObjRelease(BitmapDecoder)
   ObjRelease(BitmapFrame)
   ObjRelease(BitmapFrameWithSoftwareBitmap)
   ObjRelease(SoftwareBitmap)
   ObjRelease(OcrResult)
   ObjRelease(LinesList)
   return text
}



CreateClass(string, interface, ByRef Class)
{
   CreateHString(string, hString)
   VarSetCapacity(GUID, 16)
   DllCall("ole32\CLSIDFromString", "wstr", interface, "ptr", &GUID)
   result := DllCall("Combase.dll\RoGetActivationFactory", "ptr", hString, "ptr", &GUID, "ptr*", Class)
   if (result != 0)
   {
      if (result = 0x80004002)
         msgbox No such interface supported
      else if (result = 0x80040154)
         msgbox Class not registered
      else
         msgbox error: %result%
      ExitApp
   }
   DeleteHString(hString)
}

CreateHString(string, ByRef hString)
{
    DllCall("Combase.dll\WindowsCreateString", "wstr", string, "uint", StrLen(string), "ptr*", hString)
}

DeleteHString(hString)
{
   DllCall("Combase.dll\WindowsDeleteString", "ptr", hString)
}

WaitForAsync(ByRef Object)
{
   AsyncInfo := ComObjQuery(Object, IAsyncInfo := "{00000036-0000-0000-C000-000000000046}")
   loop
   {
      DllCall(NumGet(NumGet(AsyncInfo+0)+7*A_PtrSize), "ptr", AsyncInfo, "uint*", status)   ; IAsyncInfo.Status
      if (status != 0)
      {
         if (status != 1)
         {
            DllCall(NumGet(NumGet(AsyncInfo+0)+8*A_PtrSize), "ptr", AsyncInfo, "uint*", ErrorCode)   ; IAsyncInfo.ErrorCode
            msgbox AsyncInfo status error: %ErrorCode%
            ExitApp
         }
         ObjRelease(AsyncInfo)
         break
      }
      sleep 10
   }
   DllCall(NumGet(NumGet(Object+0)+8*A_PtrSize), "ptr", Object, "ptr*", ObjectResult)   ; GetResults
   ObjRelease(Object)
   Object := ObjectResult
}


GuiClose:
ExitApp
  

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 12 Mar 2022, 04:43

Here are two solutions which I have wanted to achieve.
1 solution, WIA which scan image from scanner and save it to .bmp format. This format is ideal for OCR engines especially when you scan in Grayscale. It have been very simple so I AM sending original script which have been created by just Me from Germany with very simple modiffication. And image is created. By The way it is even possible to rotate Image and it is possible to use prepared script which uses WIndows media OCR API. Script is very professionally made and it even release all objects correctly so there are no memory leaks or system instability at all.

Code: Select all

;                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   #NoEnv
FormatID := {BMP: "{B96B3CAB-0728-11D3-9D7B-0000F81EF32E}", PNG: "{B96B3CAF-0728-11D3-9D7B-0000F81EF32E}"
           , GIF: "{B96B3CB0-0728-11D3-9D7B-0000F81EF32E}", JPG: "{B96B3CAE-0728-11D3-9D7B-0000F81EF32E}"
           , TIF: "{B96B3CB1-0728-11D3-9D7B-0000F81EF32E}"}
DevTypes := {0: "UnspecifiedDeviceType"
           , 1: "ScannerDeviceType"
           , 2: "CameraDeviceType"
           , 3: "VideoDeviceType"}
ImgTypes := {0: "WIA_INTENT_NONE"
           , 1: "WIA_INTENT_IMAGE_TYPE_COLOR"
           , 2: "WIA_INTENT_IMAGE_TYPE_GRAYSCALE"
           , 4: "WIA_INTENT_IMAGE_TYPE_TEXT"}
WIA_IPS_PAGE_SIZE := "3097" ; Page Size
WIA_PAGE_A4     := 0 ; 8267 x 11692
WIA_PAGE_LETTER := 1 ; 8500 x 11000
WIA_PAGE_CUSTOM := 2 ; (current extent settings)
WIA_IPS_CUR_INTENT := "6146" ; Current Intent
WIA_INTENT_NONE                 := 0x00000000
WIA_INTENT_IMAGE_TYPE_COLOR     := 0x00000001 ; RGB
WIA_INTENT_IMAGE_TYPE_GRAYSCALE := 0x00000002 ; grayscale
WIA_INTENT_IMAGE_TYPE_TEXT      := 0x00000004 ; black & white
WIA_INTENT_MINIMIZE_SIZE        := 0x00010000
WIA_INTENT_MAXIMIZE_QUALITY     := 0x00020000
WIA_INTENT_BEST_PREVIEW         := 0x00040000
; ----------------------------------------------------------------------------------------------------------------------
; Image output format
FileExt := ""              ; BMP, GIF, JPG, PNG, TIF
; Device name, if required
DeviceName := ""
; Some device and image properties you may set
DevProps := {}
DevProps["3097"] := ""     ; page size (e.g. 0 = A4, 1 = letter, 2 = custom (current extend settings)
ImgProps := {}
ImgProps["3097"] := ""     ; page size (e.g. 0 = A4, 1 = letter, 2 = custom (current extend settings)
ImgProps["6146"] := 1      ; 1 = RGB color, 2 = grayscale, 4 = black & white
ImgProps["6147"] := ""     ; horizontal resolution (DPI)
ImgProps["6148"] := ""     ; vertical resolution (DPI)
ImgProps["6149"] := ""     ; horizontal start position in pixels
ImgProps["6150"] := ""     ; vertical start position in pixels
ImgProps["6151"] := ""     ; horizontal extend (width) in pixels
ImgProps["6152"] := ""     ; vertical extend (height) in pixels
; ----------------------------------------------------------------------------------------------------------------------
; Check the output format
If (FileExt = "")
   FileExt := "BMP"
If !FormatID.Haskey(FileExt) {
   MsgBox, 36, Scan, % "Output format " . FileExt . " is not supported!`n`n"
                     . "Supported formats are  BMP, GIF, JPG, PNG, TIF.`n"
                     . "The image will be scanned as BMP.`n`n"
                     . "Do you want to continue?"
   IfMsgBox, Yes
      FileExt := "BMP"
   Else
      ExitApp
}
; ----------------------------------------------------------------------------------------------------------------------
DevManager := ComObjCreate("WIA.Devicemanager")
DevCount := DevManager.DeviceInfos.Count
I := 0
Device := 0
While (I < DevCount) {
   DevInfo := DevManager.DeviceInfos(++I)
   If (DevInfo.Type = 1) { ; it's a scanner
      If (DeviceName = "") || (DeviceName = DevInfo.Properties("Name").Value) {
         Device := DevInfo.Connect
         Break
      }
   }
}
If !(Device) {
   MsgBox, Could not find a scanner device!
   ExitApp
}
Name := Device.Properties("Name").Value
Item := Device.Items(1)
; ----------------------------------------------------------------------------------------------------------------------
; Set the properties
For Prop, Value In DevProps
   If (Value <> "")
      Device.Properties(Format("{:04}", Prop)).Value := Value
For Prop, Value In ImgProps
   If (Value <> "")
      Item.Properties(Format("{:04}", Prop)).Value := Value
; Item.Properties("3097").Value := 100 ; A4
Image := Item.Transfer("{B96B3CAB-0728-11D3-9D7B-0000F81EF32E}") ; scan as BMP
Image.Savefile("data.bmp")
; MsgBox, % Image.FormatID
PicObj := WIA_GetImageBitmap(Image)
HBM := PicObj.Handle
Gui, Margin, 10, 10
Gui, Add, Pic, w600 h-1 vPic, HBITMAP:%HBM%
GuiControlGet, Pic, Pos
Gui, Show, , Device %DevName% (%PicW%*%PicH%)
Return
; ======================================================================================================================
; Retrieves the bitmap data of the image.
; Return values:
;     A new Picture object on success, otherwise false.
; Note:
;     To retrieve the HBITMAP handle for the returned object use object.Handle
; ======================================================================================================================
WIA_GetImageBitmap(ImgObj) {
   ; To retrieve the HBITMAP handle for the returned object use object.Handle
   Return (ComObjType(ImgObj, "Name") = "IImageFile") ? ImgObj.Filedata.Picture : True
}
; ======================================================================================================================
GuiClose:
ExitApp
  

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 12 Mar 2022, 05:49

And here is complete script which scan books and perform OCR on input images. The. authors of The crucial scripts are MR malcev and MR Just Me.
MR malcev is elite Autohotkey programmer as a Just Me. OCR script work excellently, fast and The script is very memory efficient.
Mr JustMe have created two very useful scripts. Device manager by using WIA and second script wwhich scan image by using scanner. So MR Justme and MR malcev are The authors of this cript in fact. I have only split two codes together and I have created very simple GUI by using Autogui. So MR malcev and MR Justme thank you for your programmers work which allow not only visually impaired users to have joy from book scanning and from performing OCR.
viewtopic.php?t=72674
And here is joyned code.

Code: Select all

#KeyHistory 0
ListLines Off
Process, Priority, , A
SetBatchLines, -1
SetKeyDelay, -1, -1
SetMouseDelay, -1
SetDefaultMouseSpeed, 0
SetWinDelay, -1
SetControlDelay, -1
SendMode Input
               #NoEnv
#Persistent                                                                                                                                
Gui Font, s9, Segoe UI
Gui Add, Button, gscanning, &Scan and OCR

Gui Show, w620 h420, Simple books reader
return
Scanning:
FormatID := {BMP: "{B96B3CAB-0728-11D3-9D7B-0000F81EF32E}", PNG: "{B96B3CAF-0728-11D3-9D7B-0000F81EF32E}"
           , GIF: "{B96B3CB0-0728-11D3-9D7B-0000F81EF32E}", JPG: "{B96B3CAE-0728-11D3-9D7B-0000F81EF32E}"
           , TIF: "{B96B3CB1-0728-11D3-9D7B-0000F81EF32E}"}
DevTypes := {0: "UnspecifiedDeviceType"
           , 1: "ScannerDeviceType"
           , 2: "CameraDeviceType"
           , 3: "VideoDeviceType"}
ImgTypes := {0: "WIA_INTENT_NONE"
           , 1: "WIA_INTENT_IMAGE_TYPE_COLOR"
           , 2: "WIA_INTENT_IMAGE_TYPE_GRAYSCALE"
           , 4: "WIA_INTENT_IMAGE_TYPE_TEXT"}
WIA_IPS_PAGE_SIZE := "3097" ; Page Size
WIA_PAGE_A4     := 0 ; 8267 x 11692
WIA_PAGE_LETTER := 1 ; 8500 x 11000
WIA_PAGE_CUSTOM := 2 ; (current extent settings)
WIA_IPS_CUR_INTENT := "6146" ; Current Intent
WIA_INTENT_NONE                 := 0x00000000
WIA_INTENT_IMAGE_TYPE_COLOR     := 0x00000001 ; RGB
WIA_INTENT_IMAGE_TYPE_GRAYSCALE := 0x00000002 ; grayscale
WIA_INTENT_IMAGE_TYPE_TEXT      := 0x00000004 ; black & white
WIA_INTENT_MINIMIZE_SIZE        := 0x00010000
WIA_INTENT_MAXIMIZE_QUALITY     := 0x00020000
WIA_INTENT_BEST_PREVIEW         := 0x00040000
; ----------------------------------------------------------------------------------------------------------------------
; Image output format
FileExt := "BMP"              ; BMP, GIF, JPG, PNG, TIF
; Device name, if required
DeviceName := ""
; Some device and image properties you may set
DevProps := {}
DevProps["3097"] := ""     ; page size (e.g. 0 = A4, 1 = letter, 2 = custom (current extend settings)
ImgProps := {}
ImgProps["3097"] := ""     ; page size (e.g. 0 = A4, 1 = letter, 2 = custom (current extend settings)
ImgProps["6146"] := 2      ; 1 = RGB color, 2 = grayscale, 4 = black & white
ImgProps["6147"] := "300"     ; horizontal resolution (DPI)
ImgProps["6148"] := "300"     ; vertical resolution (DPI)
ImgProps["6149"] := ""     ; horizontal start position in pixels
ImgProps["6150"] := ""     ; vertical start position in pixels
ImgProps["6151"] := ""     ; horizontal extend (width) in pixels
ImgProps["6152"] := ""     ; vertical extend (height) in pixels

; ----------------------------------------------------------------------------------------------------------------------
DevManager := ComObjCreate("WIA.Devicemanager")
DevCount := DevManager.DeviceInfos.Count
I := 0
Device := 0
While (I < DevCount) {
   DevInfo := DevManager.DeviceInfos(++I)
   If (DevInfo.Type = 1) { ; it's a scanner
      If (DeviceName = "") || (DeviceName = DevInfo.Properties("Name").Value) {
         Device := DevInfo.Connect
         Break
      }
   }
}
If !(Device) {
   MsgBox, Could not find a scanner device!
   ExitApp
}
Name := Device.Properties("Name").Value
Item := Device.Items(1)
; ----------------------------------------------------------------------------------------------------------------------
; Set the properties
For Prop, Value In DevProps
   If (Value <> "")
      Device.Properties(Format("{:04}", Prop)).Value := Value
For Prop, Value In ImgProps
   If (Value <> "")
      Item.Properties(Format("{:04}", Prop)).Value := Value
; Item.Properties("3097").Value := 100 ; A4
FileDelete, data.bmp

Image := Item.Transfer("{B96B3CAB-0728-11D3-9D7B-0000F81EF32E}") ; scan as BMP
Image.Savefile("data.bmp")
data :=% ocr("data.bmp", "cs")
Gui Add, Edit,Multi, %data%




ocr(file, lang := "FirstFromAvailableLanguages")
{
   static OcrEngineStatics, OcrEngine, MaxDimension, LanguageFactory, Language, CurrentLanguage, BitmapDecoderStatics, GlobalizationPreferencesStatics
   if (OcrEngineStatics = "")
   {
      CreateClass("Windows.Globalization.Language", ILanguageFactory := "{9B0252AC-0C27-44F8-B792-9793FB66C63E}", LanguageFactory)
      CreateClass("Windows.Graphics.Imaging.BitmapDecoder", IBitmapDecoderStatics := "{438CCB26-BCEF-4E95-BAD6-23A822E58D01}", BitmapDecoderStatics)
      CreateClass("Windows.Media.Ocr.OcrEngine", IOcrEngineStatics := "{5BFFA85A-3384-3540-9940-699120D428A8}", OcrEngineStatics)
      DllCall(NumGet(NumGet(OcrEngineStatics+0)+6*A_PtrSize), "ptr", OcrEngineStatics, "uint*", MaxDimension)   ; MaxImageDimension
   }
   if (file = "ShowAvailableLanguages")
   {
      if (GlobalizationPreferencesStatics = "")
         CreateClass("Windows.System.UserProfile.GlobalizationPreferences", IGlobalizationPreferencesStatics := "{01BF4326-ED37-4E96-B0E9-C1340D1EA158}", GlobalizationPreferencesStatics)
      DllCall(NumGet(NumGet(GlobalizationPreferencesStatics+0)+9*A_PtrSize), "ptr", GlobalizationPreferencesStatics, "ptr*", LanguageList)   ; get_Languages
      DllCall(NumGet(NumGet(LanguageList+0)+7*A_PtrSize), "ptr", LanguageList, "int*", count)   ; count
      loop % count
      {
         DllCall(NumGet(NumGet(LanguageList+0)+6*A_PtrSize), "ptr", LanguageList, "int", A_Index-1, "ptr*", hString)   ; get_Item
         DllCall(NumGet(NumGet(LanguageFactory+0)+6*A_PtrSize), "ptr", LanguageFactory, "ptr", hString, "ptr*", LanguageTest)   ; CreateLanguage
         DllCall(NumGet(NumGet(OcrEngineStatics+0)+8*A_PtrSize), "ptr", OcrEngineStatics, "ptr", LanguageTest, "int*", bool)   ; IsLanguageSupported
         if (bool = 1)
         {
            DllCall(NumGet(NumGet(LanguageTest+0)+6*A_PtrSize), "ptr", LanguageTest, "ptr*", hText)
            buffer := DllCall("Combase.dll\WindowsGetStringRawBuffer", "ptr", hText, "uint*", length, "ptr")
            text .= StrGet(buffer, "UTF-16") "`n"
         }
         ObjRelease(LanguageTest)
      }
      ObjRelease(LanguageList)
      return text
   }
   if (lang != CurrentLanguage) or (lang = "FirstFromAvailableLanguages")
   {
      if (OcrEngine != "")
      {
         ObjRelease(OcrEngine)
         if (CurrentLanguage != "FirstFromAvailableLanguages")
            ObjRelease(Language)
      }
      if (lang = "FirstFromAvailableLanguages")
         DllCall(NumGet(NumGet(OcrEngineStatics+0)+10*A_PtrSize), "ptr", OcrEngineStatics, "ptr*", OcrEngine)   ; TryCreateFromUserProfileLanguages
      else
      {
         CreateHString(lang, hString)
         DllCall(NumGet(NumGet(LanguageFactory+0)+6*A_PtrSize), "ptr", LanguageFactory, "ptr", hString, "ptr*", Language)   ; CreateLanguage
         DeleteHString(hString)
         DllCall(NumGet(NumGet(OcrEngineStatics+0)+9*A_PtrSize), "ptr", OcrEngineStatics, ptr, Language, "ptr*", OcrEngine)   ; TryCreateFromLanguage
      }
      if (OcrEngine = 0)
      {
         msgbox Can not use language "%lang%" for OCR, please install language pack.
         ExitApp
      }
      CurrentLanguage := lang
   }
   if (SubStr(file, 2, 1) != ":")
      file := A_ScriptDir "\" file
   if !FileExist(file) or InStr(FileExist(file), "D")
   {
      msgbox File "%file%" does not exist
      ExitApp
   }
   VarSetCapacity(GUID, 16)
   DllCall("ole32\CLSIDFromString", "wstr", IID_RandomAccessStream := "{905A0FE1-BC53-11DF-8C49-001E4FC686DA}", "ptr", &GUID)
   DllCall("ShCore\CreateRandomAccessStreamOnFile", "wstr", file, "uint", Read := 0, "ptr", &GUID, "ptr*", IRandomAccessStream)
   DllCall(NumGet(NumGet(BitmapDecoderStatics+0)+14*A_PtrSize), "ptr", BitmapDecoderStatics, "ptr", IRandomAccessStream, "ptr*", BitmapDecoder)   ; CreateAsync
   WaitForAsync(BitmapDecoder)
   BitmapFrame := ComObjQuery(BitmapDecoder, IBitmapFrame := "{72A49A1C-8081-438D-91BC-94ECFC8185C6}")
   DllCall(NumGet(NumGet(BitmapFrame+0)+12*A_PtrSize), "ptr", BitmapFrame, "uint*", width)   ; get_PixelWidth
   DllCall(NumGet(NumGet(BitmapFrame+0)+13*A_PtrSize), "ptr", BitmapFrame, "uint*", height)   ; get_PixelHeight
   if (width > MaxDimension) or (height > MaxDimension)
   {
      msgbox Image is to big - %width%x%height%.`nIt should be maximum - %MaxDimension% pixels
      ExitApp
   }
   BitmapFrameWithSoftwareBitmap := ComObjQuery(BitmapDecoder, IBitmapFrameWithSoftwareBitmap := "{FE287C9A-420C-4963-87AD-691436E08383}")
   DllCall(NumGet(NumGet(BitmapFrameWithSoftwareBitmap+0)+6*A_PtrSize), "ptr", BitmapFrameWithSoftwareBitmap, "ptr*", SoftwareBitmap)   ; GetSoftwareBitmapAsync
   WaitForAsync(SoftwareBitmap)
   DllCall(NumGet(NumGet(OcrEngine+0)+6*A_PtrSize), "ptr", OcrEngine, ptr, SoftwareBitmap, "ptr*", OcrResult)   ; RecognizeAsync
   WaitForAsync(OcrResult)
   DllCall(NumGet(NumGet(OcrResult+0)+6*A_PtrSize), "ptr", OcrResult, "ptr*", LinesList)   ; get_Lines
   DllCall(NumGet(NumGet(LinesList+0)+7*A_PtrSize), "ptr", LinesList, "int*", count)   ; count
   loop % count
   {
      DllCall(NumGet(NumGet(LinesList+0)+6*A_PtrSize), "ptr", LinesList, "int", A_Index-1, "ptr*", OcrLine)
      DllCall(NumGet(NumGet(OcrLine+0)+7*A_PtrSize), "ptr", OcrLine, "ptr*", hText) 
      buffer := DllCall("Combase.dll\WindowsGetStringRawBuffer", "ptr", hText, "uint*", length, "ptr")
      text .= StrGet(buffer, "UTF-16") "`n"
      ObjRelease(OcrLine)
   }
   Close := ComObjQuery(IRandomAccessStream, IClosable := "{30D5A829-7FA4-4026-83BB-D75BAE4EA99E}")
   DllCall(NumGet(NumGet(Close+0)+6*A_PtrSize), "ptr", Close)   ; Close
   ObjRelease(Close)
   Close := ComObjQuery(SoftwareBitmap, IClosable := "{30D5A829-7FA4-4026-83BB-D75BAE4EA99E}")
   DllCall(NumGet(NumGet(Close+0)+6*A_PtrSize), "ptr", Close)   ; Close
   ObjRelease(Close)
   ObjRelease(IRandomAccessStream)
   ObjRelease(BitmapDecoder)
   ObjRelease(BitmapFrame)
   ObjRelease(BitmapFrameWithSoftwareBitmap)
   ObjRelease(SoftwareBitmap)
   ObjRelease(OcrResult)
   ObjRelease(LinesList)
   return text
}



CreateClass(string, interface, ByRef Class)
{
   CreateHString(string, hString)
   VarSetCapacity(GUID, 16)
   DllCall("ole32\CLSIDFromString", "wstr", interface, "ptr", &GUID)
   result := DllCall("Combase.dll\RoGetActivationFactory", "ptr", hString, "ptr", &GUID, "ptr*", Class)
   if (result != 0)
   {
      if (result = 0x80004002)
         msgbox No such interface supported
      else if (result = 0x80040154)
         msgbox Class not registered
      else
         msgbox error: %result%
      ExitApp
   }
   DeleteHString(hString)
}

CreateHString(string, ByRef hString)
{
    DllCall("Combase.dll\WindowsCreateString", "wstr", string, "uint", StrLen(string), "ptr*", hString)
}

DeleteHString(hString)
{
   DllCall("Combase.dll\WindowsDeleteString", "ptr", hString)
}

WaitForAsync(ByRef Object)
{
   AsyncInfo := ComObjQuery(Object, IAsyncInfo := "{00000036-0000-0000-C000-000000000046}")
   loop
   {
      DllCall(NumGet(NumGet(AsyncInfo+0)+7*A_PtrSize), "ptr", AsyncInfo, "uint*", status)   ; IAsyncInfo.Status
      if (status != 0)
      {
         if (status != 1)
         {
            DllCall(NumGet(NumGet(AsyncInfo+0)+8*A_PtrSize), "ptr", AsyncInfo, "uint*", ErrorCode)   ; IAsyncInfo.ErrorCode
            msgbox AsyncInfo status error: %ErrorCode%
            ExitApp
         }
         ObjRelease(AsyncInfo)
         break
      }
      sleep 10
   }
   DllCall(NumGet(NumGet(Object+0)+8*A_PtrSize), "ptr", Object, "ptr*", ObjectResult)   ; GetResults
   ObjRelease(Object)
   Object := ObjectResult
}

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 13 Oct 2022, 06:50

Dear Autohotkey experts,
I Am helpless to force Switch and Case command to work as a Case sensitive commands. As a results, condition is true for lower case characters and also for The upper case characters.
So
The
or
the
Will be evaluated as The same words.
I Am using Autohotkey version 1.1.34.04 64 Bit release.
I Am running Windows 10 X64 with The latest update available.
Here is a little piece of A code which do not evaluate ccharacters by using case sensitivity.
An1 is label for Editbox so it will be executed when ever Editbox field will change its content.
SoundBeep indicates wrong answer. Which is technically really wrong until The user will not finish his answer.

Code: Select all

An1:
gui, submit, nohide
Switch
{
	case a1=word:MsgBox Good answer., %word%
 case a1 <> word: SoundBeep
}
return
Word variable is automatically filled with The good answer according to The previously chosen Listbox GUI element item index.
So issue is, that condition block is not case sensitive. And it is not acceptable for foreign languages and not only for such tasks.
Thank you for your help.

RussF
Posts: 1298
Joined: 05 Aug 2021, 06:36

Re: Help me I'm blind.

Post by RussF » 13 Oct 2022, 11:48

You are using the Switch construct totally incorrectly. Look at the docs and examples. Also, run the following code. Note that if you change StringCaseSense to Off, you will get different results.

Code: Select all

StringCaseSense, On

An1:
a1 := "Word"

Switch a1
{
  Case "word":
    MsgBox, This will display if case sensitivity is off

  Case "Word":
    MsgBox, This will display if case sensitivity is on
}

Russ

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 14 Oct 2022, 01:21

Thank you for your advice.

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 14 Oct 2022, 02:41

So is it possible to use Switch anc case command to work according to The variable content? Or is it only possible to use those commands when comparing real strings? I have thought, that if I turn Case sensitivity to on, that I will be able to correctly determine, if user has typed I AM or i AM. That only I AM will be evaluated as A right answer. So I fI have understood your correctly. I can not automatically evaluate by using The variable content. I must explicitly specify The string in "".

swagfag
Posts: 6222
Joined: 11 Jan 2017, 17:59

Re: Help me I'm blind.

Post by swagfag » 14 Oct 2022, 03:09

either do:

Code: Select all

An1:
	gui, submit, nohide

	oldCaseSense := A_StringCaseSense
	StringCaseSense On

	Switch a1
	{
	case word: MsgBox Good answer., %word%
	default: msgbox SoundBeep
	}

	StringCaseSense % oldCaseSense
return
or do:

Code: Select all

An1:
	gui, submit, nohide

	Switch
	{
	case a1 == word: MsgBox Good answer., %word%
	default: msgbox SoundBeep
	}
return

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 14 Oct 2022, 06:47

Dear MR swagfag,
You have helped Me very much. Thank you. This is what I have wanted. I have made a mistake, that I have not sent a representative part of AHK code. But you have perfectly understood my needs. I Am constructing a 100 % accessible text book for foreign language for visually impaired users. And I Am doing my best to minimize GUI complexity. As A result. If visually impaired user press arrow keys with foreign words list, Autohotkey play vocabulary audio record. Similar situation is for A dictate. == was The trick. Now, sSwitch and Case perfectly determine The case sensitivity. So even if user type several words with various combinations of lowercase or upper case characters good answer is determined correctly. So I can continue with my project smoothly thanks to your advice.

Janusz
Posts: 89
Joined: 18 Dec 2020, 17:47

Re: Help me I'm blind.

Post by Janusz » 13 Aug 2023, 04:53

Dear elite Autohotkey developers. No matter, if you are perfectly using The newest Autohotkey V 2 or older V 1.x. I have very big programmers plea addressed fo The most elite developers of this forum.
Abbyy Finereader is professional OCR software. Unfortunately, if visually impaired user want to create The professional documents converted by using OCR user must use propriate very expensive screen readers such as Jaws for Windows. Whych are using special ofscreen models by using special mirror display drivers.
But if visually impaired user use NVDA or other screen reader, special editable field in The GUI of Finereader can not be professionally used. COnverted image to OCR is displaied correctly. But screen reader read it content incorrectly. For example. Double spaces Are The part of readable words.
Does somebody of us think, that it would be extremely complex to extend build in Autohotkey command for reading text of A control by The way, that it would be possible to use this command to read The content of Abbyy Finereader text window char by char, word by words ETC?
My dream is to have a little screen reader specialized only on this specific app and only for its build in object class name with editable field with converted text from The graphic.
CDefObject:$FINEREADEREDITORCLASS$, Item:0, FilterColor:D77800, Attr:0
If somebody of us would be able to create a little Autohotkey script for this purpose, it would be perfect.
Sure, I Am aware, that it is not easy.
But Core Autohotkey programmer has excellent C language knowledge, even Assembly language knowledge.
So may be, that there is some chance to achieve.
Thank you very much for your help.

Post Reply

Return to “Ask for Help (v1)”