/
codebase/
codebase/area/
codebase/doc/
codebase/etc/
codebase/src/net/sourceforge/pain/data/trigger/
codebase/src/net/sourceforge/pain/logic/
codebase/src/net/sourceforge/pain/logic/affect/
codebase/src/net/sourceforge/pain/logic/event/
codebase/src/net/sourceforge/pain/logic/event/deploy/
codebase/src/net/sourceforge/pain/logic/event/guitool/
codebase/src/net/sourceforge/pain/logic/event/guitool/event/
codebase/src/net/sourceforge/pain/logic/fn/util/
codebase/src/net/sourceforge/pain/logic/trigger/
codebase/src/net/sourceforge/pain/logic/trigger/impl/
codebase/src/net/sourceforge/pain/network/console/
codebase/src/net/sourceforge/pain/network/console/telnet/
codebase/src/net/sourceforge/pain/network/guitool/
codebase/src/net/sourceforge/pain/plugin/
codebase/src/net/sourceforge/pain/plugin/command/
codebase/src/net/sourceforge/pain/plugin/reset/
codebase/src/net/sourceforge/pain/plugin/shutdown/
codebase/src/net/sourceforge/pain/plugin/social/
codebase/src/net/sourceforge/pain/util/
db/doc/javadoc/resources/
db/src/net/sourceforge/pain/util/
gui/
gui/lib/
gui/src/net/sourceforge/pain/tools/guitool/dbbrowse/
gui/src/net/sourceforge/pain/tools/guitool/dialog/
gui/src/net/sourceforge/pain/tools/guitool/menu/
gui/src/net/sourceforge/pain/tools/guitool/resources/
gui/src/net/sourceforge/pain/tools/guitool/resources/images/
gui/src/net/sourceforge/pain/tools/guitool/resources/images/explorer/
tests/
tests/src/
tests/src/net/sourceforge/pain/db/data/
package net.sourceforge.pain.logic.event.console.command.builder;

import net.sourceforge.pain.*;
import net.sourceforge.pain.data.*;
import net.sourceforge.pain.data.type.*;
import net.sourceforge.pain.logic.fn.*;
import net.sourceforge.pain.logic.fn.util.*;
import net.sourceforge.pain.network.console.*;

import java.util.*;

/**
 * PAiN  Date: 05.06.2003  Time: 1:40:02
 */
public final class BC_Link extends BuilderCommand {

	public void processBuilderCommand(BuilderShell p, String args) throws Exception {
		boolean failed = true;
		final Space space = p.player.asLocated().getLocation();
		Room fromRoomRole = (Room) space.getRole(Room.class);
		if (args != null) {
			StringTokenizer st = new StringTokenizer(args, " ");
			final String directionStr = st.nextToken();
			if (directionStr.length() != 1) {
				MessageOutFn.outln(p.console, "ERROR:Illegal direction:" + directionStr);
				return;
			}
			final int dir;
			try {
				dir = Utils.exitCharToDir(directionStr.charAt(0));
			} catch (Exception e) {
				MessageOutFn.outln(p.console, "ERROR:Illegal direction:" + directionStr);
				return;
			}
			Exit e = fromRoomRole == null ? null : fromRoomRole.getExit(dir);
			if (e != null) {
				MessageOutFn.outln(p.console, "ERROR:Direction is busy:" + e.getTargetRoom().asSpace().getName());
				return;
			}
			boolean single = false;
			if (st.hasMoreTokens()) {
				String uniqueName = null;
				String token = st.nextToken();
				if ("SINGLE".equalsIgnoreCase(token)) {
					single = true;
					if (st.hasMoreTokens()) {
						uniqueName = st.nextToken("\n").trim();
					}
				} else {
					uniqueName = token;
				}
				if (uniqueName != null) {
					IndexedSpace targetIndexedSpace = Core.getWorld().getIndexedSpacesRegistry().getSpace(uniqueName);
					if (targetIndexedSpace == null) {
						MessageOutFn.outln(p.console, "ERROR: no named space found with name:" + uniqueName);
						return;
					}

                    Room targetRoomRole = (Room) targetIndexedSpace.getRole(Room.class);
                    // here we should ensure that we deal with Rooms but not with simple Spaces
                    // we should add Room role to src and dst Spaces if they are not Rooms
                    if (fromRoomRole == null) {
                        fromRoomRole = (Room) space.addRole(Room.class);
                    }
                    if (targetRoomRole == null) {
                        targetRoomRole = (Room) targetIndexedSpace.addRole(Room.class);
                    }
					int reverseDir = Room.reverseDir[dir];
					if (!single && targetRoomRole.getExit(reverseDir) != null) {
						MessageOutFn.outln(p.console, "ERROR: reverse dir is used, use SINGLE option to create single way link");
						return;
					}
					// ok, creating!
					failed = false;
					link(p.console, fromRoomRole, dir, targetRoomRole);
					if (!single) { //backward link
						link(p.console, targetRoomRole, reverseDir, fromRoomRole);
					}


				}
			}

		}
		if (failed) {
			showUsage(p.console);
		}
	}

	private static void link(Console console, Room fromRoom, int dir, Room targetRoom) throws Exception {
		MessageOutFn.outln(console, "Creating link from {Y" + fromRoom.asSpace().getName() + "{x direction:{C" + LangUtil.exitName[dir] + "{x target space:{Y" + targetRoom.asSpace().getName() + "{x");
		Room link = (Room) fromRoom.getRole(Room.class);
		if (link == null) {
			link = (Room) fromRoom.addRole(Room.class);
		}
		Exit e = (Exit) ObjectFactory.create(Exit.class);
		e.setTargetRoom(targetRoom);
		link.setExit(dir, e);
	}


	public void showUsage(Console console) {
		MessageOutFn.outln(console, "LINK:Command syntax <DIRECTION> [SINGLE] <UNIQUE_ROOM_ID>\n");
	}

	public void showHelp(Console console) {
		MessageOutFn.outln(console, "Builder command LINK creates exit from current room to other.");
		MessageOutFn.outln(console, "Usage: link <DIRECTION> [SINGLE] <UNIQUE_ROOM_ID>");
		MessageOutFn.outln(console, "{wDIRECTION{x is a letter from (N,E,S,W,U,D)");
		MessageOutFn.outln(console, "{wSINGLE{x is optional param. Used when single way link should be created");
		MessageOutFn.outln(console, "{wUNIQUE_ROOM_ID{x is unique name of the target space");
		MessageOutFn.outln(console, "NOTE: 'Room' role will be added to current or target space if needed");
	}

}