[AS]DisplayObjectContainerが内包しているDisplayObjectをすべてremoveChildする
人のソースからのメモ
DisplayObjectContainerが内包しているDisplayObjectをすべてremoveする処理を1行で。
whileは無限ループになるのが怖いから苦手意識あるなー
while(numChildren) removeChildAt(0);Tweet
人のソースからのメモ
DisplayObjectContainerが内包しているDisplayObjectをすべてremoveする処理を1行で。
whileは無限ループになるのが怖いから苦手意識あるなー
while(numChildren) removeChildAt(0);Tweet
一個前の記事でも書いたのだけど、
※ここで引っかかったのはフォントの指定。
フォント名を指定するときに、flashのヒストリパネルに表示されるjsflをそのまま使ったらフォントが反映されない。
たとえば、新ゴProのLを指定したいときには、
jsflには、setElementTextAttr(‘face’,’ShinGoPro-Light’);と表示されたのでそのままコピペしたら動作しない。
フォント名を取得するサンプルで取得したフォント名を使用すると上手くいった。
setElementTextAttr(‘face’,’A-OTF 新ゴ Pro L’);ってな感じになります。
この差異の原因はFlashが日本語版か英語版かってことなのかな、まぁよくわからん。
この現象は予想通りコンパイラに依存するっぽい。
FlashDevelop + Flex4SDKBeta1の組み合わせて、フォント指定でパブリッシュしてみると、
指定した、フォント名が、
A-OTF 新ゴ Pro Lでは反映されずに、
ShinGoPro-Lightだと反映された。
Flex4SDKは日本語仕様ではないから、日本語は認識しないのだね。
この辺は無理に日本語化しないでアルファベットに統一してくれたらわかりやすいと思うんだが。。。
製作経緯はこんなかんじ。
e-ラーニング系のコンテンツをタイムラインのアニメーションで製作中のこと。
静止テキストのモーショントゥイーンを大量にステージ配置。
雛形できたら大量生産するぜー、と5ファイルくらい作ってたところで、ここにきてテキスト関係の仕様の提示。
OH MY GOD(ってかちゃんと確認しないで作り始めたボクが悪い)
フォントサイズの変更、フォント色の変更、フォントの変更。。。
1個1個MCの中に入って静止テキストを変更するのめんどくさい。。。
1ファイルあたりMCが10個以上あるし。。。
!そうだ!これ、JSFLでできるんじゃね!?
とこんな感じ。
というわけで以前作ったソースをちょろっと変更してできたのはこんな感じ。
使い方
色を変更したいMCをライブラリで選択し(複数OK)、コマンドを実行。
それぞれ値を入力するダイアログがでるので値を入力すればOK。
※内部にテキストフィールドが1個だけあるようなシンボルの変更を想定してますのでそれ以外はどうなるかわかりません。。。
◆フォントサイズ変更
var doc = fl.getDocumentDOM();
var num = prompt(“フォントサイズを入力”, “18”);
var items = doc.library.getSelectedItems();
for (var i = 0; i < items.length; i++) {
doc.library.editItem(items[i].name);
doc.selectAll();
doc.setElementTextAttr('size',num);
doc.exitEditMode();
}
[/sourcecode]
◆フォント変更
[sourcecode language='js']
var doc = fl.getDocumentDOM();
var fontName = prompt("フォントを指定", "A-OTF 新ゴ Pro L");
var items = doc.library.getSelectedItems();
for (var i = 0; i < items.length; i++) {
doc.library.editItem(items[i].name);
doc.selectAll();
doc.setElementTextAttr('face',fontName);
doc.exitEditMode();
}
[/sourcecode]
※ここで引っかかったのはフォントの指定。
フォント名を指定するときに、flashのヒストリパネルに表示されるjsflをそのまま使ったらフォントが反映されない。
たとえば、新ゴProのLを指定したいときには、
jsflには、setElementTextAttr('face','ShinGoPro-Light');と表示されたのでそのままコピペしたら動作しない。
フォント名を取得するサンプルで取得したフォント名を使用すると上手くいった。
setElementTextAttr(‘face’,’A-OTF 新ゴ Pro L’);ってな感じになります。
この差異の原因はFlashが日本語版か英語版かってことなのかな、まぁよくわからん。
おまけ
色と、フォントと、サイズをいっぺんに変更できるやつ
◆いろいろいっぺんに変更
var doc = fl.getDocumentDOM();
var num = prompt(“フォントサイズを入力”, “18”);
var fontName = prompt(“フォントを指定”, “A-OTF 新ゴ Pro L”);
var color = prompt(“テキストの文字色を入力”, “#000000”);
var items = doc.library.getSelectedItems();
for (var i = 0; i < items.length; i++) {
doc.library.editItem(items[i].name);
doc.selectAll();
//サイズ変更
doc.setElementTextAttr('size',num);
//フォント変更
doc.setElementTextAttr('face',fontName);
//色変更
doc.setFillColor(color);
doc.exitEditMode();
}
[/sourcecode]
一応、一式ダウンロードはこちら。
製作経緯はこんなかんじ。
e-ラーニング系のコンテンツをタイムラインのアニメーションで製作中のこと。
静止テキストのモーショントゥイーンを大量にステージ配置。
あれ。。。よく確認してみたら仕様と違う。。。テキストの色間違ってるじゃん。。。
もう3ファイルくらい作ってて、静止テキストをラップしたMCが大量にあるよ。。。
1個1個MCの中に入って静止テキストの色を変更するのめんどくさい。。。
1ファイルあたりMCが10個以上あるし。。。
!そうだ!これ、JSFLでできるんじゃね!?
とこんな感じ。
そしてできたのはこんなかんじ。
使い方
色を変更したいMCをライブラリで選択し(複数OK)、コマンドを実行。
色を入力するダイアログがでるので色値を入力すればOK。
※MCだけじゃなくて、グラフィックとかボタンでもOK。
※静止テキストだけじゃなくて、シェイプの色も変わります。
var doc = fl.getDocumentDOM();
var items = doc.library.getSelectedItems();
ret = prompt("テキストの文字色を入力", "#000000");
//alert(ret);
for (var i = 0; i < items.length; i++) {
doc.library.editItem(items[i].name);
doc.selectAll();
doc.setFillColor(ret);
doc.exitEditMode();
}
当初はステージに配置してあるオブジェクトを選択して選択されたMCの中の色を変更しようとしてたのだけど、どうも上手くいかない。
でも良く考えたらこの動作ってライブラリ内のオブジェクトを変更するのと同じことだからこれでいいや、と。
欲しい人いるかはわからんけど一応zipでおいておこう。
シンボル内のオブジェクトの色変更する.jsfl
ここ最近は、Tweener絶ちをして、BetweenAS3マンセーな感じです。
で、Tweenerみたいにむービークリップのタイムラインのトゥイーンってできるのかなと思い軽くググってもサンプルでてこなかったので、Twitterで呟いてみたらできますよと教えてもらいましたー、
さすがー、すげー
トゥイーン対象がMovieClipの場合は、_frameで操作できるとのこと。
Tweenerと同じ感覚で使えますね。
こんな感じです。
import org.libspark.betweenas3.BetweenAS3;
import org.libspark.betweenas3.easing.*;
import org.libspark.betweenas3.tweens.ITween;
//_mcはタイムラインを持ったMovieClipでステージにおいてあるインスタンス名
BetweenAS3.to(_mc , {_frame:_mc.totalFrames}, 2, Expo.easeOut).play();
Tweet
製作なんてどうせ1人でやるから、Singletonなんて特に決めなくても、自分で覚えてるからいいや、と思ってました。
が、改めて、書籍:ActionScript3.0デザインパターンに書かれているSingletonの基本ソースを見て目からうろこが。。。
Singleton以外のところで感動したのでメモ。
今までのかなり無駄なことをしてたかも。
まずはSingletonクラスの基本ソース
package {
/**
* ...
* @author 393
*/
public class SingletonModel{
//自身をクラスメンバーとすることでどこからでもアクセスできるようにする。
private static var instance:SingletonModel;
//SingletonEnforcerを引数とすることで外からインスタンス化をできないように。
//※ただ、引数にnullを設定すれば外からでもインスタンス化できちゃうけど
public function SingletonModel(enforcer:SingletonEnforcer) {}
//このメソッドでSingletonModelのインスタンス(instance)の参照を取れる
public static function getInstance():SingletonModel{
//SingletonModel.instanceが生成されてなければ生成してから、
if (!SingletonModel.instance){
SingletonModel.instance = new SingletonModel(new SingletonEnforcer());
}
//returnでインスタンスを返す
return SingletonModel.instance;
}
}
}
class SingletonEnforcer {}
なにが目からうろこだったかって、自分自身をクラスメンバーとして保持するという方法。
これなら、どこのクラスからでも直接参照が取れるから、インスタンスの参照を持ちまわらなくてもいいのよね。
今までは、データモデルとなるようなクラスを、他のクラスに参照渡しても持ちまわってた。
これは一応上記書籍のMVCパターンを参考にしてたのだけど、MをSingletonにしちゃえば、VとかCをインスタンス化するときにわざわざ参照渡さなくてもいいじゃないのかな。
でも全部そうしちゃったらなんか落とし穴もありそうなきもするけど。
とりあえず、こんど使ってみる。
タイトルどおりの現象。
※PreloadSWF()については↓の記事がとてもわかりやすいです。
jp.ikekou.blog.Main:Progression 4.0.1 Public Beta 1.3 追加機能① PreloadSWFクラス
で、これを観ながら上記ブログとは少し変えながら試してみたのですが、タイトルのエラー発生。
変更した箇所はatCastLoadStart()の部分で、以下のソース
override protected function atCastLoadStart():void {
var loaderList:LoaderList = new LoaderList({
onProgress:function():void{
trace(this.percent)
}
});
loaderList.addCommand(
//new PreloadSWF()が遅い
new LoadSound(new URLRequest("sound/sample.mp3"))
,new PreloadSWF()
);
loaderList.execute();
}
結論から言うと、new PreloadSWF()の書く順番が重要。
↓このように書けばOK
override protected function atCastLoadStart():void {
var loaderList:LoaderList = new LoaderList({
onProgress:function():void{
trace(this.percent)
}
});
loaderList.addCommand(
//PreloadSWF()が早い
new PreloadSWF()
,new LoadSound(new URLRequest("sound/sample.mp3"))
);
loaderList.execute();
}
ちなみに参考にしたブログでは、loaderListの処理をatCastLoadStart()のaddCommand()内で行い、そこに追加している。
その際には、new PreloadSWF()の順番は影響はしないようす。
override protected function atCastLoadStart():void {
addCommand(
function(){
var loaderList:LoaderList = new LoaderList({
onProgress:function():void{
trace(this.percent)
}
});
loaderList.addCommand(
//new PreloadSWF()の位置は先でもエラーはでない
,new PreloadSWF()
new LoadSound(new URLRequest("sound/sample.mp3"))
);
this.parent.addCommand(loaderList);
}
);
}
command周りの処理の順番がイマイチちゃんと理解していないから、泥臭く検証しないとわからないのよね。。。
ガッツリ理解しとかないとな。。。
以前書いた、
[AS]FlashPlayer10ではTestFieldにアルファ処理可能、あとFlashPlayer9でのフォントの埋め込み方法の詳細
の記事の補足
上の記事では、フォントを指定する際に、TextFormat.fontに指定するフォント名を手動で調べないといけないと書いたけど、ライブラリに登録されたフォントから、さくっと取得することができるようだ。
//フレームアクション //ライブラリ内のフォントのリンケージ名 var class_name="font1"; var loadedFont:Font = new Font(); var LoadFontClass:Class=ApplicationDomain.currentDomain.getDefinition(class_name) as Class; Font.registerFont(LoadFontClass); loadedFont = new LoadFontClass(); //これがTextFormat.fontに指定するフォント名となる。 var font_name=loadedFont.fontName; //おまけ //テキストフォーマット var fmt:TextFormat=new TextFormat(); //フォント名を指定 fmt.font=font_name; fmt.size = 40; fmt.bold = false; //テキストフィールド作成 var tf:TextField=new TextField(); tf.embedFonts=true; tf.defaultTextFormat=fmt; tf.text="Test"; //表示 addChild(tf);
教えてくれたサイト:frasio report:[AS3]埋め込みフォントの盲点
Tweetあたりまえといっちゃあたりまえのことに躓いた。
var sp:Sprite = new Sprite(); sp.graphics.beginFill(0); sp.graphics.drawRect(0,0, 10, 100); var container:Sprite = new Sprite(); container.addChild(sp); sp.y = 300; this.addChild(container) container.addChild(sp) trace(container.height);//出力は400ではなく、100 //(containerはDisplayObjectContainerの機能しか果たしていないので)
ステージに手動でMCとか作ってるときには直感的に理解していたことだけど、ASで動的に作ってるときにはなぜか上記のようなときは400になるもんだと思ってた。
そんで高さを400にするためには以下のようにすればOK。
var sp:Sprite = new Sprite(); sp.graphics.beginFill(0); sp.graphics.drawRect(0,0, 10, 100); var container:Sprite = new Sprite(); container.graphics.drawRect(0,0,0,0);//大きさの無いものをdrawしておくだけでいいらしい container.addChild(sp); sp.y = 300; this.addChild(container) container.addChild(sp) trace(container.height);//出力:400
相対的な位置情報も含めて大きさを保持したい場合は単にアルファ0でのものを置こうかと思ったけど、大きさを指定しない状態でdrawするだけでいいようだ。
これは試してみてよかった。
厳密にいうとちょっと違うみたいだけどこんな感じ。
//文字列の全角/半角チェック関数。
//(文字列内の文字が全て半角の場合にtrueを返す)
function isAll1ByteChar(str:String):Boolean {
var countCharCode:Number = 0;
var isAll1Byte:Boolean = false;
for (var i:int = 0; i < str.length; i++) {
// 条件分岐
// 2010/01/27修正:半角カナ対応(のつもり)
if (str.charCodeAt(i)<=255 || str.charCodeAt(i)>=0xFF61 &amp;amp;&amp;amp; str.charCodeAt(i)<=0xFF9F) {
countCharCode+=1;
} else {
countCharCode+=2;
}
}
if(str.length == countCharCode) {
isAll1Byte = true;
}
return isAll1Byte;
}
var str1:String = "aaアaaa"
var str2:String = "あああああ";
var str3:String = "aaaaあbcs";
trace(isAll1ByteChar(str1));//出力:true
trace(isAll1ByteChar(str2));//出力:false
trace(isAll1ByteChar(str3));//出力:false
2010/1/27:コード修正:半角カナ対応(のつもり)
Tweet