Posts tagged "cs extension builder"

In my previous blog post, I presented a fairly complete extension panel for InDesign. This time, I’d like to step back a bit and talk about the process of developing an extension for three Creative Suite applications: Illustrator, InDesign, and Photoshop. We’ll be doing something pretty basic–drawing the same shape in all three applications. While we’re at it, we’ll create a framework we can use to draw any valid shape­. This framework will simplify and standardize the process of drawing a shape, and will work for almost any extension that needs to draw shapes.

In this example, we’ll create a generic extension that can run in any of the above applications, and we’ll keep our application specific code isolated from the overall workings of the extension.

It’s All in the (Application-Specific) Details

The trickiest part of this extension, in fact, is the application-specific code. Illustrator, InDesign, and Photoshop can all draw paths, but each of the applications has a slightly different way of performing the task. In all three applications, you can draw paths using the Pen tool, and the resulting shapes, from a scripting point of view, are made up of paths, which are, in turn, made up of path points. The names and the details of the scripting objects differ a bit between products. In Illustrator and Photoshop, for example, the basic drawing object is a pathItem; in InDesign, it’s a pageItem.

Next, the applications have different ways of dealing with measurement. We’ll need to use measurement values to specify horizontal and vertical coordinates if we’re going to position new path points in a document. In InDesign and Photoshop, you can change measurement units at any time; Illustrator, by contrast, always uses points when it’s being driven by a script. In this example, we’ll be using points, but, for your own scripts, you’ll need to convert measurement values to points before sending them to Illustrator.

In InDesign and Photoshop, path point coordinates are specified relative to the ruler zero point; in Illustrator, they’re specified relative to the lower-left corner of the artboard. Since the default location of the ruler zero point is the upper-left corner of the document in all three applications, this means that the paths in Illustrator will be upside down relative to the paths in the other programs, but we don’t need to worry about that right now.

Finally, Illustrator and InDesign have a number of “shortcuts” for drawing paths with specifc arrangements of points–rectangles, ellipses, regular polygons, etc. We’ll ignore those features in favor of a “one size fits all” drawing routine.

In this tutorial, I’ll present support routines that provide a consistent approach to drawing paths in these applications. The idea is to create a generic drawing function that you can use to build new creative effects (ornamental borders for certificates, for example) or wire into your new data driven graphics feature.

You can download the project here (note that this isn’t really a “finished” extension, it’s just a container for the drawing routines):

The MakeSideHeads example (download link below) shows how to create a fully functional InDesign CS5 panel using the Creative Suite Extension Builder and the CSAW and host adapter libraries for InDesign.

This extension demonstrates:

How to use CSXS events and event listeners.

How to use the host adapter library for InDesign to monitor and respond to application-specific events (i.e., events that are outside of the standard CXSX events)

One of the great benefits of working with the Flash/AIR environment, inside the Creative Suite, is how easy it makes tasks which would be significant challenges in C++. The geolocation sample is one example of this, but another is drag and drop.

This is something with a lot of potential benefit for developers, but (due to some limitations with the current environment) needs to be addressed in a specific way. To achieve this, we use the Flash NativeDragManager, triggered on a mouseDown listener added to our component like so:

Here, we have the option of what kind of data we load onto the clipboard (in this case it is a collection of files), and also, if we so desire, we can add an Image object which would be used as the thumbnail for transfer.

If you’d like to see this in action, we’ve created a project which allows files to be dragged from a filesystem tree view into InDesign. It also allows text to be dragged from InDesign to a box in the extension, and back, using the same mechanisms. You can find that here.

A few weeks back, we gave presentations to a Creative Suite developer summit in Seattle, quite a few of which were focused partly or exclusively on using Creative Suite Extension Builder and the Creative Suite SDK.

Bill Hensler, the VP and Chief Technologist for Adobe’s Creative and Interactive Solutions business unit, addresses the conference. As part of this, we demo some CS5 extensions built using Extension Builder and CS SDK.

Explains why and how you’d integrate Creative Suite with web services and provides examples of integrating with cloud services such as Flickr and Google Maps, and how to use XMP and other metadata to drive the service interaction.

Covers topics such as using the AIR 2.0 APIs (such as NativeProcess, ServerSocket and others) from a CS5 extension, persistence mechanisms such as SharedObject / CSXSPreferences, SQLite, FlexORM and localisation in both the bundle manifest and the SWF application.

Tips and tricks and practical advice on working with the different applications in Creative Suite CS5 and the nuances of targeting each application. Although the Creative Suite SDK goal is a unified extensibility story across CS applications, this presentation discusses the lay of the land and introduces app-specific tools, as well as the Host Adapter micro-SDK, and CSAWIDExporter, a tool for generating InDesign/InCopy ActionScript wrappers exactly matching the app DOM at point of generation.

Pointers on converting code to the Creative Suite SDK, showing how you can convert or leverage existing ExtendScript code, things to watch out for when taking existing Flex/AIR code over to Creative Suite SDK, and tips on converting C++ plugin code to use Creative Suite SDK, and the whys and hows of hybrid extensions.

As part of Adobe Creative Suite Developer Summit, May 3rd – 7th, 2010, there was a session entitled Integrating Creative Suite with Other Systems. The main intent of the session was to describe how the Flex/AIR platform can be used in conjunction with Adobe Creative Suite Extension Builder and Creative Suite ActionScript wrapper libraries, to make integrating Creative Suite CS5 with other systems- such as distributed, dynamic, enterprise data- relatively straightforward.

We gave a quick demo as part of the developer summit keynote, showing a CS5 extension called BasicAmfConnector that was written in two or three days. This shows how easy it can be to keep multiple desktop clients in sync and also how easy it can be to produce Creative Suite CS5 publications based on remote, dynamic data with LiveCycle Data Services on the backend. A re-recording of the demo is shown below.

This is based on a presentation at a recent Adobe Creative Suite Developer Summit in Seattle, 4th-7th May, 2010. You can review the presentation, Introduction to Creative Suite SDK, at http://my.adobe.acrobat.com/p71668025/.

Learn more about Adobe Creative Suite SDK and Adobe Creative Suite Extension Builder by visiting http://www.adobe.com/devnet/creativesuite/sdk/index.html, from where you can download Creative Suite SDK. You can obtain Extension Builder through some of the partner programs, for instance:

Using Creative Suite Extension Builder, have found that we can build extensions to run across several Creative Suite applications in days, which might have taken months to program when using the C++ plug-in APIs. You can find documentation about Extension Builder at http://cssdk.host.adobe.com/sdk/1.0/docs/WebHelp/suitesdk.htm

Creative Suite Extension Builder is an integrated development environment for creating CS5 extensions; these extensions are mini-AIR applications, which can execute in several Creative Suite applications use the AIR 2.0 API. Creative Suite Extension Builder makes it as easy to write extensions that run in a Creative Suite CS5 application, as it is- using Adobe Flash Builder- to write a Flex application to run in the browser or an AIR application to run on the desktop.

Many teams within Adobe have contributed to the Adobe Creative Suite Extension Builder and Creative Suite SDK efforts; core technology pieces have come from the Adobe AIR, Adobe Flash and Adobe Core Technology teams, as well as Suite Technology- it really has been a distributed, collaborative effort. Our team has been most closely involved in defining what the developer experience should be and delivering the tooling that we have called Extension Builder, which is a commercial product. We have also produced the Creative Suite SDK, which is a set of libraries, documentation and resources you can use to write a CS5 extension, although without Extension Builder, it is rather more painful and involved. Creative Suite SDK is to Extension Builder as Flex SDK is to Flash Builder.

Problem

Whilst you can do incredible things with C++ API to some of the products in Creative Suite, and C++ typically offers the deepest integration with the Creative Suite products, you may find points of pain when you develop for multiple applications within Creative Suite prior to CS5. For instance, you will find that you have to use different IDEs on Mac and Windows- Microsoft Visual Studio on one, XCode on the other. You will find that you need to use different user interface frameworks across the Creative Suite applications- sometimes without GUI editors to design your UI. Also there can be detailed differences in the plugin architecture across applications that make it challenging to share code between plugins targeting different applications. It can also take a fair amount of time to implement features such as say integration of one Adobe product with a backend system, such as a relational database; for instance, to connect Adobe InDesign up to an external system via the C++ API to InDesign can take weeks or months to implement.

Even within the scripting layer, where the development is less challenging, you will see a dichotomy between some products that use the ExtendScript engine (like Photoshop, Illustrator, InDesign) and others that use the SpiderMonkey JavaScript engine (like Dreamweaver or Flash Pro). Whilst the ExtendScript hosts have a reasonably capable IDE in the ES Toolkit with a source level debugger, you’ll find that you don’t have such a nice IDE for the SpiderMonkey hosts.

Another missing piece here- both in the C++ layer and scripting layers- is a set of cross-platform, highly capable APIs to integrate with other systems, perhaps over a network- say, make HTTP requests to a cloud-based service, or call a web-service via SOAP, or interact with an enterprise backend system.

Solution

When you’re building Flex apps to run in the browser or AIR applications to run in the desktop, because you can use the rich set of components in the Flex framework to build your user interface and the splendid user interface / GUI editor in Flash Builder’s Design view to create, wire up and refine your user interface- also you can customize its look and feel to an amazing extent, especially if you work with competent designers using Adobe Flash Catalyst, and can translate their intent into a richly skinned user interface.

So we thought, if we could bring some of the Flex/Flash/AIR developer ecosystem goodness to developing extensions for Creative Suite, we could eliminate some of the points of pain- fragmentation of the UI frameworks or lack of a capable GUI editor for most Creative Suite applications, say.

The other major benefit to us developers of the Flex/Flash/AIR approach is that all of a sudden, if you’re writing a Flex/AIR extension for CS5, it becomes almost trivial to integrate Creative Suite apps with other systems- the Flex messaging APIs make it easy to integrate with web services over SOAP or HTTP, or communicate over AMF with Adobe systems like Live Cycle or my personal favourite, Live Cycle Data Services, Adobe Blaze DS (Community edition of LCDS). Adobe LiveCycle in turn comes with a fabulous range of enterprise connectors, and makes it relatively easy to integrate

Another major strategic objective for CS5 and this Flash/AIR extensibility model is to move away from siloed, monolithic desktop applications that have common branding but not much else in common, to desktop applications that are tied in with backend services in compelling ways, which deliver real value to Creative Professionals and other users of Adobe software. Rather than desktop software, you’ll find in CS5 that there is real progress to the software-and-services vision, with extensions like CS5 Comment and Review and the offerings in CS5 Live such as Browser Lab already bringing real value to creative professionals.

In addition to C++ and traditional scripting development, with Adobe Creative Suite CS5, the Creative Suite ActionScript Wrapper (CSAW) libraries and Extension Builder, you can now use the Flex/Flash/AIR platform to integrate with and extend Creative Suite CS5. Creative Suite CS5 applications have an embedded AIR 2.0 runtime, with a component that loads CS5 (Creative Suite eXtensible Services or CSXS) extensions, which are like mini-AIR applications. Extension Builder makes it quick and easy to develop, deploy, debug, package and publish these CS5 (CSXS) extensions.

One key point to note is that C++ extensibility is not going away- however, we do want to complement the traditional extensibility of the applications with extensibility based on Flex/Flash/AIR. So we wanted to enable you to develop hybrid solutions, where part of your logic could be written in C++ and perhaps user interface components and other pieces in Flex/AIR. You can mix and match environments to develop most efficiently; for example, you may want to write user interface in Flex/ActionScript and call through to C++ code from your ActionScript, and there are different options you can take.

To implement the objectives, we made a conscious decision to invest more heavily in developer tools, focusing on the overall developer experience, and of course building on the Flash Builder/ Eclipse platform. Eclipse itself has well-defined extension points and makes it relatively easy to contribute new developer tools, and we have found that it is possible to extend the Flash Builder environment and make it as easy to write extensions for Creative Suite apps, as it is to write Flex/Flash apps to run in the browser or write AIR apps to run on the desktop.

This new emphasis on Flex/Flash/AIR based extensions is part of a long-term approach to enable developers to extend Creative Suite more easily, and make it much easier and quicker to integrate Creative Suite with a range of other systems. This blog will let you access several demos, which highlight exactly how quick and easy it can be to write code that runs in several Creative Suite applications, and exactly how easy Creative Suite Extension Builder makes it to develop, debug and deploy extensions across multiple Creative Suite applications.

Software and Services

Adobe Creative Suite Extension Builder targets professional Creative Suite developers looking to minimise their development costs and reduce time-to-market for their extensions, while delivering maximum functionality to their customers.

When you develop a Creative Suite extension (based on the AIR/Flex platform), your code can run in multiple Adobe Creative Suite desktop applications, so that you can integrate your own services with the Creative Suite and/or extend Creative Suite applications in novel and innovative ways. To do this without developing a CS5 extension, you would need to master a range of quite different plug-in APIs, or else write code that would execute only within hosts that provide a scripting interface and even then find that you need slightly different scripting languages in different products or have less than ideal debugging support.

Adobe Creative Suite Extension Builder allows developers to transcend these limitations, by allowing you to develop, debug and deploy a single plug-in that can execute in multiple Adobe Creative Suite applications, using a single programming language (ActionScript) throughout, using the powerful Flash debugger and design view built into Adobe Flash Builder.

CS5 extensions run in an embedded AIR 2.0 runtime, allowing you to make use of AIR APIs and leverage the Flex ecosystem. The development environment also provides Creative Suite ActionScript Wrapper (CSAW) libraries, which provide efficient access to the Document Object Model (DOM) of CS5 applications such as Adobe InDesign, Adobe Illustrator and Adobe Photoshop.

Using Adobe Creative Suite Extension Builder, integrating Creative Suite with other systems becomes a matter of days or hours; hitherto, it would have taken considerable effort to connect products in Creative Suite CS5 to enterprise-class backends, web services, and other dynamic, remote datasources. It also becomes easy to build mash-ups between remote systems, capitalizing on the elegance and efficiency of the Flex API, tight integration with Creative Suite CS5 through Creative Suite ActionScript wrapper (CSAW) libraries and other Flex libraries provided in the tooling.

Adobe Creative Suite SDK consists of a set of ActionScript libraries, documentation and other resources that make it possible to build CS5 extensions, which can be loaded in multiple Creative Suite applications. Developers can include these ActionScript libraries in their projects and create cross-application extensions, which leverage the Flex platform and the AIR 2.0 API, as well as efficiently access the document object model (DOM) of Creative Suite applications through an ActionScript API, using Creative Suite ActionScript (CSAW) wrapper libraries.

This post is going to walk through creating a CS Extension which checks grammar in InDesign. To achieve this, we’ll be using an Adobe Labs technology called Alchemy. If you’re not familiar, Alchemy is a tool that lets you compile C/C++ code into ActionScript bytecode. That means you can efficiently call into your C/C++ code from a pure ActionScript solution. This is especially exciting in the context of the Creative Suite because many developers already have a huge amount of existing code in C/C++. Here’s a brief demo:

After Alchemy is set up, we next need to download an open-source C library called Link Grammar, you can get the source from here. While the library has plenty of features, we’ll just be using it to tell whether a sentence is grammatically correct or not. To call into this C library from ActionScript we need to define an interface that Alchemy can understand. We define this interface in the C code’s main function. Link Grammar defines a sample main in src/parse.c; replace it with this one, which defines the interface to Alchemy. Here are some magical lines to note:

This tells Alchemy that we have two C functions we want to expose to ActionScript; setup and isThisGrammar. Now all we have to do is flesh out these functions. For example, here’s our isThisGrammar function:

This function first reads in a string passed from ActionScript and stores it in the variable val. We then pass val into the Link Grammar library. Based on the result, we return a Boolean to ActionScript telling it whether or not this sentence is grammatically correct. Notice, because we’re in C-land we have to keep in mind memory management (e.g. releasing the sentences when we’re done).

Compiling the library

Now that our interface is defined, let’s compile the C code into a swc. Since Alchemy uses a modified version of gcc, we pass it the compiler flag “-swc”. In the Link Grammar Makefile, we need only to change the rule which builds the binary so that it reads:

${BIN}/parse: ${OBJECTS}

${CC} ${CLDFLAGS} ${OBJECTS} -swc -o parse.swc

Running “make” from the command line will generate parse.swc. Easy as that!

From the ActionScript side

In most Alchemy use cases, all we have to do is initialize the C library and then call into the interfaces we defined:

However, it’s slightly more complex in our case. Alchemy requires that you pass any files needed by the C code as a byte array to the loader before calling your interfaces. Because the C code requires access to the file system (to read the dictionary, grammar rules, etc.), we’re going to need a function something like this:

And that’s all there is to it. To compile the CS Extension, generate the swc and copy it into the libs/ folder. At runtime, make sure you have the contents of Link Grammar’s data/ folder (which includes 4.0.dict, words/, etc.) copied onto the desktop.

If you are developing extensions for Creative Suite CS5, you might want to adapt your software to your audience based on their language or specific region. The Creative Suite host applications have been localised to many languages and now you can also localise your extensions so your users will be able to interact with them in their native or preferred language.

Adding multiple locale support doesn’t have to increase your engineering effort. This cookbook recipe explains you how you can localise not only your extension user interface but also the extension configuration.

There is also a sample that puts in practice the steps explained in the cookbook recipe. This image below shows how the same extension can be localised to different languages and also how we can change it’s configuration based on specific locales. The same sample extension is running in an English version of Illustrator, a Japanese version of Flash Pro and a Spanish version of Photoshop.

If you are using Extension Builder, you can download the “Localised” sample by selecting:

As part of the Creative Suite Developer Summit we’ve been showing off some sample code that illustrates just how easy certain workflows become when you move into Flash. One of these, that was shown at the session on Connecting the Creative Suite to Web Services (go here to watch), illustrates how you can connect up the Creative Suite to Google Maps and Flickr.

This sample shows an extension built to run in Photoshop, InDesign and Bridge CS5 (and could easily be extended to any product in the Suite). It connects to Google Maps to show location information, and Flickr to show relevant images – with the data used to power those searches customised based on the application the extension runs in. So, in Photoshop this will check the geolocation of the current image (extracted via XMP) and show the images taken nearby. In InDesign it will instead take the location from the machine’s IP address and search based on keywords using the user’s last sentence. Bridge provides a combination of both, where location comes from the XMP and the keywords come from the image tags.

The best part of this is how cheap integration is with these external systems. Google Maps Flex SDK, for example, requires a single MXML entry to create a map, with an additional call into that object being enough to change the positioning of the map;

For Flickr there are plenty of SDK options available, including one for ActionScript, but for the purposes of this I’ve chosen to roll my own calls. This uses a network communications library provided with Extension Builder, which lets us use the minimal amount of code to make a quick call across the network to retrieve the relevant data;

If you’d like to try this out, you can grab the Extension Builder project here. You’ll need to drop the Google Maps Flex SWC (available here) into the libs folder, and enter your own API key for both the Maps service and Flickr.

I’ve also made it available as a ZXP (here), and as a zip for Bridge (here) the contents of which should be unzipped into your Bridge CS5 user startup scripts folder.