2017年3月27日 星期一

製作日誌--018

上周在趕作業,就沒有更新了
於是今天的更新決定來個大的
本日將鬧鐘系統搭載完成
以及將失望表情的動畫完成

###鬧鐘###

實作上跟備忘錄差不多,因為兩者本質上是類似的
一樣有新增項目、查看、刪除、清空與開關的功能
不過鬧鐘這裡不一樣的是
只要是沒有設定任何鬧鐘的情況下
開關就一定是關著的狀態
且不被允許在沒有鬧鐘的情況下打開鬧鐘
這個部分下面會詳細說明

由於各項鬧鐘功能的實作和備忘錄十分相似
這裡只說明基本鬧鐘的做法
首先先在初始參數中宣告"alarmtime"、"alarmnum"、"alarmopen"三個變數
alarmtime是用來儲存全部的鬧鐘時間
其形態是以字串為元素的陣列
alarmnum代表目前設定的鬧鐘個數
alarmopen則是用來判斷目前鬧鐘是否為開啟狀態
接著看到這段程式碼:

SetAlarm
{
    "\0\s[0]想要小鳥在什麼時候叫%(username)呢?\![open,timeinput,OnSetAlarm]\e"
}

OnSetAlarm
{
    tmpalarmtime = reference0
    time = SPLIT(reference0,",")
    "\0\s[0]在%(time[0])時%(time[1])分的時候提醒%(username)嗎?\n\n/
    \q[○是,SetAlarmYes]\n/
    \q[○否,SetAlarmNo]\e"
}

Select.SetAlarmYes
{
    alarmtime ,= tmpalarmtime
    alarmnum += 1
    "\0\s[0]我知道了!\e"
}

Select.SetAlarmNo
{
    "\0\s[0]真的不需要小鳥提醒%(username)嗎?\w8\1\s[10]總是不能什麼事都依賴妳吧。\w8\0\s[0]\n\n嗯…\w5我知道了。\e"
}

教學文章進行至此,相信讀者應該都已經對SakuraScript有一定的了解了
這裡就簡單說明這段程式碼的功能
首先是先詢問使用者想要設定鬧鐘的時間
輸入的時間會被當作字串傳入OnSetAlarm
我們只取時與分
然後詢問使用者輸入是否正確
是的話就新增鬧鐘,不是就不做任何修改

再來我們直接跳過其他功能的實作
這些功能的寫法都可以參考備忘錄的作法
詳情請閱讀製作日誌--014製作日誌--017
以下我們看到鬧鐘實踐的方式:

if alarmopen == 1
{
    for i = 0; i < alarmnum; i ++
    {
        time = alarmtime[i]
        time = SPLIT(time,",")
if hour == time[0] && minute == time[1]
        {
"\0\s[0]現在是%(time[0])時%(time[1])分喔!\![sound,play,alarm.mp3]\x\![sound,stop]"
--
"\0\s[0]唉嘿嘿,小鳥有記得提醒%(username)喔!"
"\0\s[2]咦…\w5…\w5…\w8\n%(username)怎麼一臉呆滯?\w8\1\s[10]該不會是小鳥妳把%(username)給嚇傻了吧。\w8\0\s[0]\n\n真的嗎!?\w5\n對不起!%(username)!"
--
"\e"
break
}
    }
}

這段程式碼放在OnMinuteChange事件中
每一分鐘過去就檢查一次是否有鬧鐘該響鈴
首先檢查鬧鐘是否開啟
接著用for迴圈將所有鬧鐘檢查過一輪
一旦找到一個符合的時間就響鈴
而響鈴的辦法是使用\![sound,play,alarm.mp3]
這個指令會去自動搜尋放在人格資料夾下稱為alarm.mp3的檔案
並且播放
接著看到\x指令
這個指令會使目前對話框停滯,直到使用者去點擊對話框為止
點擊後對話框會直接刷新,進行之後的對話
而我們可以看到,在\x指令後接著\![sound,stop]的指令
因為使用者點擊就代表關掉鬧鐘的動作
這樣就完成鬧鐘功能了

===================================================================
把失望表情的動畫給實作了
之後畫的表情可能會開始脫離偽春菜的預設表情列表
以需要用到的為優先考量


via GIPHY

有點鬧彆扭的樣子真可愛

2017/03/27

2017年3月13日 星期一

製作日誌--017

難得的準時更新
今天把備忘錄功能補齊了
因為偽春菜本身有自己的一套語法
很多操作上有不少限制
只能用比較取巧的方式去處理一些功能

###備忘錄###

本日的更新內容只有備忘錄
因為刪除項目的部份讓我研究了一兩個小時
以下開始說明實作方法

首先,假設我們的備忘錄參數memo現在長這樣子:

memo = "0\n1\n2\n"

在查看備忘錄時,因為有\n的存在,看起來就像條列式的清單
為了讓使用者可以選取想要刪除的項目
我們先用AYA的內建函數SPLIT來處理字串:

memoarr = SPLIT(memo,"\n")

上面的操作會將memo分割成陣列,而分割點為\n
在這裡便會將memo分割成["0","1","2",""]
需注意最後面會多出一個空字串
因為SPLIT的分割模式是一但看到分割點
就會將前後分別做為單一字串放入陣列
因此在memo中最後一個\n的前後分別是"2"與""
這個部分讓我頭痛了一陣子
所以在這裡特別提醒一下
接著就是要將選項輸出了

大家應該還記得選項的輸出方式為:

\q[標題,ID]

但是這裡就有個問題,我們存在memoarr中的元素皆為字串
而上面程式碼中的標題本身就只是一串字,而不是字串
只是傳入內碼的時候會作為字串傳入而已
因此要怎麼將memoarr中的字串成功在選項中被顯示呢?
這時就可以利用AYA內建函數STRFORM
該函數的功能與C語言中的sprintf相似
以下便說明如何將memoarr的每個字串化為一個一個選項輸出:

question = STRFORM("\q[○$s,OnRemoveMemo,$d]\n", i, cnt)

可以看到STRFORM的傳入值為一個有點怪怪的字串
首先,上面程式碼中的$s和$d代表這個地方要由後面提供的變數來替換
s代表string,代表替換變數型態為字串
而d代表decimal,其他應該都與C語言相同
因此上面程式碼中的$s與$d會分別被變數i與cnt代換
而question變數便會存放"\q[○(字串i),OnRemoveMemo,(整數cnt)]\n"
這樣便是一個選項的正確形式了
由於選項中的ID為On開頭的函數,後面的參數會作為reference0、reference1...等等傳入ID函數
而這裡的傳入值是cnt變數所存放的整數
而前面也提過了,傳入值會以字串傳入

現在要將memoarr的內容全部變成選項:

cnt = 0
talk = "\0\s[0]"
foreach memoarr;i
{
    if i != ""
    {
        question = STRFORM("\q[○$s,OnRemoveMemo,$d]\n", i, cnt)
        talk = talk + question
        cnt = cnt + 1
    }
}

首先看到前面兩行
cnt為計數器,記錄memoarr中每個字串的序數
而talk為最後要讓偽春菜說出的話,因此初始值為開啟對話框與設定表情
接著看到foreach迴圈,其功能跟python中的for i in list相同
這裡便是以變數i作為迭代器,將memoarr中每個元素迭代一輪
每一次迭代都檢查i是否為空字串,避免生成不該存在的選項
這個動作便是在防範前面提到SPLIT分割模式所造成的問題
再來看到STRFORM,裡面我將每個選項的序數做為reference0傳入OnRemoveMemo
用途下面會說明
每跑完一圈,cnt就加1,以得到正確的序數
最後看到OnRemoveMemo怎麼處理刪除動作

OnRemoveMemo
{
    memoarr = SPLIT(memo)
    idx = TOINT(reference0)
    cnt = 0
    memo = ""
   
    foreach memoarr;i
    {
        if (idx != cnt) && (i != "")
        {
            memo = memo + i + "\n"
        }
        cnt = cnt + 1
    }
}

這裡的操作基本與前一段程式碼相同
首先看到idx變數,由於reference0會被當作字串傳入
因此要用AYA內建函數TOINT將字串轉為整數
接著在memo被更動前再一次將其分割並存入memoarr變數中
然後將memo清空並重新將沒被刪除的內容填入
這裡重新填入同樣用到foreach迴圈
但是判斷式稍微不一樣
要兩個條件同時為真才會執行if內的動作
第一個是idx不等於cnt,這個判斷是確認當前i的序數是否等於待刪除項目的序數
第二個是i不為空字串,這個判斷的理由在前面已經提過了
在字串內部做刪除這個動作比較困難
但刪除這個動作等價於將剩下的記錄下來
因此我們便是用後者處理刪除的動作

這裡的解說只提了最核心的功能
而我另外還追加了選擇刪除項目時,最下面會出現取消選擇肢
可以用來防按錯的情況
而當memo被刪除所有項目後
會自動還原到空白的狀態
以及當memo為空白狀態時
小鳥會提醒使用者目前備忘錄是空白而不進行刪除工作

==================================================================
今天是把失望表情完成之後才開始編程工作
但並沒有將表情實裝,只有將設定檔寫好而已


一個計畫拖越久,畫風就變越多
這是一件無比哀傷的事情

2017/03/13

2017年3月6日 星期一

製作日誌--016

228連假沒了電腦,又休息一周
不過這周的進度也很少

###AI對話###

新增了兩個對話
突然想到所有很電波的事情都丟給啾啾來說就好了
這樣應該可以增加不少對話內容

###備忘錄###

稍微調整了一下備忘錄所用到的函式

=============================================
由於先寫了些作業,能畫圖的時間剩不多
就先把失望表情給描起來而已


下周應該就可以上色了

2016/03/06