Implementasi Metode Generate and Test Dalam Penyelesaian Puzzle 2048 Berbasis Mobile
LAMPIRAN A
A- 1 -
using UnityEngine;
using System.Collections;
public class AI : MonoBehaviour {
#region var
private string[] strRandSpawn5 = new string[5]; private int intCurSpawn5 = 0;
public struct Node {
public string strNodeId;
public string strNodeIdParent; public string strNodeIdChild; public int intHighNum;
public int intSpaceLeft; public int intSpawnPos; public string OwnBoard; public string strDirection; public bool isIdle;
}
public Node[] myNode = new Node[1364]; public string strSaveDataAIArah = ""; public string strSaveDataAISpawn = "";
public controller_Gameplay myController_Gameplay; public Module myModule;
#endregion
public void setNodeID() {
int intCurArah = 1; int intIdxParent = -1;
for (int i = 0; i < myNode.Length; i++) {
if (i < 4) {
myNode[i].strNodeIdParent = "";
myNode[i].strNodeId = intCurArah.ToString() + "0000"; } else { myNode[i].strNodeIdParent = myNode[intIdxParent].strNodeId;
if (i < 20) myNode[i].strNodeId =
myNode[i].strNodeIdParent.Substring(0, 1) + intCurArah.ToString() + "000"; // 16 + 4
else if (i < 84) myNode[i].strNodeId =
myNode[i].strNodeIdParent.Substring(0, 2) + intCurArah.ToString() + "00"; // 64 + 16 + 4
(2)
LAMPIRAN A
A- 2 -
else if (i < 340) myNode[i].strNodeId =
myNode[i].strNodeIdParent.Substring(0, 3) + intCurArah.ToString() + "0"; // 256 + 64 + 16 + 4
else if (i < 1364) myNode[i].strNodeId =
myNode[i].strNodeIdParent.Substring(0, 4) + intCurArah.ToString(); // 1024 + 256 + 64 + 16 + 4
}
setNodeStrDirection(i, intCurArah); intCurArah++;
if (intCurArah > 4) {
intCurArah = 1; intIdxParent++; }
} }
void setNodeStrDirection(int idx, int dir) {
switch (dir) {
case 1: myNode[idx].strDirection = "Up"; break;
case 2: myNode[idx].strDirection = "Down"; break;
case 3: myNode[idx].strDirection = "Left"; break;
case 4: myNode[idx].strDirection = "Right"; break;
} }
public void resetNode() {
for (int i = 0; i < myNode.Length; i++) {
myNode[i].intHighNum = 0; myNode[i].intSpaceLeft = 0; myNode[i].intSpawnPos = -1; myNode[i].OwnBoard = ""; myNode[i].isIdle = false; }
strSaveDataAIArah = ""; strSaveDataAISpawn = "";
for (int j = 0; j < strRandSpawn5.Length; j++) strRandSpawn5[j] =
myModule.RandomItemInString("0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15"); ContinueAI();
}
void simulator4(int idxMyNode) {
bool bAdd = false;
//declare the iBoard as template for move test int[][] iBoard;
(3)
LAMPIRAN A
A- 3 -
for (int i = 0; i < 4; i++) {
iBoard[i] = new int[4]; }
int idxString = 1; if (idxMyNode < 4) {
idxString = 1;
for (int d = 0; d < 4; d++) {
for (int e = 0; e < 4; e++) {
int.TryParse(myModule.GetItemPos(myController_Gameplay.strMasterBoa rd, idxString), out iBoard[e][d]);
idxString++; }
} }
else if (idxMyNode >= 4) {
idxString = 1;
//find the parent Node
int idxParentGet = findIdxParent(idxMyNode); for (int a = 0; a < myNode.Length; a++)
{
if (myNode[a].strNodeId == myNode[idxMyNode].strNodeIdParent)
{
idxParentGet = a; break;
} }
//pass the parent's OwnBoard to iBoard for (int b = 0; b < 4; b++)
{
for (int c = 0; c < 4; c++) {
int.TryParse(myModule.GetItemPos(myNode[idxParentGet].OwnBoard, idxString), out iBoard[c][b]);
idxString++; }
} }
int idxPick = 1;
int intNextSpawn = -1; bool bolSpawn = false;
//find appropriate spot to spawn next Number from strRandSpawn5
while (!bolSpawn && idxPick <=
myModule.GetItemCount(strRandSpawn5[intCurSpawn5])) {
(4)
LAMPIRAN A
A- 4 -
int.TryParse(myModule.GetItemPos(strRandSpawn5[intCurSpawn5], idxPick), out intNextSpawn);
////print("callout : " + intNextSpawn.ToString()); int kolSpawn = intNextSpawn % 4;
int brsSpawn = intNextSpawn / 4; if (iBoard[kolSpawn][brsSpawn] == 0) {
iBoard[kolSpawn][brsSpawn] = 2; bolSpawn = true;
} else idxPick++; } if (bolSpawn) {
// cek direction & calculate //bool bAdd = false;
switch (myNode[idxMyNode].strDirection) {
case "Up":
for (int i = 0; i < 4; i++) {
for (int j = 0; j < 4; j++) {
for (int k = j + 1; k < 4; k++) {
if (iBoard[i][k] == 0) {
continue; }
else if (iBoard[i][k] == iBoard[i][j])
{
iBoard[i][j] *= 2; iBoard[i][k] = 0; bAdd = true; break;
} else {
if (iBoard[i][j] == 0 && iBoard[i][k] != 0)
{
iBoard[i][j] = iBoard[i][k];
iBoard[i][k] = 0; j--;
bAdd = true; break;
}
else if (iBoard[i][j] != 0) {
break; }
} }
(5)
LAMPIRAN A
A- 5 -
} }
break; case "Right":
for (int j = 0; j < 4; j++) {
for (int i = 3; i >= 0; i--) {
for (int k = i - 1; k >= 0; k--) {
if (iBoard[k][j] == 0) {
continue; }
else if (iBoard[k][j] == iBoard[i][j])
{
iBoard[i][j] *= 2; iBoard[k][j] = 0; bAdd = true; break;
} else {
if (iBoard[i][j] == 0 && iBoard[k][j] != 0)
{
iBoard[i][j] = iBoard[k][j];
iBoard[k][j] = 0; i++;
bAdd = true; break;
}
else if (iBoard[i][j] != 0) { break; } } } } } break; case "Down":
for (int i = 0; i < 4; i++) {
for (int j = 3; j >= 0; j--) {
for (int k = j - 1; k >= 0; k--) {
if (iBoard[i][k] == 0) {
continue; }
else if (iBoard[i][k] == iBoard[i][j])
(6)
LAMPIRAN A
A- 6 -
iBoard[i][j] *= 2; iBoard[i][k] = 0; bAdd = true; break;
} else {
if (iBoard[i][j] == 0 && iBoard[i][k] != 0)
{
iBoard[i][j] = iBoard[i][k];
iBoard[i][k] = 0; j++;
bAdd = true; break;
}
else if (iBoard[i][j] != 0) { break; } } } } } break; case "Left":
for (int j = 0; j < 4; j++) {
for (int i = 0; i < 4; i++) {
for (int k = i + 1; k < 4; k++) {
if (iBoard[k][j] == 0) {
continue; }
else if (iBoard[k][j] == iBoard[i][j])
{
iBoard[i][j] *= 2; iBoard[k][j] = 0; bAdd = true; break;
} else {
if (iBoard[i][j] == 0 && iBoard[k][j] != 0)
{
iBoard[i][j] = iBoard[k][j];
iBoard[k][j] = 0; i--;
bAdd = true; break;
(7)
LAMPIRAN A
A- 7 -
else if (iBoard[i][j] != 0) { break; } } } } } break; }
// save spawnPos....ownBoard...highestPoint.... spaceLeft...
// convert back to string string strBoardResult = ""; int inthighNum = 0;
int intFreeSpots = 0;
for (int m = 0; m < 4; m++) {
for (int n = 0; n < 4; n++) {
strBoardResult =
myModule.AddItem(strBoardResult, iBoard[n][m].ToString());
if (iBoard[n][m] > inthighNum) inthighNum = iBoard[n][m];
if (iBoard[n][m] == 0) intFreeSpots += 1; }
}
myNode[idxMyNode].intSpawnPos = intNextSpawn; myNode[idxMyNode].OwnBoard = strBoardResult; myNode[idxMyNode].intHighNum = inthighNum; myNode[idxMyNode].intSpaceLeft = intFreeSpots; if (!bAdd) myNode[idxMyNode].isIdle = true; else
{
if (idxMyNode < 4) myNode[idxMyNode].isIdle = false;
else //follow the parent's idle stat { myNode[idxMyNode].isIdle = myNode[findIdxParent(idxMyNode)].isIdle; } } } else print("GAMEOVER"); } void ContinueAI() { //simulate result
for (int k = 0; k < myNode.Length; k++) {
if (k == 0) intCurSpawn5 = 0; else if (k == 4) intCurSpawn5 = 1; else if (k == 20) intCurSpawn5 = 2;
(8)
LAMPIRAN A
A- 8 -
else if (k == 84) intCurSpawn5 = 3; else if (k == 340) intCurSpawn5 = 4; simulator4(k);
}
//get bottom best value int getTmpIdx = 340; int intHighNum = 0; int intSpaceLeft = 0;
for (int v = 340; v < myNode.Length; v++) {
if (!myNode[v].isIdle && ((intHighNum <
myNode[v].intHighNum) || (intHighNum == myNode[v].intHighNum && intSpaceLeft < myNode[v].intSpaceLeft)))
{
getTmpIdx = v;
intHighNum = myNode[v].intHighNum; intSpaceLeft = myNode[v].intSpaceLeft; }
}
//trace up
for (int w = 5; w > 0; w--) { strSaveDataAIArah = myModule.AddItemReversed(strSaveDataAIArah, myNode[getTmpIdx].strDirection); strSaveDataAISpawn = myModule.AddItemReversed(strSaveDataAISpawn, myNode[getTmpIdx].intSpawnPos.ToString());
for (int x = 0; x < myNode.Length; x++) {
if (myNode[x].strNodeId == myNode[getTmpIdx].strNodeIdParent)
{
getTmpIdx = x; }
} }
myController_Gameplay.intUpdate = 10; }
int findIdxParent(int idxChild) {
int idxParentGet = -1;
for (int a = 0; a < myNode.Length; a++) {
if (myNode[a].strNodeId == myNode[idxChild].strNodeIdParent)
{
idxParentGet = a; break;
} }
return idxParentGet; }
(9)
LAMPIRAN A
A- 9 -
(10)
LAMPIRAN B
B- 1 -
using UnityEngine;
using System.Collections; [System.Serializable] public class Box2048 {
public int intIdx; public int intKol; public int intBrs; public float posX; public float posY; public int FillNum; }
[System.Serializable] public class Number2048 {
public int intIdx; public int intKol; public int intBrs; public float posX; public float posY; public int Number; public GameObject GO; }
public class controller_Gameplay : MonoBehaviour {
#region var
public int intUpdate = -1; public bool isInput = false; public int intWaitMove;
public bool bolAllMove = false;
public Box2048[] myBox = new Box2048[16];
public Number2048[] myNumber = new Number2048[16]; public bool[] isNumberMove = new bool[16];
private int intCountMove = -1; private int intCurSpawn = -1; private string strCurMove = ""; public AI myAI;
public string strMasterBoard = ""; public Module myModule;
#endregion
// Use this for initialization void Start () {
//print("void start");
for (int i = 0; i < myBox.Length; i++) {
myBox[i].intIdx = i;
myBox[i].intKol = (i % 4); myBox[i].intBrs = (i / 4);
myBox[i].posX = -4.0f + (2.0f * (i % 4)); myBox[i].posY = 3.0f - (2.0f * (i / 4));
(11)
LAMPIRAN B
B- 2 -
myBox[i].FillNum = 0; myNumber[i].intIdx = i;
myNumber[i].intKol = (i % 4); myNumber[i].intBrs = (i / 4);
myNumber[i].posX = -4.0f + (2.0f * (i % 4)); myNumber[i].posY = 3.0f - (2.0f * (i / 4)); myNumber[i].Number = 0;
}
myAI.setNodeID(); intUpdate = 5; }
// Update is called once per frame void Update()
{
switch (intUpdate) {
case 0: break;
case 5: intUpdate = 0; callAI();
break;
case 10: intUpdate = 0; intCountMove = 0; intUpdate = 15; break;
case 15: intUpdate = 0; intCountMove++;
if (intCountMove > 5) intUpdate = 5; else { int.TryParse(myModule.GetItemPos(myAI.strSaveDataAISpawn,intCountMo ve),out intCurSpawn); strCurMove = myModule.GetItemPos(myAI.strSaveDataAIArah, intCountMove); intUpdate = 20;
} break;
case 20: intUpdate = 0;
spawnNumber(intCurSpawn); break;
case 25: intUpdate = 0;
moveNumber(strCurMove); break;
case 30: intUpdate = 0; checkGameOver(); break;
case 40: intUpdate = 0;
GameObject.Find("EventSystem").SendMessage("Finish"); GUI.Box(new Rect(0, 0, Screen.width, Screen.height), "The game ends /n the time is "+ Time.time);
break;
case 500 : if (Input.GetKeyDown(KeyCode.Space)) {
(12)
LAMPIRAN B
B- 3 -
afterMove(); } break; } } void callAI() { //print("void callAI");
//convert currentBoard to string strMasterBoard = "";
for (int i = 0; i < myNumber.Length; i++) strMasterBoard = myModule.AddItem(strMasterBoard, myNumber[i].Number.ToString());
//call AI to start myAI.resetNode(); }
void spawnNumber(int intPosSpawn) {
//print("void spawnNumber"); myBox[intPosSpawn].FillNum = 2; myNumber[intPosSpawn].Number = 2; myNumber[intPosSpawn].GO =
Instantiate(Resources.Load("Numbers/GO_2")) as GameObject; myNumber[intPosSpawn].GO.transform.position = new
Vector3(myNumber[intPosSpawn].posX, myNumber[intPosSpawn].posY, 0.0f); intUpdate = 25;
}
public void moveNumber(string direction) {
//print("void moveNumber");
//set EndPos (order based on direction) //#######################################// #region RIGHT
if (direction == "Right") {
for (int j = 0; j < 4; j++) {
for (int i = 3; i >= 0; i--) {
for (int k = i - 1; k >= 0; k--) {
if (myBox[(4 * j) + k].FillNum == 0) {
continue; }
else if (myBox[(4 * j) + k].FillNum == myBox[(4 * j) + i].FillNum)
{
myNumber[(4 * j) + k].GO.GetComponent<controller_moveAnimTes>().endPos = new
Vector3(myNumber[(4 * j) + i].posX, myNumber[(4 * j) + k].posY, 0.0f); myNumber[(4 * j) +
k].GO.GetComponent<controller_moveAnimTes>().interval =
(13)
LAMPIRAN B
B- 4 -
isNumberMove[(4 * j) + k] = true; myBox[(4 * j) + i].FillNum *= 2; myBox[(4 * j) + k].FillNum = 0; break;
} else {
if (myBox[(4 * j) + i].FillNum == 0 && myBox[(4 * j) + k].FillNum != 0)
{
myNumber[(4 * j) + k].GO.GetComponent<controller_moveAnimTes>().endPos = new
Vector3(myNumber[(4 * j) + i].posX, myNumber[(4 * j) + k].posY, 0.0f); myNumber[(4 * j) +
k].GO.GetComponent<controller_moveAnimTes>().interval =
Mathf.Abs(myBox[(4 * j) + k].intKol - myBox[(4 * j) + i].intKol);
isNumberMove[(4 * j) + k] = true;
myBox[(4 * j) + i].FillNum = myBox[(4 * j) + k].FillNum;
myBox[(4 * j) + k].FillNum = 0;
i++; break; }
else if (myBox[(4 * j) + i].FillNum != 0)
{ break; } } } } } } #endregion //#######################################// #region LEFT
if (direction == "Left") {
for (int j = 0; j < 4; j++) {
for (int i = 0; i < 4; i++) {
for (int k = i + 1; k < 4; k++) {
if (myBox[(4*j)+k].FillNum == 0) {
continue; }
else if (myBox[(4 * j) + k].FillNum == myBox[(4 * j) + i].FillNum)
{
myNumber[(4 * j) + k].GO.GetComponent<controller_moveAnimTes>().endPos = new
(14)
LAMPIRAN B
B- 5 -
myNumber[(4 * j) + k].GO.GetComponent<controller_moveAnimTes>().interval =
Mathf.Abs(myBox[(4 * j) + k].intKol - myBox[(4 * j) + i].intKol);
isNumberMove[(4 * j) + k] = true; myBox[(4 * j) + i].FillNum *= 2; myBox[(4*j)+k].FillNum = 0; break;
} else {
if (myBox[(4 * j) + i].FillNum == 0 && myBox[(4 * j) + k].FillNum != 0)
{
myNumber[(4 * j) + k].GO.GetComponent<controller_moveAnimTes>().endPos = new
Vector3(myNumber[(4 * j) + i].posX, myNumber[(4 * j) + k].posY, 0.0f); myNumber[(4 * j) +
k].GO.GetComponent<controller_moveAnimTes>().interval =
Mathf.Abs(myBox[(4 * j) + k].intKol - myBox[(4 * j) + i].intKol);
isNumberMove[(4 * j) + k] = true;
myBox[(4 * j) + i].FillNum = myBox[(4 * j) + k].FillNum;
myBox[(4 * j) + k].FillNum = 0;
i--; break; }
else if (myBox[(4 * j) + i].FillNum != 0)
{ break; } } } } } } #endregion //#######################################// #region DOWN
if (direction == "Down") {
for (int i = 0; i < 4; i++) {
for (int j = 3; j >= 0; j--) {
for (int k = j - 1; k >= 0; k--) {
if (myBox[(4 * k) + i].FillNum == 0) //kosong jd tidak ad yg perlu digeser
{
continue; }
else if (myBox[(4 * k) + i].FillNum == myBox[(4 * j) + i].FillNum) //timpa... nilai sama.... jd tujuan x2... asal jd nol krn digeser
(15)
LAMPIRAN B
B- 6 -
{
myNumber[(4 * k) + i].GO.GetComponent<controller_moveAnimTes>().endPos = new
Vector3(myNumber[(4 * k) + i].posX, myNumber[(4 * j) + i].posY, 0.0f); myNumber[(4 * k) +
i].GO.GetComponent<controller_moveAnimTes>().interval =
Mathf.Abs(myBox[(4 * k) + i].intBrs - myBox[(4 * j) + i].intBrs);
isNumberMove[(4 * k) + i] = true; myBox[(4 * j) + i].FillNum *= 2; myBox[(4 * k) + i].FillNum = 0; break;
} else {
if (myBox[(4 * j) + i].FillNum == 0 && myBox[(4 * k) + i].FillNum != 0) //geser masuk.... tujuan jd ad nilai.... asal jd nol krn digeser
{
myNumber[(4 * k) + i].GO.GetComponent<controller_moveAnimTes>().endPos = new
Vector3(myNumber[(4 * k) + i].posX, myNumber[(4 * j) + i].posY, 0.0f); myNumber[(4 * k) +
i].GO.GetComponent<controller_moveAnimTes>().interval =
Mathf.Abs(myBox[(4 * k) + i].intBrs - myBox[(4 * j) + i].intBrs);
isNumberMove[(4 * k) + i] = true;
myBox[(4 * j) + i].FillNum = myBox[(4 * k) + i].FillNum;
myBox[(4 * k) + i].FillNum = 0;
j++; break; }
else if (myBox[(4 * j) + i].FillNum != 0)//tdk bisa geser krn nilai beda
{ break; } } } } } } #endregion //#######################################// #region UP
if (direction == "Up") {
for (int i = 0; i < 4; i++) {
for (int j = 0; j < 4; j++) {
for (int k = j + 1; k < 4; k++) {
if (myBox[(4 * k) + i].FillNum == 0) //kosong jd tidak ad yg perlu digeser
(16)
LAMPIRAN B
B- 7 -
continue; }
else if (myBox[(4 * k) + i].FillNum == myBox[(4 * j) + i].FillNum) //timpa... nilai sama.... jd tujuan x2... asal jd nol krn digeser
{
myNumber[(4 * k) + i].GO.GetComponent<controller_moveAnimTes>().endPos = new
Vector3(myNumber[(4 * k) + i].posX, myNumber[(4 * j) + i].posY, 0.0f); myNumber[(4 * k) +
i].GO.GetComponent<controller_moveAnimTes>().interval =
Mathf.Abs(myBox[(4 * k) + i].intBrs - myBox[(4 * j) + i].intBrs);
isNumberMove[(4 * k) + i] = true; myBox[(4 * j) + i].FillNum *= 2; myBox[(4 * k) + i].FillNum = 0; break;
} else {
if (myBox[(4 * j) + i].FillNum == 0 && myBox[(4 * k) + i].FillNum != 0) //geser masuk.... tujuan jd ad nilai.... asal jd nol krn digeser
{
myNumber[(4 * k) + i].GO.GetComponent<controller_moveAnimTes>().endPos = new
Vector3(myNumber[(4 * k) + i].posX, myNumber[(4 * j) + i].posY, 0.0f); myNumber[(4 * k) +
i].GO.GetComponent<controller_moveAnimTes>().interval =
Mathf.Abs(myBox[(4 * k) + i].intBrs - myBox[(4 * j) + i].intBrs);
isNumberMove[(4 * k) + i] = true;
myBox[(4 * j) + i].FillNum = myBox[(4 * k) + i].FillNum;
myBox[(4 * k) + i].FillNum = 0;
j--; break; }
else if (myBox[(4 * j) + i].FillNum != 0)//tdk bisa geser krn nilai beda
{ break; } } } } } } #endregion
intWaitMove = 0;
bool isSthMove = false;
for (int k = 0; k < myNumber.Length; k++) {
if (isNumberMove[k]) {
(17)
LAMPIRAN B
B- 8 -
myNumber[k].GO.GetComponent<controller_moveAnimTes>().startPos = new Vector3(myNumber[k].posX, myNumber[k].posY, 0.0f);
myNumber[k].GO.GetComponent<controller_moveAnimTes>().startTime = Time.time; myNumber[k].GO.GetComponent<controller_moveAnimTes>().journeyLength = Vector3.Distance(myNumber[k].GO.GetComponent<controller_moveAnimTes>().st artPos, myNumber[k].GO.GetComponent<controller_moveAnimTes>().endPos); myNumber[k].GO.GetComponent<controller_moveAnimTes>().isMoveable = true;
isSthMove = true; }
}
if (isSthMove) bolAllMove = true; else decreaseIntWaitMove();
}
public void decreaseIntWaitMove() {
//print("void decreaseIntWaitMove..."); intWaitMove--;
//print("hasil pengurangan..." + intWaitMove.ToString()); if (intWaitMove <= 0)
{
bolAllMove = false; afterMove();
} }
void afterMove() {
for (int i = 0; i < myNumber.Length; i++) {
if (myNumber[i].Number > 0) {
myNumber[i].GO.transform.position = new Vector3(myNumber[i].posX, myNumber[i].posY, 0.0f);
GameObject.Destroy(myNumber[i].GO.gameObject); }
myNumber[i].Number = myBox[i].FillNum; if (myNumber[i].Number > 0)
{
myNumber[i].GO = Instantiate(Resources.Load("Numbers/GO_" + myNumber[i].Number.ToString())) as GameObject;
myNumber[i].GO.transform.position = new Vector3(myNumber[i].posX, myNumber[i].posY, 0.0f);
(18)
LAMPIRAN B
B- 9 -
if (myNumber[i].Number == 2048) {
GameObject.Find("EventSystem").SendMessage("Finish"); }
if (myNumber[i].Number == 1024) {
GameObject.Find("EventSystem").SendMessage("Catat"); }
isNumberMove[i] = false; }
//can Spawn ???
bool canSpawn = false;
for (int j = 0; j < myBox.Length; j++) {
if (myBox[j].FillNum == 0) {
canSpawn = true; break;
} }
//print("void afterMove => cek Can Spawn???"); if (canSpawn)
intUpdate = 15; else
intUpdate = 30; }
void checkGameOver() {
//print("void checkGameOver"); bool isPlayable = false;
for (int j = 0; j < myNumber.Length; j++) {
//not mostLeft if (j % 4 != 0) {
if (myNumber[j].Number == myNumber[j - 1].Number) {
isPlayable = true; break;
} }
//NOT mostRight else if (j % 4 != 3) {
if (myNumber[j].Number == myNumber[j + 1].Number) {
isPlayable = true; break;
} }
//not mostTop
(19)
LAMPIRAN B
B- 10 -
{
if (myNumber[j].Number == myNumber[j - 4].Number) {
isPlayable = true; break;
} }
//not mostBottom else if (j / 4 != 3) {
if (myNumber[j].Number == myNumber[j + 4].Number) {
isPlayable = true; break;
} }
}
if (isPlayable) intUpdate = 10; else intUpdate = 40;
} }
(20)
LAMPIRAN C
C-- 1 --
using UnityEngine;
using System.Collections;
public class controller_moveAnimTes : MonoBehaviour { //tes
public GameObject myGO_AnimTes;
public controller_Gameplay myGameplayScript; public Vector3 startPos;
public Vector3 endPos; public Vector4 startColor; public Vector4 endColor; public float speed = 1.0f; public float interval = 1.0f; public float startTime;
public float journeyLength; private float colorLength; public bool isMoveable;
// Use this for initialization void Start () {
//tes
myGameplayScript =
GameObject.Find("Controller_Gameplay").GetComponent<controller_Gameplay>( );
////print("GO found"); speed = 15.0f;
startTime = Time.time;
journeyLength = Vector3.Distance(startPos, endPos); //startColor = new
Vector4(this.gameObject.GetComponent<SpriteRenderer>().color.r, this.gameObject.GetComponent<SpriteRenderer>().color.r,
this.gameObject.GetComponent<SpriteRenderer>().color.r, 1.0f); //endColor = new
Vector4(this.gameObject.GetComponent<SpriteRenderer>().color.r, this.gameObject.GetComponent<SpriteRenderer>().color.r,
this.gameObject.GetComponent<SpriteRenderer>().color.r, 0.0f); //colorLength = Vector4.Distance(startColor, endColor); //---//
}
// Update is called once per frame void Update()
{
if (isMoveable && myGameplayScript.bolAllMove) {
//print("initial calculate ");
float distCovered = (Time.time - startTime) * speed * interval;
float fracJourney = distCovered / journeyLength; //print("about to transform");
myGO_AnimTes.transform.position = Vector3.Lerp(startPos, endPos, fracJourney);
//print("transform is done ");
if (myGO_AnimTes.transform.position == endPos) {
(21)
LAMPIRAN C
C-- 2 --
isMoveable = false;
myGameplayScript.decreaseIntWaitMove(); }
//float fadeCovered = (Time.time - startTime) * speed; //float fracFading = fadeCovered / colorLength;
//myGO_AnimTes.GetComponent<SpriteRenderer>().color = Vector4.Lerp(startColor, endColor, fracFading);
} }
(22)
LAMPIRAN C
C-3-
using UnityEngine;
using System.Collections;
public class Module : MonoBehaviour {
public string AddItem(string sourceString, string addString) {
string temp = sourceString; if (temp == "")
{
temp += addString; }
else {
temp += "," + addString; }
return temp; }
public string AddItemReversed(string sourceString, string addString)
{
string temp = sourceString; if (temp == "")
{
temp += addString; }
else {
temp = addString + "," + temp; }
return temp; }
public string RandomItemInString(string pstr) {
int roundDirection; string temp1 = pstr; string temp2 = "";
int maxItem = GetItemCount(pstr); int maxRound = Random.Range(5, 10); int front = 1;
int last = maxItem;
for (int i = 1; i < maxRound; i++) {
if (temp2 != "") {
temp1 = temp2; temp2 = ""; }
front = 1; last = maxItem;
for (int j = 1; j <= maxItem; j++) {
(23)
LAMPIRAN C
C-4-
if (roundDirection == 1) {
temp2 += GetItemPos(temp1, front); front += 1;
} else {
temp2 += GetItemPos(temp1, last); last -= 1;
}
if (j < maxItem) {
temp2 += ","; }
} }
return temp2; }
public int GetItemCount(string pstr) {
int temp = 1;
if (pstr == "") return temp; int maxChar = pstr.Length;
for (int i = 0; i < maxChar; i++) {
if (pstr.Substring(i, 1) == ",") {
temp += 1; }
}
return temp; }
public string GetItemPos(string pstr, int pos) {
string temp = ""; int count = 1;
int maxChar = pstr.Length;
for (int i = 0; i < maxChar; i++) {
if (pstr.Substring(i, 1) == ",") {
if (count >= pos) {
return temp; }
temp = ""; count += 1; }
else {
(24)
LAMPIRAN C
C-5-
} }
if ((count + 1) < pos) temp = ""; return temp;
} }
(25)
LAMPIRAN D
D-1-
using UnityEngine;
using System.Collections;
public class Module : MonoBehaviour {
public string AddItem(string sourceString, string addString) {
string temp = sourceString; if (temp == "")
{
temp += addString; }
else {
temp += "," + addString; }
return temp; }
public string AddItemReversed(string sourceString, string addString)
{
string temp = sourceString; if (temp == "")
{
temp += addString; }
else {
temp = addString + "," + temp; }
return temp; }
public string RandomItemInString(string pstr) {
int roundDirection; string temp1 = pstr; string temp2 = "";
int maxItem = GetItemCount(pstr); int maxRound = Random.Range(5, 10); int front = 1;
int last = maxItem;
for (int i = 1; i < maxRound; i++) {
if (temp2 != "") {
temp1 = temp2; temp2 = ""; }
front = 1; last = maxItem;
(26)
LAMPIRAN D
D-2-
{
roundDirection = Random.Range(1, 3); if (roundDirection == 1)
{
temp2 += GetItemPos(temp1, front); front += 1;
} else {
temp2 += GetItemPos(temp1, last); last -= 1;
}
if (j < maxItem) {
temp2 += ","; }
} }
return temp2; }
public int GetItemCount(string pstr) {
int temp = 1;
if (pstr == "") return temp; int maxChar = pstr.Length;
for (int i = 0; i < maxChar; i++) {
if (pstr.Substring(i, 1) == ",") {
temp += 1; }
}
return temp; }
public string GetItemPos(string pstr, int pos) {
string temp = ""; int count = 1;
int maxChar = pstr.Length;
for (int i = 0; i < maxChar; i++) {
if (pstr.Substring(i, 1) == ",") {
if (count >= pos) {
return temp; }
temp = ""; count += 1; }
(27)
LAMPIRAN D
D-3-
{
temp += pstr.Substring(i, 1); }
}
if ((count + 1) < pos) temp = ""; return temp;
} }
(28)
LAMPIRAN E
E-1-
using UnityEngine;
using System.Collections;
public class tesKlik5 : MonoBehaviour { // Use this for initialization void Start () {
}
// Update is called once per frame void Update () {
}
public void OnMouseDown1() {
Application.LoadLevel("Gameplay"); }
(29)
LAMPIRAN F
F-1-
using UnityEngine; using UnityEngine.UI; using System.Collections;
public class Timer : MonoBehaviour { // Use this for initialization public Text timerText;
public Text timerText2; private float startTime;
private bool finished = false; private float t1024;
void Start () {
startTime = Time.time; }
// Update is called once per frame void Update () {
if (finished == true)
Time.timeScale=0; else {
float t = Time.time - startTime;
string minutes = ((int)t / 60).ToString ();
string seconds = (t % 60).ToString ("f2");
timerText.text = minutes + ":" + seconds;
} }
public void Finish() {
finished = true;
timerText.color = Color.red; }
public void Catat() {
if (t1024 == 0) {
float t = Time.time - startTime;
string minutes = ((int)t / 60).ToString ();
string seconds = (t % 60).ToString ("f2");
timerText2.text = minutes + ":" + seconds;
t1024++; } }
(30)
Nama : Devina Pratiwi Halim Tempat, tanggal Lahir : Medan, 16 Mei 1992 Jenis Kelamin : Perempuan
Umur : 24 tahun Tinggi, berat badan : 158cm , 55 kg Agama : Buddha
Alamat : Jalan Brig. Jend. Katamso GG. Baru No. 16 Medan Status : Belum Kawin
Telepon : 085767658992
Email : devinapratiwihalim@gmail.com
Formal
1998 – 2004 : Lulusan SD Methodist 2 Medan 2004 – 2007 : Lulusan SMP Methodist 2 Medan 2007 – 2010 : Lulusan SMA Methodist 2 Medan 2012 – 2015 : Bachelor Jurusan Administrasi dan Finansial di Net Academy 2012 – 2016 : S1 Jurusan Akuntansi di Professional Management College
Indonesia
2014 : Associate Chartered Financial Practitioner(AChFP) di Asia Pacific Financial Services Association
2015
Pacific Financial Services Association
Data Pribadi
Latarbelakang Pendidikan :
(31)
Non Formal
2006 – 2007 : Bimbingan bahasa Inggris di The British Institute 2007 – 2008 : Bimbingan Matematika di AXIS
2009 : Bimbingan 1 Tahun Program Komputer di VISITEK
2010 : Workshop Teknik Dasar Fotografi di Ikatan Mahasiswa S1 Ilmu Komputer USU
2010 : Workshop Teknik Hacking di Ikatan Mahasiswa S1 Ilmu Komputer USU
2010 : Workshop Setting Cisco Router di WEBMEDIA Training Center
2011 : Panitia Seminar Teknologi Informasi di Universitas Sumatera Utara
2012 : Peserta Lomba Problem Solving IMILKOM Contest 2012 2013 : Partisipasi dalam Galang Dana Lions Club
2013 : Workshop Mengenal Kopi di Starbucks Medan
2013 : Partisipasi dalam Seminar Orang Yang Kaya Orang Yang Kreatif dari Professional Management College Indonesia
2015 : Liasion Officer (LO) Kegiatan Forum Rektor Indonesia XVII di Universitas Sumatera Utara
2016 : Volunteer dalam partisipasi Education Expo
• 2006 – 2007 : Anggota dari Klub Teater Methodist 2 Medan
• 2010 – 2012 : Anggota dari Keluarga Mahasiswa Buddhis di Universitas Sumatera Utara
• 2013 – 2014 : Anggota dari Singing Club di Professional Management College Indonesia
• 2014 – 2015 : Pengurus Badan Eksekutif Mahasiswa di Professional Management College Indonesia dengan jabatan Hubungan Masyarakat Eksternal
(32)
• 2002 : Penghargaan sebagai Juara X Reading-A di Language School Best
• 2007 : Penghargaan sebagai Peserta dalam mengikuti Pekan Olimpiade Sekolah
• 2008 : Penghargaan sebagai Juara II Kelas XI
• 2008 : Penghargaan sebagai peserta dalam mengikuti Lomba Sains Plus Antar Pelajar SMA Se-Sumut
• 2008 : Penghargaan sebagai Peserta dalam mengikuti Pekan Olimpiade Sekolah
• 2009 : Penghargaan sebagai Peserta dalam Pekan Olimpiade Sekolah
• 2009-2010 : Bekerja di Leny English Private Classes sebagai asisten pengajar bahasa Inggris
• Praktek Kerja Lapangan:
Praktek Kerja Lapangan di di Kantor Pelayanan Perbendaharaan Negara Medan Periode : Agustus 2013 – Oktober 2013
Tujugan : Mata Kuliah Wajib
Posisi : Konsultan IT dan Programmer Rincian Pekerjaan:
• Memasang jaringan pada satu ruangan
• Memasukkan biografi pegawai secara online pada website yang baru
• Mengorganisir data 10 tahun dan lebih dan menyusunnya sehingga dapat di akses seluruh departemen
• Membangun sebuah program dengan menggunakan Microsoft Excel untuk menangani pembayaran gaji pada semua unit di dalam departemen.
• 2014 : Bekerja di Scholars Hub sebagai pengajar sampai sekarang
• 2015 : Bekerja sebagai Agen Asuransi untuk Asuransi Panin Life Dai-ichi sampai sekarang
Penghargaan
(33)
• Kemampuan Komputer
Office
1. Microsoft Word 2. Microsoft Excel 3. Microsoft Power Point 4. Microsoft Access
Design & Video
1. Adobe Photoshop 2. Adobe Dreamweaver
Pemrograman
1. Visual Studio 2. Eclipse 3. Visual Basic 4. Unity 5. MatLab 6. FoxPro
Medan, 2 Nopember 2016 Hormat saya,
Devina Pratiwi Halim
(34)
36
DAFTAR PUSTAKA
Coppin, Ben. 2004. AI Illuminated. United States of America: Penerbit Jones and Bartlett Publishers.
Ekaputra, V., Panggabean, F. & Satria, T. 2014. Analisis dan Perancangan Aplikasi Game Multiplayer Life Simulaton Pet Master menggunakan Game Engine Unity 3D. Skripsi. Jakarta: Binus University.
Hayuningtyas, Nastiti. 2014. Aplikasi Game Edukasi Supermath Berbasis Android. Skripsi. Jakarta: Binus University.
Johannes, Frits. 2014. Aplikasi Game Survival Horror The Sight pada PC menggunakan Unity 3D. Skripsi. Jakarta: Binus University.
Kyaw, A., Peters, C. & Swe, T. 2013. Unity 4.x Game AI Programming. E-Book. Birmingham: Packt Publishing.
Karam, P. 2012. Artificial Intelligence. New York: Penerbit Chelsea House.
Maulina, E. & Satyaputra, A. 2014. Beginning Android Programming with ADT Bundle. Jakarta : PT. Elex Media Komputindo.
Murya, Yosef. 2014. Pemrograman Android BlackBox. Jakarta : Jasakom.
Norvig, P. & Russell, S. 2010. Artificial Intelligence A Modern Approach. Third
Edition. New Jersey: Prentice Hall.
Suyanto. 2007. Artificial Intelligence. Bandung: Informatika Bandung. Unity. Diakses 30 November 2014
Fitur – Fitur Unity. Diakses 30 Novembe 2014 https://unity3d.com/unity/engine-features
(35)
16
BAB 3
ANALISIS DAN RANCANGAN
3.1 Analisis
Pencarian solusi dilakukan dengan menggunakan metode Generate and Test melakukan pencarian solusi dengan cara membuat terlebih dahulu semua kemungkinan langkah kemudian melakukan langkah terbaik. Pada penelitian ini penulis merancang pencarian untuk tujuan mencapai nilai 2048.
3.1.1 Analisis Masalah (Problem Analysis)
Untuk mengidentifikasi masalah digunakan diagram Ishikawa (fishbone
diagram). Diagram Ishikawa adalah sebuah alat grafis yang digunakan untuk
membantu mengidentifikasi, mengeksplorasi dan menggambarkan suatu masalah serta sebab dan akibat dari masalah tersebut. Diagram ini juga sering disebut sebagai diagram sebab-akibat atau diagram tulang ikan. Identifikasi terhadap permasalahan akan membantu analisis persyaratan sistem yang nantinya akan dikembangkan.
Masalah utama yang mendapat perhatian adalah mendapatkan nilai tertinggi untuk blok yang diinginkan. Selanjutnya masalah ini diuraikan ke dalam beberapa kategori seperti pada Gambar 3.1.
l
Gambar 3.1 Diagram Ishikawa untuk Analisis Permasalahan Sistem
Mencapai poin 2048
Machine
Generate and Test 2048
Man
Kemampuan prosesor yang
terbatas Menjalankan program dan
memantau program
Mengenal objek permainan
Tidak kehabisan langkah
Gameplay
Menjalankan langkah terbaik yang telah digenerate
(36)
17
Pada diagram Ishikawa diatas masalah utama ditunjukkan oleh segi empat paling kanan (kepala ikan), sedangkan kategori ditunjukkan oleh segi empat yang dihubungkan oleh sebuah garis ke tulang utama (garis horizontal yang terhubung ke kepala ikan). Selanjutnya sebab akibat yang muncul ditunjukkan oleh tulang-tulang kecil yang diwakili oleh garis panah yang mengarah ke tulang-tulang kategori masalah.
3.1.2 Analisis Persyaratan (Requirement Analysis)
Analisis persyaratan sebuah sistem dikelompokkan ke dalam dua bagian besar yaitu, analisis persyaratan fungsional dan analisis persyaratan non-fungsional.
3.1.2.1 Persyaratan Fungsional
Persyaratan fungsional yang harus dipenuhi oleh sistem adalah segala sesuatu yang harus dimiliki oleh sistem. Sistem harus dapat membangkitkan langkah dan menentukan langkah terbaik kemudian menjalankan langkah tersebut.
3.1.2.2 Analisis Persyaratan Non-Fungsional
Persyaratan non-fungsional adalah persyaratan apa yang harus dilakukan sistem. Seringkali berupa batasan atau sesuatu yang menjadi perhatian stakeholder sebuah sistem. Beberapa persyaratan non-fungsional yang harus dipenuhi oleh sistem yang dirancang adalah sebagai berikut:
1. Performa
Sistem atau perangkat lunak yang akan dibangun harus dapat menampilkan setiap langkah yang diambil dalam waktu yang cepat.
2. Mudah digunakan (User friendly)
Sistem yang akan dibangun harus user friendly, artinya bahwa sistem mudah digunakan oleh user dengan tampilan (interface) yang sederhana dan mudah dimengerti.
3. Hemat Biaya Sistem atau perangkat lunak yang digunakan tidak memerlukan
(37)
18
4. Dokumentasi Sistem yang akan dibangun harus bisa menyimpan total waktu
yang diambil secara akurat.
5. Kontrol Sistem yang akan dibangun harus dapat menampilkan kotak dialog
selesai ketika target telah tercapai dan menampilkan kotak dialog gagal ketika proses gagal.
6. Manajemen Kualitas Sistem atau perangkat lunak yang akan dibangun harus
memiliki kualitas yang baik yaitu dapat membangkitkan langkah secara tepat serta dapat menghitung nilai Running Time .
3.2 Pemodelan Perangkat Lunak
Pemodelan perangkat lunak dilakukan untuk memperoleh gambaran yang lebih jelas tentang objek apa saja yang akan berinteraksi dengan sistem serta hal-hal apa saja yang harus dilakukan oleh sebuah sistem sehingga sistem dapat berfungsi dengan baik sesuai dengan fungsionalitasnya.
Perancangan fungsionalitas pemilihan solusi 2048 akan dikembangkan dan dimodelkan dengan diagram use-case. Actor yang nantinya akan berinteraksi dengan sistem adalah human. Human dikategori sebagai entitas yang akan menjalankan program dan mencatat hasil solusi yang dibangkitkan (generated).
3.2.1 Use-Case Diagram
Use-case diagram merupakan diagram yang memodelkan perilaku dari sebuah
sistem. Use-case diagram memiliki actor use-case dan interaksi apa saja yang dilakukan actor tersebut.
Use-case untuk metode Generate and Test dapat dilihat seperti pada Gambar
(38)
19
Gambar 3.2 Use Case Generate and Test
Pada diagram Gambar 3.2 tersebut tampak bahwa seorang User (pengguna) hanya bekerja dengan mengakses use-case sistem pencarian jarak terpendek menggunakan metode Generate and Test. Pengguna tidak perlu mengetahui secara jelas proses apa saja yang terjadi pada setiap tahap. Dengan demikian untuk memutuskan proses apa yang nantinya dilakukan pada setiap tahap adalah menjadi tanggung jawab sistem.
3.2.1.1 Use Case Generate and Test
Spesifikasi use case Generate and Test dapat dilihat pada Tabel 3.1
Tabel 3.1. Spesifikasi Use Case Generate and Test
Name Generate and Test
Actors System
(39)
20
Precondition Pengguna menekan button mulai pada tampilan awal sistem
Post Condition Program mulai menjalankan proses dan menampilkan
langkah-langkah yang diambil sistem
Success Scenario 1. Pengguna menekan tombol start
2. Sistem menampilkan halaman generate and test
3. Sistem menjalankan perhitungan dan menampilkan langkah-langkah yang diambil
4. Sistem mencapai nilai 2048
Alternative Flows 1. Pengguna menekan tombol start
2. Sistem menampilkan halaman generate and test
3. Sistem menjalankan perhitungan dan menampilkan langkah-langkah yang diambil
4. Sistem kehabisan langkah dan berhenti
3.2.2 Activity Diagram
Activity diagram merupakan gambaran dari alur aktivitas sistem. Berikut ini activity diagram untuk masing-masing use case yang terdapat dalam sistem ini.
(40)
21
Gambar 3.3 Activity Diagram Generate and Test
3.2.3 Sequence Diagram
Proses pencarian jarak terpendek menggunakan metode Generate and Test adalah dengan melakukan pembangkitan rute-rute dengan DFS (Depth First Search),
Backtracking serta proses pencarian serta informasi hasil pencarian jarak terpendek
yang dalam penelitian ini digambarkan sebagai sequence diagram seperti pada Gambar 3.4.
(41)
22
Gambar 3.4 Sequence Diagram Generate and Test 3.3 Flowchart Sistem
Berdasarkan penjelasan sebelumnya, maka dapatlah digambarkan flowchart metode Generate and Test dalam mencari jarak terpendek dapat dilihat seperti pada Gambar 3.5.
(42)
23
Gambar 3.5 Flowchart Sistem
n = bilangan bulat (jumlah rute backtracking) (1,2,3 …) Begin
Terminate?
I<7 I = 1
I ++
Simpan posisi langkah yang akan keluar
Generate block baru & simpan posisinya
END Y
Y N
N
Tentukan langkah terbaik dan lakukan langkah terbaik
Mencapai 2048
(43)
24
3.3.1 Flowchart menentukan langkah terbaik
Gambar 3.6 Flowchart Langkah Terbaik 3.4 Pseudocode Sistem
Untuk lebih memahami sistem yang akan dibuat, maka berikut pseudocode program AI dari sistem yang akan dibuat. Dalam pembuatan AI generate and test terdapat 3 buah prosedur utama untuk membangkitkan langkah dan menjalankan langkah terbaik,yaitu
1. Reset Node(); 2. ContinueAI();
Pdeudocode reset node adalah sebagai berikut: 1. for (int i = 0; i < myNode.Length; i++)
Begin
Mengambil posisi dan angka yang digenerate
Menentukan langkah yang menyisakan banyak kotak kosong
End
Menentukan langkah dengan nilai tertinggi
(44)
25
2. {
3. myNode[i].intAngkaTinggi = 0; 4. myNode[i].intSisaKotak = 0; 5. myNode[i].intPosisiKeluar = -1; 6. myNode[i].BoardAktif = ""; 7. myNode[i].isIdle = false; 8. }
9. strSaveDataAIArah = ""; 10. strSaveDataAISpawn = "";
11. for (int j = 0; j < strRandSpawn6.Length; j++) strRandSpawn6[j] = myModule.RandomItemInString("0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15"); 12. ContinueAI();
13. }
Keterangan:
Tujuan dari prosedur ini adalah untuk mereset semua variabel yang telah dibangkitkan pada langkah sebelumnya. Semua variabel yang akan digunakan akan dikosongkan kemudian prosedur Continue AI akan dibangkitkan. Berikut merupakan detail penjelasan pseudocode untuk prosedur reset():
1) for (int i = 0; i < myNode.Length; i++)
myNode.Length merupakan jumlah panjang dari node yang dibangkitkan (generated). Untuk setiap node, dilakukan pembersihan untuk variabel yang terbentuk.
2) Untuk baris 2 sampai 7 merupakan variabel yang akan mereset node yang digunakan.
a. myNode[i].intAngkaTinggi merupakan array variabel untuk menampung nilai tertinggi dalam permainan;
b. myNode[i].intSisaKotak merupakan array variabel untuk menyimpan jumlah kotak kosong yang terdapat dalam permainan;
c. myNode[i].intPosisiKeluar merupakan array variabel untuk menyimpan posisi kotak baru yang akan ditampilkan;
d. myNode[i].BoardAktif merupakan array variabel untuk menyimpan posisi object yang merupakan hasil dari pembangkitan sebelumnya;
e. myNode[i].isIdle merupakan array boolean yang akan menampung nilai object ketika tidak bergerak dari posisi sebelumnya
3) strSaveDataAIArah merupakan array variabel untuk menyimpan arah yang akan ditempuh.
4) strSaveDataAISpawn merupakan array variabel untuk menyimpan tempat posisi kotak baru yang akan keluar.
(45)
26
6) Pemanggilan prosedur continue ai
Pseudocode ContinueAI() adalah sebagai berikut:
1)for (int k = 0; k < myNode.Length; k++) 2) {
3) if (k == 0) intCurSpawn5 = 0; 4) else if (k == 4) intCurSpawn5 = 1; 5) else if (k == 20) intCurSpawn5 = 2; 6) else if (k == 84) intCurSpawn5 = 3; 7) else if (k == 340) intCurSpawn5 = 4; 8) simulator4(k);
9) }
10)int getTmpIdx = 340; 11)int intAngkaTinggi = 0; 12)int intSisaKotak = 0;
13)for (int v = 340; v < myNode.Length; v++) 14){
15)if (!myNode[v].isIdle && ((intAngkaTinggi < myNode[v].intAngkaTinggi) || (intAngkaTinggi == myNode[v].intAngkaTinggi && intSisaKotak < myNode[v].intSisaKotak)))
16){
17)getTmpIdx = v;
18)intAngkaTinggi = myNode[v].intAngkaTinggi; 19)intSisaKotak = myNode[v].intSisaKotak; 20)}
21)}
22)for (int w = 5; w > 0; w--) 23){
24)strSaveDataAIArah =
myModule.AddItemReversed(strSaveDataAIArah, myNode[getTmpIdx].strArah);
25)strSaveDataAISpawn =
myModule.AddItemReversed(strSaveDataAISpawn, myNode[getTmpIdx].intPosisiKeluar.ToString()); 26)for (int x = 0; x < myNode.Length; x++)
27){
28)if (myNode[x].strNodeId == myNode[getTmpIdx].strNodeIdParent) 29){
30)getTmpIdx = x; 31)}
32)} 33)}
34)myController_Gameplay.intUpdate = 10; 35)}
(46)
27
Keterangan:
Tujuan dari prosedur continueAI adalah untuk menyimpan array langkah kemudian memilih langkah terbaik kemudian melakukan trace up untuk langkah yang terbaik.
3.5 Perancangan Antarmuka Pengguna (User Interface)
Dalam membangun sebuah sistem perlu adanya perancangan antarmuka (User
Interface) yang nantinya sangat membantu memudahkan pengoperasian sistem.
Dalam merancang antarmuka pengguna, ada beberapa syarat yang harus dipenuhi agar tercipta sebuah perangkat lunak yang mudah dan informatif untuk pengguna (user
friendly).
Gambar 3.7 Rancangan Tampilan Pertama
Keterangan:
1. Tampilan Judul program
2. Button Start yang akan menjalankan proses Generate and Test 3. Tampilan nama dan identitas pembuat program.
Tampilan menu utama hanya memiliki 1 Button yaitu tombol Start untuk memulai dan berisi tentang beberapa informasi tentang pembuat program. Ketika tombol Start ditekan maka akan dilanjutkan langsung pada tampilan permainan.
1
2
(47)
28
BAB IV
IMPLEMENTASI DAN PENGUJIAN SISTEM
4.1 Implementasi Sistem
Setelah melakukan proses analisis dan perancangan sistem, proses selanjutnya dalam penerapan pembuatan aplikasi adalah proses implementasi dan pengujian sistem. Implementasi merupakan tahap di mana sistem melakukan fungsionalitas utamanya setelah suatu program atau perangkat lunak selesai dirancang, sedangkan tahap pengujian merupakan tahap yang dilakukan setelah proses pengimplementasikan selesai dilakukan dan sampai proses uji coba sesuai dengan kriteria-kriteria yang diinginkan pengguna pada tahap perancangan sistem.
4.1.1 Tampilan permainan
Tampilan permainan merupakan tampilan untuk melakukan semua proses pengimplementasian proses generate and test dan pengambilan n langkah terbaik dalam permainan. Dimana n yang digunakan adalah 5 dan 6. Berikut ini pada gambar 4.1 menampilkan contoh tampilan permainan:
Gambar 4.1 Tampilan permainan (gameplay scene)
2
3
1
(48)
29
Keterangan:
1. Judul yang menampilkan nama program yang sedang dijalankan.
2. Tampilai User Interface yang akan menunjukan waktu ketika 1024 telah dicapai.
3. Tampilan User Interface untuk waktu yang sedang berjalan dan akan berhenti ketika telah mencapai 2048 atau program kehabisan langkah.
4. Panel merupakan tempat Game Object akan ditampilkan.
Pengujian dianggap berhasil jika dalam hasil pengerjaannya, program menunjukkan nilai 2048 pada kotak yang ada dan adanya pengukuran waktu yang dihentikan segera. Berikut contoh hasil program generate and test 5 langkah yang mampu berhasil yang dilakukan pada android:
Gambar 4.2 Tampilan berhasil
Suatu pengujian dianggap gagal apabila program mempunyai grid yang sudah penuh dan ditandai dengan permainan tidak dapat dijalankan lagi karena langkah berikutnya sudah tidak dapat dibangkitkan. Pada gambar 4.3 terlihat contoh pengujian 5 langkah yang tidak mampu mencapai 2048 dan pengukuran waktu dihentikan pada saat itu juga.
(49)
30
Gambar 4.3 Tampilan gagal
4.2 Perhitungan Manual
Adapun perhitungan manual yang dilakukan dalam pengerjaan sistem ini adalah untuk menentukan berapa banyak iterasi yang dilakukan untuk membangkitkan langkah yang ada.
Berikut ilustrasi langkah yang dapat dilakukan untuk 2 langkah berturut.
(50)
31
Dari ilustrasi tersebut dapat dilihat bahwa untuk pembangkitan langkah dari
parent terdapat 4 buah langkah yang mungkin sedangkan untuk langkah berikutnya
dibutuhkan lagi masing – masing 4 langkah yang mungkin dengan total 16 langkah. Jumlah iterasi yang perlu dilakukan untuk 2 buah langkah adalah 16+4=20. Sehingga untuk menghitung jumlah iterasi dilakukan 4n + 4n-1 + 4n-2 +...+ 4n-n.
Pada tabel 4.1 ditunjukkan hasil perhitungan jumlah iterasi yang perlu dilakukan untuk n buah langkah.
Tabel 4.1 Hasil perhitungan jumlah iterasi untuk n buah langkah
N 4n Perhitungan Total
1 4 4 4
2 16 4+16 20
3 64 20+64 84
4 256 84+256 340
5 1024 340+1024 1364
6 4096 1364+4096 5460
7 16384 5460+16384 21844 8 65536 21844+65536 87380 9 262144 87380+262144 349524 10 1048576 349524+1048576 1398100
4.3 Pengujian Sistem
Pada pengujian sistem permainan puzzle 2048, akan dilakukan proses generate 5 langkah dan 6 langkah untuk kemudian dibandingkan waktu kecepatan rata-rata dan nilai keberhasilan rata-rata dari masing-masing proses. Pengujian dilakukan pada perangkat android dan simulator yang sudah tersedia pada Unity 3D.
Dalam pengujiannya untuk mengambil data, maka program akan dijalankan sebanyak 10 kali untuk dihitung rata-ratanya untuk kemudian dibandingkan hasilnya. Berikut tabel 4.2 untuk menunjukan seluruh hasil pengukuran waktu solusi 2048 dengan 5 langkah:
(51)
32
Tabel 4.2 Hasil pengujian program terhadap waktu dan keberhasilan program dengan 5 langkah
Percobaan
ke- 1024 2048 Hasil
1 0:02:54 0:05:40 Gagal 2 0:02:58 0:05:43 Gagal 3 0:02:53 0:06:02 Gagal 4 0:03:04 0:06:39 Gagal 5 0:03:12 0:06:36 Gagal 6 0:03:26 0:06:34 Gagal 7 0:03:57 0:07:14 Berhasil 8 0:03:14 0:06:51 Berhasil 9 0:03:06 0:06:24 Berhasil 10 0:03:16 0:07:18 Gagal Rata-rata 0:03:12 0:06:30 30%
Dari hasil pengujian program generate and test 5 langkah, dapat dilihat bahwa persentase keberhasilan pada program semuanya dapat mencapai nilai 1024 dengan waktu rata-rata 3 menit 12 detik. Dengan program terminated pada waktu rata-rata 6 menit 30 detik. Dari tabel 4.1 terlihat bahwa keberhasilan pada program 5 langkah hanya mencapai 30% dengan catatan program terminated pada saat 1024 dan 512 sudah terlihat.
Dari hasil tersebut didapatkan bahwa metode tersebut kurang andal dalam mencari solusi sehingga pengujian dilakukan pada pembangkitan 6 langkah. Hasil pengukuran waktu untuk generate and test 6 langkah ditunjukan oleh tabel berikut:
Tabel 4.3 Hasil pengujian program terhadap waktu dan keberhasilan program dengan 6 langkah
Percobaan
ke- 1024 2048 Hasil
1 0:04:42 0:10:26 Gagal 2 0:04:27 0:09:00 Berhasil 3 0:04:36 0:09:07 Berhasil 4 0:04:48 0:08:54 Gagal 5 0:04:41 0:08:56 Berhasil 6 0:04:30 0:08:56 Berhasil 7 0:04:37 0:09:01 Berhasil 8 0:04:29 0:08:54 Berhasil
(52)
33
9 0:05:00 0:09:13 Berhasil 10 0:04:42 0:08:51 Gagal
Rata-rata 0:04:39 0:09:08 70%
Dari hasil pengujian program generate and test 6 langkah, dapat dilihat bahwa persen keberhasilan pada program semuanya dapat mencapai nilai 1024 dengan waktu rata-rata 4 menit 39 detik serta mampu mencapai 2048 dengan waktu rata-rata 9 menit 8 detik. Dapat dilihat pula dari tabel 4.2 bahwa keberhasilan pada program 6 langkah mencapai hingga 70%.
Jika dibandingkan, program 5 langkah mampu mencapai 1024 dengan waktu yang lebih singkat jika dibandingkan program 6 langkah, namun untuk mencapai 2048, program 5 langkah hanya memiliki 3 keberhasilan dari 10 percobaan. Berikut grafik perbandingan waktu mencapai 1024 pada program 5 langkah dan 6 langkah:
Gambar 4.6 Grafik perbandingan waktu mencapai 1024
Pada gambar 4.6, dapat dilihat bahwa pada setiap percobaan yang telah dilakukan, adanya waktu yang berlebihan dalam penyelesaian permainannya pada langkah ke – 6. Setelah dirata- ratakan waktu yang telah dicatat dan di ambil dari kedua tabel 4.2 dan tabel 4.3, maka akan didapatkan kelebihan waktu 1 menit 20 detik antara kedua buah langkah.
Pada langkah ke 6 dan langkah ke 5, dapat dilihat bahwa keduanya selalu berhasil dalam menyelesaikan permainannya sampai dengan 1024. Hal ini
(53)
34
membuktikan bahwa sampai dengan 1024, penggu naan langkah ke 5 akan cukup efektif dikarenakan waktu yang didapatkan lebih cepat dibandingkan dengan langkah ke 6. Namun, pencapaian permainan 1024 merupakan separuh jalan dalam menyelesaikan permainannya. Oleh karena itu, diharuskan untuk dibandingkan dalam pencapaian hasil akhirnya yaitu 2048.
Gambar 4.7 Grafik perbandingan waktu mencapai 2048
Pada Gambar 4.7 diatas, dapat dilihat bahwa perbandingan waktu langkah ke 5 dan langkah ke 6 sangatlah berbeda. Pada 10 percobaan yang telah dilakukan untuk mencapai 2048, langkah ke 6 membuktikan adanya pencapaian yang lebih baik dalam menyelesaikan permainan puzzle 2048. Langkah ke 5 memberikan waktu yang lebih cepat namun keberhasilan dalam penyelesaiannya sangat rendah.
Oleh karena itu, meski lebih cocok untuk 1024, langkah ke 5 tidak dapat diterapkan untuk menyelesaikan permainan 2048 hingga selesai. Di perlukan langkah ke 6 untuk memastikan keberhasilan permainan 2048 sampai akhir. Langkah ke 6 terbukti lebih efektif namun memerlukan waktu yang lebih lama juga.
(54)
35
BAB V
KESIMPULAN DAN SARAN
5.1. Kesimpulan
Berdasarkan pengujian sistem yang telah dilakukan, dapat diambil beberapa kesimpulan, yaitu:
1. Metode Generate and Test dapat digunakan untuk mencari solusi dalam menyelesaikan game puzzle 2048.
2. Semakin banyak iterasi yang digunakan dalam penentuan langkah selanjutnya, maka kemungkinan untuk menyelesaikan game puzzle 2048 semakin besar.
3. Waktu dalam menyelesaikan game puzzle 2048 akan bertambah dan berjalan semakin lambat jika iterasi yang digunakan semakin besar
5.2. Saran
Berdasarkan dari kesimpulan di atas, maka penulis memberikan beberapa saran untuk pengembangan sistem ini selanjutnya, yaitu:
1. Diharapkan agar metode Generate and Test dapat dibandingkan dengan metode lainnya seperti Algoritma MiniMax yang sering dipakai untuk menyelesaikan
game puzzle 2048.
2. Diharapkan agar game puzzle 2048 dapat diimplementasikan pada platform yang berbeda untuk dibandingkan dengan platformAndroid yang digunakan pada penelitian ini.
3. Diharapkan agar iterasi yang lebih tinggi dapat di percepat waktu perhitungannya sehingga dapat menyelesaikan game puzzle 2048 dengan lebih efektif.
(55)
9
BAB 2
TINJAUAN PUSTAKA
2.1. Kecerdasan Buatan
Kecerdasan buatan (artificial intelligence), yang disingkat AI, merupakan salah satu cabang dalam ilmu komputer yang mempelajari tentang bagaimana membuat komputer menyelesaikan suatu masalah sebaik yang dapat dilakukan oleh manusia.
Kecerdasan buatan adalah sebuah teknologi yang baru muncul pada dekade ini dengan banyak aplikasi terapan yang sedang berkembang. Salah satu pandangan dalam kecerdasan buatan berhubungan tentang cara membuat komputer menjadi lebih pintar. Sehingga penelitian pada kecerdasan buatan berfokus pada 2 hal, yaitu:
1. Membuat mesin lebih berguna 2. Memahami kecerdasan
Masalah dalam pengembangan kecerdasan buatan umumnya berkaitan dengan cara mengenal proses yang kompleks, tidak pasti dan ambigu. Proses yang tidak memiliki penyelesaian secara algoritma dan membutuhkan suatu metode penyelesaian yang mengikuti pola pemikiran manusia dan hewan untuk mengatasi masalah yang kompleks. (Coppin, 2004)
Manusia pandai dalam menyelesaikan permasalahan karena manusia memiliki kemampuan merasakan indera (sentience) dan kecerdasan
(Inteligence).Untuk menirukan kemampuan indera manusia, komputer dapat
dihubungkan dengan sebuah kamera atau scanner sehingga dapat melihat seperti manusia. Komputer juga dipasangkan sensor seperti microphone dan dapat diprogram sehingga dapat mengenali kata-kata dan membalas sesuai perintah.
(56)
10
Untuk mendapatkan kemampuan merasakan, komputer dapat dihubungkan dengan sensor yang tepat.
Kecerdasan sering didefiniskan sebagai kemampuan untuk mempelajari. Kemampuan manusia untuk mempelajari dapat dilakukan karena manusia mempunyai pengetahuan dan pengalaman.Pengetahuan diperoleh dari belajar.Semakin banyak bekal pengetahuan yang dimiliki, seseorang diyakini lebih mampu dalam menyelesaikan permasalahan.Namun, bekal ilmu pengetahuan saja tidaklah cukup jika manusia tidak diberikan akal untuk melakukan penalaran yang digunakan untuk mengambil kesimpulan berdasarkan pengalaman dan pengetahuan yang dimiliki. Tanpa memiliki kemampuan untuk menalar dengan baik, manusia dengan sejumlah pengalaman dan pengetahuan tidak akan dapat menyelesaikan masalah dengan baik. Demikian juga dengan kemampuan menalar yang sangat baik, namun tidak memiliki pengetahuan dan pengalaman yang memadai, seseorang tidak akan bisa menyelesaikan masalah dengan baik.
Mesin diciptakan untuk membantu manusia dalam menyelesaikan dan membantu manusia didalam kesehariannya.Dengan demikian, mesin juga diharapkan dapat menjadi cerdas yaitu dapat bertindak seperti dan sebaik manusia.Diharapkan bahwa aplikasi komputer atau mesin yang dibuat dan diciptakan dapat menjadi lebih pintar dan mudah dalam penggunaannya serta ditingkatkan lagi dalam efisiensi penggunaannya.Oleh karena itu, mesin diberikan pengetahuan sehingga mempunyai kemampuan untuk menalar dengan baik.(Karam, 2012)
Pengertian kecerdasan buatan dapat dipandang dari berbagai sudut pandang, antara lain:
1. Sudut pandang kecerdasan
Kecerdasan buatan akan membuat mesin menjadi cerdas (mampu berbuat seperti apa yang dilakukan oleh manusia).
2. Sudut pandang penelitian
Kecerdasan buatan adalah suatu studi bagaimana membuat agar komputer dapat melakukan sesuatu sebaik yang dikerjakan oleh manusia.
(57)
11
Kecerdasan buatan adalah kumpulan peralatan yang sangat kuat dan metodologis dalam menyelesaikan masalah- masalah bisnis.
4. Sudut pandang pemrograman
Kecerdasan buatan meliputi studi tentang pemrograman simbolik, penyelesaian masalah dan pencarian.Dalam pembuatan aplikasi kecerdasan buatan, ada dua bagian utama yang sangat dibutuhkan, yaitu:
a. Basis pengetahuan (Knowledge Base), bersifat fakta- fakta, teori, pemikiran dan hubungan antar satu dengan yang lainnya.
b. Motor Inferensi (Inference Engine), kemampuan menarik
kesimpulan berdasarkan pengetahuan dan pengalaman.
2.1.1 Turing Test
Untuk menentukan apakah suatu kecerdasan buatan sudah mendekati kemampuan manusia dan dapat disebut ‘cerdas’, dilakukan suatu percobaan yang disebut Turing Test yang ditemukan oleh Alan Turing pada tahun 1950, seorang pioneer AI dan ahli matematika asal Inggris yang melakukan experiment dengan menempatkan AI di satu terminal dan terminal lainnya dikendalikan oleh manusia. Kedua terminal ini ditempatkan di posisi berjauhan. Manusia tersebut berkomunikasi dengan komputer tersebut dan mengira bahwa lawan komunikasinya adalah manusia juga. Menurut Turing jika seseorang bisa salah mengira komputer sebagai manusia, maka komputer tersebut bisa dikatakan ‘cerdas’.
Untuk dapat lolos Turing Test, komputer harus setidaknya memiliki kemampuan untuk melakukan beberapa proses berikut:
A. Natural language processing, yaitu kemampuan komputer agar dapat
berkomunikasi dengan lancar dengan struktur bahasa yang natural.
B. Knowledge representation, yaitu kemampuan komputer menyimpan
informasi-informasi yang diterimanya dan bertindak sebagai pengetahuan komputer.
C. Automated reasoning, yaitu kemampuan komputer dalam mengolah informasi
(58)
12
D. Machine learning, yaitu kemampuan komputer untuk mempelajari hal baru
dan beradaptasi terhadap hal yang baru. Cara paling sederhana dalam
machine learning adalah dengan mencoba dan gagal (trial and error).
Selain Turing Test, terdapat Total Turing Test yang membutuhkan 2 proses tambahan selain 4 proses yang telah disebutkan untuk dapat lolos tes ini. Agar dapat lolos, sebuah komputer juga harus mampu melakukan 2 proses berikut:
A. Computer vision, dimana komputer harus mampu melihat dan
menginterpretasikan objek.
B. Robotics, dimana komputer mampu memanipulasi objek dan dapat
bergerak.(Norvig,2010)
2.2 Bidang-bidang Terapan pada Kecerdasan Buatan
Berikut beberapa bidang terapan yang dapat dihubungkan dengan kecerdasan buatan:
a. Sistem pakar (expert system)
Sebuah sistem komputer yang digunakan sebagai sarana untuk menyimpan pengetahuan yang dimiliki oleh seorang pakar dengan tujuan agar komputer memiliki keahlian untuk menyelesaikan permasalahan dengan meniru keahlian yang dimiliki pakar tersebut.
b. Pengolahan bahasa alami (natural language processing)
Pemrograman sistem komputer yang memungkinkan manusia berkomunikasi dengan komputer dengan menggunakan bahasa sehari-hari.
c. Pengenalan suara (speech recognition)
Kemampuan membuat komputer agar dapat mengenali suara dan melakukan perintah yang diberikan kepadanya melalui suara tersebut.
(59)
13
Kumpulan sistem yang mampu memanipulasi benda dan bergerak sesuai dengan program di dalamnya dan dilengkapi berbagai sensor untu mendeteksi pekerjaan secara otomatis.
e. Intelligence computer-aided instruction
Sistem komputer yang digunakan sebagai pengajar untuk manusia.
f. Computer vision
Pemrograman yang bertujuan untuk menginterpretasikan gambar dan objek tampak melalui komputer untuk proses selanjutnya.
g. Game playing
Sistem permainan yang dilengkapi dengan kecerdasan buatan untuk bergerak sendiri tanpa dikendalikan. AI akan menggerakan karakter dengan sendirinya tanpa dikendalikan oleh pemain (Non-Player Character).
Dalam pembuatan AI dalam game playing dapat dilakukan dengan beberapa cara, salah satunya adalah dengan menggunakan metode pencarian Heuristik.
2.3 Metode Pencarian Heuristik
Teknik pencarian heuristik (heuristic searching) atau dikenal juga dengan
rapid-prototyping merupakan suatu strategi untuk melakukan proses pencarian ruang
keadaan (state space) suatu problema secara selektif, yang memandu proses pencarian yang kita lakukan disepanjang jalur yang memiliki kemungkinan sukses paling besar, dan mengesampingkan usaha yang bodoh dan memboroskan waktu.
Heuristik merupakan sebuah teknik yang mengembangkan efisiensi dalam proses pencarian, namun dengan kemungkinan mengorbankan kelengkapan (completeness). Heuristik dapat diterapkan dengan baik dalam suatu domain tertentu jika memiliki suatu fungsi heuristik, dimana fungsi heuristik ini digunakan untuk mengevaluasi keadaan keadaan problema individual dan menentukan seberapa jauh hal tersebut dapat digunakan untuk mendapatkan solusi yang diinginkan.
Jenis – jenis pencarian heuristik terdiri atas Generate and Test, Hill
Climbing, Best First Search, Alpha Beta Prunning, Means-End-Analysis, dan Constraint Satisfaction.
(60)
14
B D
B A
8
4 3
7
6 C
5
D
B 8
4 3
7
6
2.3.1 Generate and Test
Metode Generate and Testadalah metode yang paling sederhana dalam teknik pembelajaran komputer.Metode ini menciptakan semua solusi yang mungkin dikerjakan secara sistematis dengan aturan tertentu dan menjamin akan menemukan solusi terhadap suatu masalah. Namun, jika ruang masalahnya sangat luas, mungkin memerlukan waktu yang sangat lama.
Algoritma Generate And Test menggunakan prosedur Depth First
Search(DFS) karena suatu solusi harus dibangkitkan secara lengkap sebelum
dilakukan Test. Algoritma ini berbentuk sistematis, pencarian sederhana yang mendalam dari suatu ruang permasalahan. Generate And Test juga dapat dilakukan dengan pembangkitan solusi secara acak, tetapi tidak ada jaminan solusinya akan ditemukan.
Di dalam Generate And Test, terdapat dua prosedur penting: pembangkit (membangkitkan sebuah solusi yang mungkin) dan tes (menguji solusi yang dibangkitkan tersebut). Dengan penggunaan memori yang sedikit, DFS bisa digunakan sebagai prosedur Pembangkit yang menghasilkan suatu solusi. (Suyanto, 2007)
Contoh penyelesaian dengan menggunakan metode Generate and Test dapat dilihat pada gambar 2.1 dan gambar 2.2. Gambar 2.1 merupakan contoh penggunaan
generate pada pencarian jalur, sedangkan gambar 2.2 merupakan contoh penggunaan generate pada pencarian 5 langkah game 2048.
(61)
15
Gambar 2.2. Ilustrasi Alur Pencarian Generate and Test untuk pencarian 4
langkah
Dari kedua gambar tersebut, maka dapat dihasilkan tabel hasil langkah yang mungkin untuk kemudian dilakukan langkah test. Tabel 2.1 menujukkan hasil langkah
test untuk panjang lintasan terpilih sebagai berikut:
Tabel 2.1 Tabel hasil lintasan terpendek menggunakan Generate and Test
Pencarian
Ke - Lintasan
Panjang Lintasan
Lintasan Terpilih
Panjang Lintasan Terpilih
1 ABCD 19 ABCD 19
2 ABDC 18 ABDC 18
3 ACBD 12 ACBD 12
4 ACDB 13 ACBD 12
5 ADBC 16 ACBD 12
Pada tabel 2.1 dapat dilihat bahwa jalur terpendek adalah melalui lintasan ACBD dengan panjang lintasan 12. Maka langkah selanjutnya, AI akan menjalankan langkah ACBD.
(62)
16
2.3.1.1 Algoritma Generate and Test
Algoritma generate and test menurut (Suyanto, 2007) pada generate and test adalah sebagai berikut:
1. Bangkitkan sebuah solusi yang mungkin. Solusi bisa berupa suatu keadaan(state). 2. Lakukan Testapakah solusi yang dibangkitkan tersebut adalah sebuah solusi yang
bisa diterima sesuai dengan kriteria yang diberikan.
3. Jika solusi telah ditemukan, keluar. Jika belum, kembali ke langkah 1. (Suyanto, 2007)
Sedangkan menurut (Kyaw, 2013), algoritma generate and test adalah sebagai berikut:
Generate_and_test() {
Begin:
Dijabarkan solusi yang memungkinkan;
Evaluasi solusi dengan membandingkannya dengan criteria yang telah diterima;
If (solusi memuaskan dan sesuai dengan kriteria yang diinginkan) quit; Else go to begin;
}
Dari kedua kutipan tersebut, dapat kita dapat menarik kesimpulan bahwa algoritma generate and test terdiri dari proses pembangkitan (generate) dan pengujian (test).
2.4 Unity
Unity merupakan suatu aplikasi yang digunakan untuk mengembangkan
game multi platform yang didesain agar mudah digunakan. Unity dipenuhi perpaduan
(63)
17
Editor pada Unity dibuat dengan user interface yang sederhana. Grafis pada unity dibuat dengan grafis tingkat tinggi untuk OpenGL dan directX. Unity mendukung semua format file, terutamanya format umum seperti semua format dari art
applications. Unity cocok dengan versi 64-bit dan dapat beroperasi pada Mac OS x
dan Windows dan dapat menghasilkan game untuk Mac, Windows, Wii, iPhone, iPad dan Android.
Unity secara rinci dapat digunakan untuk membuat video game 3D,animasi 3D real timedan visualisasi arsitektur dengan isi serupa yang interaktif. Editor Unity dapat menggunakan plugin web player dan menghasilkan game browser yang didukung oleh Windows dan Mac. Plugin web player dapat juga dipakai untuk
widgets Mac. Unity juga akan mendukungconsole terbaru seperti PlayStation 3 dan
Xbox 360.
Server aset dari Unity dapat digunakan semua scripts dan aset game sebagai solusi dari versi kontrol dan dapat mendukung proyek yang terdiri atas banyak
gigabytes dan ribuan dari file multi-megabyte. Editor Unity dapat menyimpan
metadata dan versi yang dapat berjalan, pembaharuan dan didalam perbandingan versi grafis. Editor Unity dapat diperbaharui secara langsung seperti file yang telah dimodifikasi. Server aset Unity juga cocok pada Mac, Windows dan Linux dan juga berjalan pada PostgreSQL, database server opensource.
2.4.1Fitur-fitur pada Unity
Unity sebagai editor memiliki fitur-fitur seperti rendering, scripting, asset tracking,
multi-platform, asset store, physics engine yang akan turut membantu dalam
pengembangan aplikasi.
2.4.1.1 Rendering
Graphics engine yang digunakan adalah Direct3D (Windows, Xbox 360), OpenGL (Mac, Windows, Linux, PS3), OpenGL ES (Android, iOS), dan proprietary APIs (Wii). Ada pula kemampuan untuk bump mapping, reflection mapping, parallax
(64)
18
mapping, screen space ambient occlusion (SSAO), dynamic shadows using shadow maps, render-to-texture and full-screen post-processing effects.
Unity dapat mengambil format desain dari 3Ds Max, Maya, Softimage, Blender, modo, ZBrush, Cinema 4D, Cheetah3D, Adobe Photoshop, Adobe Fireworks and Algorithmic Substance. Asset tersebut dapat ditambahkan ke game project dan diatur melalui graphical user interface Unity.
ShaderLab adalah bahasa yang digunakan untuk shaders, dimana mampu memberikan deklaratif “programming” dari fixed-function pipeline dan program shader ditulis dalam GLSL atau Cg. Sebuah shader dapat menyertakan banyak varian dan sebuah spesifikasi fallback declarative, dimana membuat Unity dapat mendeteksi berbagai macam video card terbaik saat ini, dan jika tidak ada yang kompatibel, maka akan digunakanshader alternatif yang mungkin dapat menurunkan fitur dan performa.
2.4.1.2 Scripting
Script game engine dibuat dengan Mono 2.6, sebuah implementasi open-source dari .NET Framework.Programmer dapat menggunakan UnityScript (bahasa
terkustomisasi yang terinspirasi dari sintax ECMAScript, dalam bentuk JavaScript), C#, atau Boo (terinspirasi dari sintaks bahasa pemrograman phyton).Dimulai dengan dirilisnya versi 3.0, Unity menyertakan versi MonoDevelop yang terkustomisasi untuk
debug script.
2.4.1.3 Asset Tracking
Unity juga menyertakan Server Unity Asset – sebuah solusi terkontrol untuk developer game asset dan script. Server tersebut menggunakan PostgreSQL sebagai
backend, sistem audio dibuat menggunakan FMOD library (dengan kemampuan untuk
memutar Ogg Vorbis compressed audio), video playback menggunakan Theora codec,
engine daratan dan vegetasi (dimana mendukungtree billboarding, Occlusion Culling
dengan Umbra), built-in lightmapping dan global illumination dengan Beast,
multiplayer networking menggunakan RakNet, dan navigasi mesh pencari jalur built-in.
(65)
19
2.4.1.4 Multi-Platforms
Unity support pengembangan ke berbagai plaform. Didalam project,
developer memiliki kontrol untuk mengirim keperangkat mobile, web browser, desktop, and console. Unity juga mengijinkan spesifikasi kompresi textur dan
pengaturan resolusi di setiap platform yang didukung.
Saat ini platform yang didukung adalah BlackBerry 10, Windows 8, Windows Phone 8, Windows, Mac, Linux, Android, iOS, Unity Web Player, Adobe Flash, PlayStation 3, Xbox 360, Wii U and Wii. Meskipun tidak semua terkonfirmasi secara resmi, Unity juga mendukung PlayStation Vita yang dapat dilihat pada game Escape Plan dan Oddworld: New ‘n’ Tasty.
2.4.1.5 Asset Store
Diluncurkan November 2010, Unity Asset Store adalah sebuah resource yang hadir di Unity editor. Asset store terdiri dari koleksi lebih dari 4,400 asset packages, beserta 3D models, textures dan materials, sistem particle, musik dan efek suara, tutorial dan project, scripting package, editor extensions dan servis online.
2.4.2.6 Physics Engine
Unity juga memiliki suport built-in untuk PhysX physicsengine (sejak Unity 3.0) dari Nvidia (sebelumnya Ageia) dengan penambahan kemampuan untuk simulasi
real-timecloth pada arbitrary dan skinned meshes, thick ray cast, dan collision layers.
2.5 Android
Permainan komputer (computer game) adalah permainan video yang dimainkan pada komputer pribadi, dan bukan pada konsol permainan, maupun mesin ding-dong.Permainan komputer telah berevolusi dari sistem grafis sederhana sampai menjadi kompleks dan mutakhir.Namun, pasar permainan komputer di Amerika Serikat mulai menurun sejak tahun 1999. (Maulina, 2014)
(66)
20
Game komputer dibuat oleh satu atau beberapa pengembang game,
biasanyabersama dengan spesialis lainnya (seperti game artists) dan dipublikasikan baik secara sendiri atau melalui penerbit pihak ketiga. Mereka kemudian mendistribusikan pada media fisik seperti DVD dan CD, atau dapat didistribusikan secara bebas melalui internet, software, atau melalui jasa pengiriman online seperti Direct2Drive dan Steam. Game komputer membutuhkan hardware khusus di komputer pengguna untuk bermain, seperti generasi spesifik unit pemrosesan grafik atau koneksi internet untuk bermain online, meskipun persyaratan sistem ini bermacam-macam pada setiap game.(Murya, 2014)
(67)
12
BAB 1 PENDAHULUAN
1.1. Latar Belakang
Kecerdasan buatan merupakan cabang ilmu computer yang bertujuan membuat mesin menjadi lebih pintar dan dapat melakukan pekerjaan seperti manusia. Kecerdasan dapat diterapkan dalam membuat game dengan menentukan sejumlah aturan. Kecerdasan buatan dalam game umumnya digunakan untuk membuat non – player
characters (NPCs) yang bergerak dengan sendirinya didalam game. Selain itu,
kecerdasan buatan juga digunakan untuk menghasilkan solusi dari sistem kepada pemain game. Jadi tujuan adanya kecerdasan buatan tidak untuk mereplikasi pikiran dari binatang atau manusia, namun untuk membuat NPCs lebih cerdas dengan reaksinya sendiri dalam game sesuai dengan lingkungan yang dihadapinya.
Game memiliki banyak variasi bentuk dan diciptakan mulai dari tingkat
kesulitan mudah kompleks dengan tujuan membuat suatu game menjadi lebih seru untuk dimainkan. Permainan puzzle merupakan salah satu permainan yang
membutuhkan pemikiran yang panjang dalam menentukan langkah selanjutnya yang akan diambil. Permainan puzzle yang cukup dikenal akhir–akhir ini adalah permainan
puzzle 2048 yang merupakan salah satu permainan game yang dimainkan dengan cara
memberikan masukan berupa arah untuk menggeser kotak-kotak yang muncul didalamnya. Ketika dua dari kotak yang saling berhimpit berisikan angka yang sama, maka mereka akan disatukan dan nilainya dijumlahkan. Tujuan utama dari game ini adalah mendapatkan kotak dengan nilai 2048 sebelum semua grid terisi penuh dan tidak ada kotak yang dapat disatukan lagi. Permainan puzzle 2048 diciptakan oleh Gabriel Cirulli untuk iOS dan Android dan cukup banyak beredar.
Permainan puzzle 2048 banyak diminati oleh berbagai kalangan dikarenakan adanya tantangan dalam mencapai hasil akhirnya, yaitu 2048. Permasalahan yang
(68)
13
(69)
5
nilai tertinggi. Beberapa orang berspekulasi bahwa permainan puzzle 2048 mungkin tidak dapat diselesaikan. Oleh karena itu, adanya beberapa penerapan rumus dan penerapan algoritma dalam mencari penyelesaian dari permainan tersebut. Kecerdasan buatan diharapkan dapat membantu menyelesaikan permainan 2048 sehingga pemain dapat mempelajari bagaimana cara menyelesaikan permainannya pada perangkat mobile seperti Android.
Dalam pembuatan game pada perangkat mobile seperti smartphone berbasis
Android, dapat digunakan beberapa cara, salah satunya adalah dengan menggunakan game engine. Game engine menawarkan paket pengembangan visual dan elemen-
elemen software yang dapat digunakan kembali, selain itu juga ditawarkan built-in
platform dan fitur lainnya yang memungkinkan efisiensi dalam pengembangan game.
Hal ini akan memudahkan developer dalam membuat sebuah game dibandingkan dengan mengetikkan program pada file kosong karena game engine menyediakan berbagai fitur – fitur seperti penyisipan gambar, tombol, bahkan grafik 3D. Game
engine yang akan digunakan pada pembuatan algoritma kecerdasan buatan ini adalah game engine Unity.
Penulis ingin merancang suatu aplikasi untuk permainan puzzle 2048 dimana
game tersebut akan dikembangkan dengan menggunakan metode Generate and Test
sebagai algoritma kecerdasan buatannya. Oleh karena itu, judul “Implementasi
Metode Generate and Test Pada Permainan Puzzle 2048 Berbasis Mobile”
diangkat oleh penulis dimana dalam merancangnya, akan dikembangkan dengan menggunakan game engine Unity.
1.2. Rumusan Masalah
Berdasarkan uraian pada latar belakang, maka rumusan masalah yang akan dibahas adalah bagaimana memperoleh solusi dari permainan puzzle 2048 dengan
mengimplementasikan metode Generate and Test dan merancangnya ke perangkat
(1)
vi
ABSTRAK
Kecerdasan buatan sering digunakan untuk menyelesaikan masalah dengan suatu metode yang konkrit, salah satunya adalah untuk membuat solusi untuk permainan 2048. Dalam mencapai poin 2048 pada permainannya, dapat digunakan beberapa algoritma dimana salah satunya adalah metode generate and test. Metode generate and test adalah algoritma yang membangkitkan semua n langkah yang memungkinkan dan mengambil langkah yang mendapatkan poin yang tertinggi. Kecerdasan buatan kemudian akan menjalankan langkah – langkah yang dapat menghasilkan poin yang ingin dicapai. Dalam membangkitkan n yang berbeda, maka hasil dan waktu yang didapatkan juga akan berbeda. Pembangkitan n yang lebih tinggi akan menghasilkan solusi yang lebih diinginkan namun akan memakan waktu rata- rata yang lebih lama daripada pembangkitan n yang lebih kecil.
Kata kunci: Kecerdasan buatan, Generate and Test , puzzle game 2048.
(2)
vi
IMPLEMENTATION OF GENERATE AND TEST METHODS ON MOBILE BASED PUZZLE GAME 2048
ABSTRACT
Artificial intelligence is often used to solve problems with a concrete method, one of them is to create a solution for game 2048. In reaching point 2048 in the game, there are algorithms that can be used and one of them is generate and test method. Generate and test method is an algorithm that generate every possible n - steps possibility and determined the best steps with the highest point. Then, the artificial intelligence will perform the steps that will produce the specified point. For n different generation will produce different results and different time. For higher n will produce a more desirable solution, however it will take longer time.
(3)
viii
DAFTAR ISI
Halaman
Persetujuan ... ii
Pernyataan ... iii
Penghargaan ... iv
Abstrak ... vi
Abstract ... vii
Daftar isi ... viii
Daftar Gambar... x
Daftar Tabel ... xi
Bab 1 Pendahuluan 1.1 Latar Belakang 1 1.2 Rumusan Masalah 2
1.3 Batasan Masalah 2 1.4 Tujuan Penelitian 3
1.5 Manfaat Penelitian 3
1.6 Metodologi Penelitian 3 1.7 Sistematika Penulisan 4 Bab 2 Tinjauan Pustaka 2.1 Kecerdasan Buatan 5
2.1.1 Turing Test 7
2.2 Bidang – Bidang Terapan pada Kecerdasan Buatan 8 2.3 Metode Pencarian Heuristik 9 2.3.1 Generate and Test 9 2.3.1.1 Algoritma Generate and Test 11 2.4 Unity 12 2.4.1 Fitur – Fitur Pada Unity 13 2.4.1.1 Rendering 13
2.4.1.2 Scripting 13
2.4.1.3 Asset Tracking 14 2.4.1.4 Multi-Platform 14 2.4.1.5 Asset Store 14 2.4.1.6 Physics Engine 15
2.5 Android 15 Bab 3 Analisis dan Perancangan sistem 3.1 Analisis 16 3.1.1 Analisis Masalah (Problem Analysis) 16 3.1.2 Analisis Persyaratan (Requirement Analysis) 17 3.1.2.1 Persyaratan Fungsional 17
(4)
ix
3.1.2.2 Analisis Persyaratan Non – Fungsional 17
3.2 Pemodelan Perangkat Lunak 18
3.2.1 Use-Case Diagram 18
3.2.1.1 Use Case Generate and Test 19
3.2.2 Activity Diagram 20
3.2.3 Sequence Diagram 22
3.3 Flowchart System 22
3.3.1 Flowchart menentukan langkah terbaik 24
3.4 Pseudocode Sistem 24
3.5 Perancangan Antarmuka Pengguna (User Interface) 27 Bab 4 Implementasi dan Pengujian Sistem
4.1 Implementasi Sistem 28
4.1.1 Tampilan Permainan 28
4.2 Perhitungan Manual 30
4.3 Pengujian Sistem 31
Bab 5 Kesimpulan dan Saran
5.1 Kesimpulan 35
5.2 Saran 35
Daftar Pustaka 36
Lampiran A A-1
Lampiran B B-1
Lampiran C C-1
Lampiran D D-1
Lampiran E E-1
(5)
x
Halaman Gambar 2.1 Ilustrasi Lintasan Metode Generate and Test 10 Gambar 2.2 Ilustrasi Alur pencarian Generate and Test untuk
pencarian 4 langkah 10
Gambar 3.1 Diagram Ishikawa untuk Analisis Permasalah Sistem 16
Gambar 3.2 Use Case Generate and Test 18
Gambar 3.3 Activity Diagram Generate and Test 21
Gambar 3.4 Sequence Diagram Generate and Test 22
Gambar 3.5 Flowchart Sistem 23
Gambar 3.6 Flowchart Langkah Terbaik 24
Gambar 3.7 Rancangan Tampilan Pertama 27
Gambar 4.1 Tampilan Permainan (Gameplay Scene) 28
Gambar 4.2 Tampilan Berhasil 29
Gambar 4.3 Tampilan Gagal 30
Gambar 4.4 Ilustrasi Pembangkitan Untuk 2 Langkah 30
Gambar 4.5 Grafik perbandingan waktu mencapai 1024 33
Gambar 4.6 Grafik perbandingan waktu mencapai 2048 34
DAFTAR GAMBAR
(6)
xi
DAFTAR TABEL
Halaman Tabel 2.1 Hasil lintasan terpendek menggunakan Generate and Test 11
Tabel 3.1 Spesifikasi Use Case Generate and Test 19
Tabel 4.1 Hasil Perhitungan Jumlah Iterasi untuk n buah langkah 31 Tabel 4.2 Hasil Pengujian program terhadao waktu dan keberhasilan
program dengan 5 langkah 32
Tabel 4.3 Hasil Pengujian program terhadap waktu dan keberhasilan