2.0에서 꽤 까다로웠던 기술인 런타임 폰트 공유(참고 URL)를 3.0에 와서는 훨씬 간단하게 구사할 수 있게 되었다.
그를 이용해 일반적인 Loader처럼 폰트 로드/공유할 수 있도록 만든 클래스가 SFont이다.
(내부적으로 (link)SLoader를 이용하므로 참고)
(참조 블로그 : http://blog.jidolstar.com/468)
- 사용법 : 폰트.swf의 파일경로와 라이브러리의 Font Class를 이용해 로드 후 .name 속성으로 폰트의 이름을 TextFormat에 적용하면된다.
import com.showjean.net.*; import flash.net.*; var sl:SFont = new SFont(); sl.addEventListener(Event.COMPLETE,completeHandler); sl.addEventListener(IOErrorEvent.IO_ERROR,__eventHandler); sl.addEventListener(ProgressEvent.PROGRESS, progressHandler); sl.load("assets/kroe0554.swf", "kroeger05_54"); function completeHandler(event:Event):void { trace(event); var tf:TextFormat=txt.getTextFormat(); var fn:String=sl.name; if (fn == null) { } else { tf.font=fn; txt.embedFonts=true; txt.defaultTextFormat=tf; txt.text="ABCDEFG12345 "+fn; } } function __eventHandler(event:Event):void { trace(event); } function progressHandler(event:ProgressEvent):void { trace("progressHandler: bytesLoaded=" + event.bytesLoaded + " bytesTotal=" + event.bytesTotal); }
- 로드될 공유용 폰트.swf파일을 만드는 법
1. 새 fla파일을 생성하고 라이브러리 메뉴>new Font... 를 선택한다.
2. 공유할 폰트를 고르고 Name을 적당히 입력한다.
3. 폰트가 라이브러리에 등록되었다면 Linkage...를 선택한다.
4. Export for ActionScript와 Export in first frame 을 체크하고 Class에 사용할 이름을 넣는다.
5. 컴파일 후 swf파일을 적당한 위치에 놓는다.
- SFont.as : 유저가 사용하는 주클래스로 proxy의 성격을 띤다.
/** * SFont - * * @author: showjean in http://showjean.com/works, mobile , mailto:showjean@hanmail.net * @version: 1.0.0 * @date: 2009.5.22. * * @comment: 유저가 사용하는 클래스, FontAsset의 proxy 성격을 가지고있다. */ package com.showjean.net{ import flash.events.*; public class SFont extends EventDispatcher { protected var fontAsset:FontAsset; function SFont() { } // _____________________________________________________ public /** * 폰트를 로드 * url: swf의 위치 * linkage: swf 라이브러리의 Font Class */ public function load(url:String,linkage:String):void { if (fontAsset == null) { fontAsset=FontAssetManager.getInstance().getFontAsset(url,linkage); // 폰트가 이미 로드된 경우 if (fontAsset.isComplete()) { dispatchEvent(new Event(Event.COMPLETE)); // 이미 로드에러인 경우 } else if (fontAsset.isError()) { dispatchEvent(new Event(IOErrorEvent.IO_ERROR)); } else { fontAsset.addEventListener(Event.OPEN,__eventHandler); fontAsset.addEventListener(Event.COMPLETE,__eventHandler); fontAsset.addEventListener(IOErrorEvent.IO_ERROR,__eventHandler); fontAsset.addEventListener(ProgressEvent.PROGRESS,__eventHandler); fontAsset.addEventListener(HTTPStatusEvent.HTTP_STATUS,__eventHandler); } } } /** * 로드를 중지 또는 제거(등록된 폰트가 제거되지는 않는다) */ public function close():void { dispose(); fontAsset=null; } /** * 등록된 폰트의 이름을 반환 */ public function get name():String { return fontAsset ? fontAsset.name : null; } // _____________________________________________________ protected protected function dispose():void { if (fontAsset) { fontAsset.removeEventListener(Event.OPEN,__eventHandler); fontAsset.removeEventListener(Event.COMPLETE,__eventHandler); fontAsset.removeEventListener(IOErrorEvent.IO_ERROR,__eventHandler); fontAsset.removeEventListener(ProgressEvent.PROGRESS,__eventHandler); fontAsset.removeEventListener(HTTPStatusEvent.HTTP_STATUS,__eventHandler); fontAsset.close(); } } // ____________________________________________________________ listener protected function __eventHandler(event:Event):void { if (event.type == Event.COMPLETE || event.type == IOErrorEvent.IO_ERROR) { dispose(); } dispatchEvent(event); } } }
- FontAsset : 폰트를 로드, 정보를 저장하는 클래스
/** * FontAsset - * * @author: showjean in http://showjean.com/works, mobile , mailto:showjean@hanmail.net * @version: 1.1.1 * @date: 2009.7.6. * * @comment: FontAssetManager에서 생성되는 클래스로, font.swf파일을 로드하고 fontname까지 저장하고 있는다. */ package com.showjean.net{ import flash.display.*; import flash.events.*; import flash.system.*; import flash.text.*; import flash.net.*; import flash.utils.*; public class FontAsset extends EventDispatcher { protected var __linkage:String; protected var __name:String; protected var loader:Loader; function FontAsset() { } // _____________________________________________________ public /** * url: swf의 위치 * linkage: swf 라이브러리의 Font Class * * >다른 도메인의 폰트.swf를 로드해 올경우 LoaderContext를 설정한다 * >crossdomain.xml이 설정되어 있어야한다. */ public function load(url:String, linkage:String):void { __linkage = linkage; loader = new SLoader(); // LoaderContext var context:LoaderContext=new LoaderContext(); context.checkPolicyFile=true; context.applicationDomain = ApplicationDomain.currentDomain; // 로컬에서 작동하지 않게 if ( Security.sandboxType == Security.REMOTE ) { context.securityDomain=SecurityDomain.currentDomain; } loader.contentLoaderInfo.addEventListener(Event.OPEN,__completeHandler); loader.contentLoaderInfo.addEventListener(Event.COMPLETE,__completeHandler); loader.contentLoaderInfo.addEventListener(IOErrorEvent.IO_ERROR,__completeHandler); loader.contentLoaderInfo.addEventListener(ProgressEvent.PROGRESS,__completeHandler); loader.contentLoaderInfo.addEventListener(HTTPStatusEvent.HTTP_STATUS, __completeHandler); loader.load(new URLRequest(url), context); } /** * 로드를 중지 또는 제거(등록된 폰트가 제거되지는 않는다) */ public function close():void { dispose(); } /** * 등록된 폰트의 이름을 반환 */ public function get name():String { return __name; } /** * 폰트로드가 완료되었는지 확인 */ protected var _isComplete:Boolean = false; public function isComplete():Boolean { return _isComplete; } /** * 폰트로드가 실패했는지 확인 */ protected var _isError:Boolean = false; public function isError():Boolean { return _isError; } // _____________________________________________________ protected protected function dispose():void { if (loader) { loader.contentLoaderInfo.removeEventListener(Event.OPEN,__completeHandler); loader.contentLoaderInfo.removeEventListener(Event.COMPLETE,__completeHandler); loader.contentLoaderInfo.removeEventListener(IOErrorEvent.IO_ERROR,__completeHandler); loader.contentLoaderInfo.removeEventListener(ProgressEvent.PROGRESS,__completeHandler); loader.contentLoaderInfo.removeEventListener(HTTPStatusEvent.HTTP_STATUS, __completeHandler); // 폰트를 등록한 후에는 swf파일이 필요없다. try { if (loader.content) { loader.unload(); } else { loader.close(); } } catch (error:Error) { trace(this, error); } loader = null; prevFontArr = null; //trace(this, "dispose......"); } } protected function getIndexByName(font:Font):int{ for (var i:int = 0; i < prevFontArr.length; ++i) { var item:Font = prevFontArr[i] as Font; if (item.fontName == font.fontName) { return i; } } return -1; } // ____________________________________________________________ listener protected var prevFontArr:Array protected function __completeHandler(event:Event):void { if (event.type == Event.OPEN) { prevFontArr = Font.enumerateFonts(false); } else if (event.type == Event.COMPLETE) { try { var className:String = getQualifiedClassName( loader.content ); // flash에서 new Font로 라이브러리에 등록한 파일일 경우. if (className == "flash.display::MovieClip") { var fontclass:Class = loader.contentLoaderInfo.applicationDomain.getDefinition(__linkage) as Class; Font.registerFont(fontclass); } else { // flex sdk로 폰트를 임베드한 파일일 경우(unicodeRange로 캐릭터 범위를 지정할 수 있다) // 자동 등록되므로 아무것도 하지 않는다. } // 때에 따라서 배열의 앞쪽 또는 뒤쪽으로 추가되어서 어느쪽으로 추가되었는지 판별 var arr:Array = Font.enumerateFonts(false); // 텍스트필드에 수동으로 임베드한 폰트들이 indexOf연산에 -1이 반환되어서 제대로 작동하지 않음 /*for each(var font:Font in arr) { if (prevFontArr.indexOf(font) == -1) { __name = font.fontName; break; } }*/ for each(var font:Font in arr) { if (getIndexByName(font) == -1) { __name = font.fontName; break; } } trace(this, "added font name: ", __name); } catch (e:Error) { trace(this, "error - Font.registerFont............ ", e.toString()); // 폰트 등록 에러일경우 다시 등록하거나, 폰트가 포함되지 않은 swf파일 } _isComplete = true; dispose(); } else if (event.type == IOErrorEvent.IO_ERROR) { _isError = true; dispose(); } dispatchEvent(event); } } }
- FontAssetManager : FontAsset을 관리하는 싱글톤 클래스
/** * FontAssetManager - * * @author: showjean in http://showjean.com/works, mobile , mailto:showjean@hanmail.net * @version: 1.0.0 * @date: 2009.5.22. * * @comment: SFont에서 이용하는 싱글톤 클래스로, FontAsset이 중복 생성되지 않도록 관리한다. */ package com.showjean.net{ public class FontAssetManager { private static var instance:FontAssetManager; protected var _fontsObject:Object=new Object(); // _____________________________________________________ singleton /** * 싱글톤 생성자 */ function FontAssetManager( singletonForce:SingletonForce ) { } /** * 싱글톤 클래스 접근 메서드 */ public static function getInstance():FontAssetManager { if ( !instance ) { instance = new FontAssetManager( new SingletonForce() ); } return instance; } // _____________________________________________________ public /** * url: swf의 위치 * linkage: swf 라이브러리의 Font Class * * url을 object의 속성으로 저장된 FontAsset은 같은 url에 대해서는 하나의 객체만 존재하게 된다. */ public function getFontAsset(url:String, linkage:String):FontAsset { var asset:FontAsset; if (_fontsObject[url] == undefined) { // 아직 로드전이라면 FontAsset생성, 로드 시작 asset = new FontAsset(); _fontsObject[url] = asset; try { asset.load(url, linkage); } catch (e:Error) { trace(this, e); } } else { // 로드중이거나 로드완료라면 asset = _fontsObject[url]; //trace(this, "이미 로드중... ", url); } return asset; } } } /** * @private * 싱글톤 패턴을 위한 클래스 */ class SingletonForce { }
'Flash > AS3.0' 카테고리의 다른 글
4096*4096 //2009/05/29 18:01 (0) | 2012.06.05 |
---|---|
SFont + 폰트 문자 범위 지정(Flex3 SDK) //2009/05/26 13:34 (0) | 2012.06.05 |
SLoader - 순차적 로더 //2009/04/19 23:07 (0) | 2012.06.05 |
navigateToURL이 팝업차단에 걸릴 때 //2009/05/08 16:00 (0) | 2012.06.05 |
RegExp 1 - 최단 일치 검색 //2009/04/29 14:41 (0) | 2012.06.05 |