//opacity_Enhancer.jsx for PhotoshopCS or later/  by （z-）2012.01.19
//CSで使用する場合は拡張子を.jsに変更してください

function dupLay(){ //レイヤー複製_新規ドキュメント
	var mk = charIDToTypeID( "Mk  " );
	var desc = new ActionDescriptor();
	var nul = charIDToTypeID( "null" );
	var ref1 = new ActionReference();
	var dcmn = charIDToTypeID( "Dcmn" );
	ref1.putClass( dcmn );
	desc.putReference( nul, ref1 );
	var nm = charIDToTypeID( "Nm  " );
	desc.putString( nm, "Target Document" );
	var usng = charIDToTypeID( "Usng" );
	var ref2 = new ActionReference();
	var lyr = charIDToTypeID( "Lyr " );
	var ordn = charIDToTypeID( "Ordn" );
	var trgt = charIDToTypeID( "Trgt" );
	ref2.putEnumerated( lyr, ordn, trgt );
	desc.putReference( usng, ref2 );
	executeAction( mk, desc, DialogModes.NO );
	}

function dupChnl(myChnl){ //演算
	var mk = charIDToTypeID( "Mk  " );
	var desc1 = new ActionDescriptor();
	var nw = charIDToTypeID( "Nw  " );
	var chnl = charIDToTypeID( "Chnl" );
	desc1.putClass( nw, chnl );
	var usng = charIDToTypeID( "Usng" );
	var desc2 = new ActionDescriptor();
	var ttt = charIDToTypeID( "T   " );
	var ref1 = new ActionReference();
	var trgt = charIDToTypeID( myChnl ); //ターゲット（選択）チャンネルを指すらしい
	ref1.putEnumerated( chnl, chnl, trgt );
	desc2.putReference( ttt, ref1 );
	var src2 = charIDToTypeID( "Src2" );
	var ref2 = new ActionReference();
	ref2.putEnumerated( chnl, chnl, trgt );
	desc2.putReference( src2, ref2 );
	var clcl = charIDToTypeID( "Clcl" );
	desc1.putObject( usng, clcl, desc2 );
	executeAction( mk, desc1, DialogModes.NO );
	}

function thrsFunc(val){ //2階調化
	var id1 = charIDToTypeID( "Thrs" );
	var desc = new ActionDescriptor();
	desc.putInteger( charIDToTypeID( "Lvl " ), val );
	executeAction( id1, desc, DialogModes.NO );
	}

function lvlsFunc(){ //レベル補正_ダイアログ開く
	var lvls = charIDToTypeID( "Lvls" );
	var desc1 = new ActionDescriptor();
	var adjs = charIDToTypeID( "Adjs" );
	var list1 = new ActionList();
	var desc2 = new ActionDescriptor();
	var chnl = charIDToTypeID( "Chnl" );
	var ref1 = new ActionReference();
	var ordn = charIDToTypeID( "Ordn" );
	var trgt = charIDToTypeID( "Trgt" );
	ref1.putEnumerated( chnl, ordn, trgt );
	desc2.putReference( chnl, ref1 );
	var inpt = charIDToTypeID( "Inpt" );
	var list2 = new ActionList();
	list2.putInteger( 0 );
	list2.putInteger( 255 );
	desc2.putList( inpt, list2 );
	var lvla = charIDToTypeID( "LvlA" );
	list1.putObject( lvla, desc2 );
	desc1.putList( adjs, list1 );
	try{
		executeAction( lvls, desc1, DialogModes.ALL );
		}
	catch(e){}
	}

function appiFunc(cMode){ //画像操作_引数にカラーモード、Target Document の 選択アルファチャンネルでマスク
	var appi = charIDToTypeID( "AppI" );
	var desc1 = new ActionDescriptor();
	var with1 = charIDToTypeID( "With" );
	var desc = new ActionDescriptor();
	var ttt = charIDToTypeID( "T   " );
	var ref2 = new ActionReference();
	var chnl = charIDToTypeID( "Chnl" );
	var mode1 = charIDToTypeID( cMode );
	ref2.putEnumerated( chnl, chnl, mode1 );
	var lyr = charIDToTypeID( "Lyr " );
	var bckg = charIDToTypeID( "Bckg" );
	ref2.putProperty( lyr, bckg );
	var dcmn = charIDToTypeID( "Dcmn" );
	ref2.putName( dcmn, "Target Document" );
	desc.putReference( ttt, ref2 );
	var usms = charIDToTypeID( "UsMs" );
	var ref3 = new ActionReference();
	var ordn = charIDToTypeID( "Ordn" );
	var trgt = charIDToTypeID( "Trgt" );
	ref3.putEnumerated( chnl, ordn, trgt );
	ref3.putName( dcmn, "Target Document" );
	desc.putReference( usms, ref3 );
	var clcl = charIDToTypeID( "Clcl" );
	desc1.putObject( with1, clcl, desc );
	executeAction( appi, desc1, DialogModes.NO );
	}

function removeLastHistory(){ //最新のヒストリーを削除
	var id1 = charIDToTypeID( "Dlt " );
	var desc = new ActionDescriptor();
	var id2 = charIDToTypeID( "null" );
	var ref1 = new ActionReference();
	var id3 = charIDToTypeID( "HstS" );
	var id4 = charIDToTypeID( "Ordn" );
	var id5 = charIDToTypeID( "Lst " ); //Last=最終ヒストリ
	ref1.putEnumerated( id3, id4, id5 );
	desc.putReference( id2, ref1 );
	executeAction( id1, desc, DialogModes.NO );
	}

function main(){
if(app.version.split(".")[0]-0 < 8){ //7.0はエラーが出たのでさようなら
	alert("対応バージョンはAdobe PhotoshopⓇCS 以降となります");
	return;
	}
var myDoc=activeDocument;
if(myDoc.mode.toString().match(/BITMAP|INDEXEDCOLOR|MULTICHANNEL/) || myDoc.bitsPerChannel.toString()=="BitsPerChannelType.THIRTYTWO"){
	alert("レイヤー機能非対応のカラーモードでは使用できません");
	return;
	}
var myLay=myDoc.activeLayer; //アクティブレイヤーがない場合はエラー

if(myLay.isBackgroundLayer){
	alert("背景レイヤーには透明ピクセルがないため効果がありません");
	return;
	}
if(myDoc.quickMaskMode==true){
	alert("クイックマスクモードでは使用できません");
	return;
	}
for(var i=0; i<documents.length; i++){
	if(documents[i].name=="Target Document"){
		alert("開かれているドキュメント「Target Document」\nを閉じてから実行してください");
		return;
		}
	}
var defLockStates=null;
if(myLay.allLocked || myLay.pixelsLocked || myLay.transparentPixelsLocked){
	var conf1=confirm("処理対象レイヤー「"+myLay.name+"」のロックを一時的に解除します");
	if(! conf1) return;
	defLockStates=[myLay.allLocked, myLay.pixelsLocked, myLay.transparentPixelsLocked];
	myLay.allLocked=false;
	myLay.pixelsLocked=false;
	myLay.transparentPixelsLocked=false;
	}
var componentLength=myDoc.componentChannels.length; //最前面にある時じゃないと正確に拾えないみたい
dupLay(); //レイヤーを新規ドキュメントに複製
var tarDoc=activeDocument;
tarDoc.layers[0].name="Target Layer";
var chnlNmbr=tarDoc.channels.length;
for(var i=0; i<chnlNmbr; i++){
	tarDoc.activeChannels=[tarDoc.channels[i]];
	dupChnl("Trgt"); //選択チャンネルを演算から新規チャンネル
	}
dupChnl("Trsp");//透明部分を演算から新規チャンネル
for(var i=0; i<chnlNmbr; i++){ //オリジナルチャンネルを削除
	tarDoc.channels[0].remove();
	}
var maskCh=tarDoc.channels[chnlNmbr];
if(componentLength==1){
	tarDoc.activeChannels=[tarDoc.channels[0]];
	maskCh.visible=true;
	}
if(myDoc.mode !=DocumentMode.DUOTONE){ //ダブルトーンだけはグレースケールで、他は元と同じカラーモードに
	tarDoc.changeMode(eval("ChangeMode"+myDoc.mode.toString().match(/\..+/)));
	}
else{
	tarDoc.changeMode(ChangeMode.GRAYSCALE);
	}
tarDoc.activeChannels=[tarDoc.channels[chnlNmbr]];
var conf2=confirm("不透明部分をすべて100%にしますか？\n「いいえ」で「レベル補正」が開きます");
if(conf2){
	thrsFunc(1);
	}
else{
	lvlsFunc();
	}
activeDocument=myDoc;
switch(myDoc.mode.toString().split(".")[1]){
	case "CMYK" : appiFunc("CMYK"); break;//画像操作
	case "DUOTONE" : 
	case "GRAYSCALE" : appiFunc("Blck"); break;
	case "RGB" : appiFunc("RGB "); break;
	case "LAB" : appiFunc("Lab "); 
	}
tarDoc.close(SaveOptions.DONOTSAVECHANGES);
if(defLockStates != null){ //ロック状態の復元
	myLay.allLocked=defLockStates[0];
	myLay.pixelsLocked=defLockStates[1];
	myLay.transparentPixelsLocked=defLockStates[2];
	}
if(app.version.split(".")[0]-0 > 11){ //CS5以降の一発undo対策
	myLay.opacity=(myLay.opacity==100)? 99 : 100; //ダミーヒストリー作成
	myDoc.activeHistoryState=myDoc.historyStates[myDoc.historyStates.length-3];
	removeLastHistory(); //最新のヒストリーを削除
	myDoc.activeHistoryState=myDoc.historyStates[myDoc.historyStates.length-1];
	}
}

main();
