AppleScript w/Objetive-C to convert numbers to words

Hello all!

I’m new to this forum, I’m a software developer. I had been working with Java but I just started to code for iOS devices so I needed to change my old computer for a Mac.

The problem at this moment is that I had been using excel to make my, hum… quotation (I guess that’s the word, my mother language is Spanish), and even when I have mostly translated all my usual formulas to numbers, there is one function I’m still missing. The thing is that I coded thas specific function as a macro in VBA, and numbers (AFAIK) can’t use macros.

So I need to convert a given figure to it’s word equivalent. I might say that there are some places over the Internet that you can do that and just copy and paste the result, but I thought that this was the perfect oportunity to learn some basics about Applescript, sadly I’m far from done.

I have been searching ways to do this, and found a specific function:

on convertNumberToWords(thisNumber)
	tell current application's NSNumberFormatter to ¬
		set resultingText to localizedStringFromNumber_numberStyle_(thisNumber, current application's NSNumberFormatterSpellOutStyle)
 	return (resultingText as string)
end convertNumberToWords

For what I read this is ASOC (AppleScript with Objective C), but when I call this function it send me this message:
error “NSNumberFormatter no entiende el mensaje “localizedStringFromNumber_numberStyle_”.” number -1708 from NSNumberFormatter (The Spanish part is: “Can’t understand the message”)

And that may be right, because at least for iOS that function is:

(NSString * nonnull)localizedStringFromNumber:(NSNumber * nonnull)num
numberStyle:(NSNumberFormatterStyle)localizationStyle

But it seems that I can’t call this function this way either. By the way, I tryied this with Automator as a work flow, but then I read that when I call ObjC from a script I need to save this as a Script Bundle and check AppleScript/Objective-C Library checkbox so for that I used the AppleScript Editor, so the next problem I can foresee is that I don’t have any idea how to use this as a service as I did with Automator, but I guess I need to read more about that later, but be prepared for more questions if I can’t solve that either :frowning:

When I discovered this forum, the first thing I did was searching for the full answer, an I found this topic: http://macscripter.net/viewtopic.php?id=32033

Nevertheless I’m still intrigued about how to call Objective C functions from a script, and use them as services. So if anyone can shed a little light on this matter I’ll be glad and very thankful.

Model: iMac 27-inch, Late 2013
AppleScript: 2.3.2
Browser: Chrome 43.0.2357.124
Operating System: Mac OS X (10.9)

Hello,

The method localizedStringFromNumber:numberStyle: requires an NSNumber object passed to it as a the first parameter. You need to convert your applescript number to an NSNumber before.

Also, the method is a class method (has a + sign before), therefore you need to use it like this:

tell current application's class "NSNumber" to set theNSNumber to numberWithInt_(thisNumber) -- I assume you are providing an integer here. Change the method according to the kind of number you need.
tell current application's class "NSNumberFormatter" to set theResultNSString to localizedStringFromNumber_numberStyle_(theNSNumber, current application's NSNumberFormatterSpellOutStyle)
set theResult to theResultNSString as string -- if you need to use it back in applescript, you need to coerce the NSString to an applescript string first.

Try it like this. I haven’t tested it, but it seems right to me. Report back here your results.

Browser: Safari 534.51.22
Operating System: Mac OS X (10.8)

Hi,

the syntax of the handler is correct, but in Mavericks you can’t call the handler directly in (Apple)Script Editor.
You need to save the script as script library with activated AppleScriptObjC option in ~/Library/Script Libraries

The whole procedure is described in the book of Shane Stanley or here

No: you never have to do any conversion when passing a parameter.

Again, no. Please, let’s not confuse a newcomer (and lurkers) with guesses where the code is so easy to test.

The OP’s code is fine, except for the missing:

use framework "Foundation"

However, his signature says he’s using Mavericks, and as Stefan points out, that means he has to save it as a Script Library, and call it from there.

Shane, I tried to help, not confuse anyone. I’ve always had better success converting things to ObjC objects before using a method, especially a class method. It’s based on my experience. Tried it your way before, was unstable. Maybe I was doing something wrong elsewhere, but I don’t see the harm in doing it my way. It still works, doesn’t it? Your way can’t be the only way?

I don’t know his level of knowledge, do you? He mentionned doing Java before and now doing iOS development. I’m assuming he’ll understand just fine or look it up. And it’s not a guess. I did not remember how to use a class method in ASOC, so I looked it up in your book.

I don’t mind being told I made a mistake, but I found your comments a bit harsh this morning, unecessarily.

Hex, please do it their way and ignore my post, I seem to be wrong, and I am sorry if I am. Good luck!

My apologies – I should have been more careful of how I framed my message.

Apologies accepted. :slight_smile:

Hello again

I appreciate your answers and points of view, and I apologize for not posting my solution before, but I was busy with my son’s birthday party.

So I followed Shane’s advice, so my code was:

use framework "Foundation"

on convertNumeroToPalabra(thisNumber)
	tell current application's NSNumberFormatter to ¬
		set resultingText to localizedStringFromNumber_numberStyle_(theNSNumber, current application's NSNumberFormatterSpellOutStyle)
	return (resultingText as string)
end convertNumeroToPalabra

I saved it as a Script Bundle, and I checked the AppleScriptObjC option.

So I was ready to make it a service and for that I used the following code:

on run {selectedText}
	tell script "Converter"
		return convertNumeroToPalabra(selectedText) as string
	end tell
end run

But for some reason it always converted to “missing value”. I tryied calling the script with a fixed parameter (convertNumeroToPalabra(11)) and it worked fine, So I tryied the solution of leonsimard, and I added:

tell current application's class "NSNumber" to set theNSNumber to numberWithInt_(thisNumber)

And it worked perfectly fine. I’m sure I’m the one to blame, because I’m just starting with AppleScript and I don’t want to disrespect Shane’s statement about that I never have to do any conversion, but without that conversion the script never worked.

So my final code was:

use framework "Foundation"

on convertNumeroToPalabra(thisNumber)
	tell current application's class "NSNumber" to set theNSNumber to numberWithInt_(thisNumber)
	tell current application's NSNumberFormatter to ¬
		set resultingText to localizedStringFromNumber_numberStyle_(theNSNumber, current application's NSNumberFormatterSpellOutStyle)
	return (resultingText as string)
end convertNumeroToPalabra

I still have some loose ends, how to handle input errors and for that I’ll start reading more in depth about AppleScript, so I can have a better understanding of what I’m doing. Meanwhile I really appreciate all the help you gave me.

Glad to hear you made it work. :slight_smile:

The reason is because you are passing selectedText, which is presumably a string, to a method that wants a number. So numberWithInit_ is forcing the coercion from text to number, which is just a long-winded way of saying “as integer”.

Change your code to actually pass a number:

		return convertNumeroToPalabra(selectedText as integer) as string

And you shouldn’t need the extra conversion step.

Thank you Shane, it makes sense now that you wrote it, coming from ObjC being a strongly typed language it seems plain logical, but for some reason I didn’t foresaw it. Practice I guess…

I will read the basics of AppleScript so I don’t need to solve everything by guessing and I’ll focus on validate the input. I find this forum very friendly and I hope that in time, I’ll be able to help too.