package jp.hasc.hasctool.core.runtime.filter;

import java.util.ArrayList;

import jp.hasc.hasctool.core.data.SignalMessage;
import jp.hasc.hasctool.core.messaging.MessageProcessor;
import jp.hasc.hasctool.core.messaging.MessageQueue;
import jp.hasc.hasctool.core.runtime.RuntimeContext;
import jp.hasc.hasctool.core.runtime.source.AbstractSource;

/**
 * 複数のメッセージ系列（文字列系列など）を、ポート番号順に連結して出力します。
 * SignalMessageを入力するのは不適切です（出力するメッセージが時刻順に並ばないため）。
 * @author iwasaki
 */
public class SimpleMultipleInputMerger extends AbstractSource {
	
	// それぞれの入力はキューに積まれ、それを別スレッドから取り出して処理される
	protected ArrayList<MessageQueue> inputPorts_=new ArrayList<MessageQueue>();
	
	protected int inputPortCount_=0;
	
	public int getInputPortCount() {
		return inputPortCount_;
	}
	
	/**
	 * 入力ポートの数を指定します。
	 */
	public void setInputPortCount(int size) {
		inputPortCount_=size;
	}
	
	/**
	 * 指定したインデックスの入力ポートを返します。
	 */
	public MessageProcessor getInputPort(int index) {
		return inputPorts_.get(index);
	}
	
	public int getInputPortIndex(MessageProcessor idx) {
		return inputPorts_.indexOf(idx);
	}
	
	@Override
	public void setup(RuntimeContext context) {
		super.setup(context);
		
		// create input ports
		inputPorts_.clear();
		for(int i=0;i<inputPortCount_;++i) {
			inputPorts_.add(createMessageQueue(i));
		}
	}
	
	public MessageQueue createMessageQueue(int portIndex) {
		return getRuntimeContext().createDefaultMessageQueue();
	}

	@Override
	protected void run() throws InterruptedException {
		outputMessage(SignalMessage.BEGIN);
		for(MessageQueue q:inputPorts_) {
			while(true){
				Object message=q.readMessage();
				if (message==SignalMessage.BEGIN) continue;
				if (message==SignalMessage.END) break;
				else outputMessage(message);
			}
		}
		outputMessage(SignalMessage.END);
	}
}
