Mailing Lists: Apple Mailing Lists

Image of Mac OS face in stamp
 
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Implementing a new command



On Nov 19, 2007, at 11:14 AM, Christiaan Hofman wrote:

The command seems to be send to a scriptable object of class "order", and that one is not registered in the .sdef to respond to the complete command.

You are right, and this was a bit of a concern to me, but I think I am following the way apple says to do it for subclasses that respond to commands. Below comes from:
http://developer.apple.com/documentation/Cocoa/Conceptual/ScriptableCocoaApplications/SApps_script_cmds/chapter_8_section_3.html#//apple_ref/doc/uid/20001242-SW2

In its sdef, Sketch also adds a responds-to element to the rectangle class (rectangles are the only graphics that can be rotated by this command).
            <responds-to name="rotate">

                <cocoa method="rotate:"/>

            </responds-to>

This element definition specifies that for a rotate command, Cocoa scripting should call the rotate: method of the rectangle object to be rotated.

This mirrors my situation (but see below). Only those orders that are scheduled orders should respond to a complete command. But for a test, I did duplicate the responds-to section in my order class and my complete: method did get called! But this is not good, because it allowed any order to get sent the complete command, not just scheduled orders. What I want is exactly what Apple showed with the rotate command.

From what you write I cannot tell where the error is. I don't know your script,

Sorry, a simple version is:

tell application "Scheduler"
activate


set theOrder to scheduled order id "24778"


complete theOrder


end tell

and I don't know your object specifiers.

Sorry, here is my only one, in Order.m:

- (NSScriptObjectSpecifier *)objectSpecifier
{
unsigned index = [[[NSApp delegate] orders] indexOfObjectIdenticalTo:self];
if (index == NSNotFound) 
{
NSLog (@"objectSpecifier couldn't find: %@", self);
return nil;
}


NSLog (@"objectSpecifier: %@", self);

NSScriptClassDescription * containerClassDesc = (NSScriptClassDescription *)[NSScriptClassDescription classDescriptionForClass:[NSApp class]];
return [[[NSUniqueIDSpecifier alloc] initWithContainerClassDescription:containerClassDesc
    containerSpecifier:nil 
   key:@"orders"
      uniqueID:[self pNumber]] autorelease];
}

I don't think you can use the same Cocoa class for different scripting classes, as you do. It confuses the system. You should use subclasses.

OK this may be the key. I do understand what you are saying, and it is very observant of you to pick this out. With Apple's example, they have graphic as a superclass to rectangle.

But in my situation, I have my Cocoa Order class being used for orders and scheduled orders in AS. It will pain me to subclass orders to make a scheduled order in my Cocoa application but maybe it's not so bad? Or maybe there is some other way I can approach it. Maybe make my complete: method check to make sure it is a scheduled order and return an applescript error if it isn't. Would that be reasonable?

In any case, I think this is the cause of my problem. Thank you for helping me once again. You are officially the most knowledgeable AppleScript Implementor I know  :) I hope I can help some other newbie out some day.

On 19 Nov 2007, at 4:40 PM, Paul Bruneau wrote:

I am so thankful for the kind help I have received from this list. It has helped me to much better understand implementing Applescript in my app. It was such good help that I felt sure that my new command would work eventually, but it just won't.

I would like to describe what I have done and see if anyone spots anything missing. I am using the steps outlined on Script Commands Overview, although I have read through the entire guide many times looking for clues:

My app is currently OK supporting getting and setting properties via applescript, and I have successfully implemented the Core command "make" to create new objects. Now I want to create a new object-first command called "complete".

1. In my sdef, I provided a responds-to entry for my scheduled order class (a subclass of order) that is meant to handle the command:

<class name="scheduled order" code="SORD" inherits="order" description="An order that is currently scheduled for production.">
<cocoa class="Order"/>

<responds-to name="complete">
<cocoa method="complete:"/>
</responds-to>
</class>

2. Since it's a new applescript command, I added a command element to my sdef. The following snippet appears directly below the above one, inside my app's custom suite:

<!-- Commands -->

<command name="complete" code="SK3DCOMP" description="Complete an object to indicate that work has been completed.">
<direct-parameter type="order"/>
</command>

</suite>

</dictionary>

Here is the whole sdef if you'd like to see it:

3. In my implementation of my scriptable class (Order), I implemented the named method:

from Order.h:
- (void)complete:(NSScriptCommand *)command;

from Order.m:
- (void)complete:(NSScriptCommand *)command;
{
NSLog(@"Order complete: %@", command);

NSLog (@"arguments: %@", [command evaluatedArguments]);
NSLog (@"receivers: %@", [command evaluatedReceivers]);
NSLog (@"direct param: %@", [command directParameter]);
}

I'm not subclassing NSScriptCommand because I believe for this simple object-first command I don't need to.

When I call "complete myOrder" in script editor, I get "Scheduler got an error: NSReceiversCantHandleCommandScriptError"

2007-11-19 10:09:54.500 Scheduler[571] Command: Intrinsics.get
Direct Parameter: <NSUniqueIDSpecifier: scheduledOrders with an ID of "24778">
Receivers: <NSUniqueIDSpecifier: scheduledOrders with an ID of "24778">
Arguments: {}
2007-11-19 10:09:54.500 Scheduler[571] key checked = scheduledOrders
2007-11-19 10:09:54.500 Scheduler[571] key checked = scheduledOrders
2007-11-19 10:09:54.500 Scheduler[571] key checked = scheduledOrders
2007-11-19 10:09:54.500 Scheduler[571] Property Value: 24778 (5)
2007-11-19 10:09:54.501 Scheduler[571] objectSpecifier: 24778 (7)
2007-11-19 10:09:54.501 Scheduler[571] Result: <NSAppleEventDescriptor: 'obj '{ 'from':''null''(), 'want':'Ordr', 'form':'ID  ', 'seld':'utxt'($32003400370037003800$) }
2007-11-19 10:09:54.516 Scheduler[571] Command: Scheduler Suite.complete
Direct Parameter: <NSUniqueIDSpecifier: orders with an ID of "24778">
Receivers: <NSUniqueIDSpecifier: orders with an ID of "24778">
Arguments: {}
2007-11-19 10:09:54.516 Scheduler[571] key checked = orders
2007-11-19 10:09:54.517 Scheduler[571] key checked = orders
2007-11-19 10:09:54.517 Scheduler[571] key checked = orders
2007-11-19 10:09:54.517 Scheduler[571] Result: (null)
2007-11-19 10:09:54.517 Scheduler[571] Error: 4 "NSReceiversCantHandleCommandScriptError"

"key checked" is a log entry that is in my application: delegateHandlesKey: method which resides in my AppController class which is the app's delegate. I don't know why it gets called three times in a row, but here is the method in case it looks crazy to anyone:

- (BOOL)application:(NSApplication *)app
 delegateHandlesKey:(NSString *)key;
{
NSLog(@"key checked = %@", key);

NSSet * keys = [NSSet setWithObjects:@"scheduledOrders", @"orderEntryOrders", @"finishedOrders", @"orders", nil];

if ([keys member:key] != nil)
{
return YES;
} else {
return NO;
}
}

I am thankful for any ideas.
 _______________________________________________
Do not post admin requests to the list. They will be ignored.
Applescript-implementors mailing list      (email@hidden)
Help/Unsubscribe/Update your Subscription:
http://lists.apple.com/mailman/options/applescript-implementors/email@hidden

This email sent to email@hidden

References: 
 >Implementing a new command (From: Paul Bruneau <email@hidden>)
 >Re: Implementing a new command (From: Christiaan Hofman <email@hidden>)



Visit the Apple Store online or at retail locations.
1-800-MY-APPLE

Contact Apple | Terms of Use | Privacy Policy

Copyright © 2007 Apple Inc. All rights reserved.