/// <summary>
        /// 載入明眼字文件並轉換成點字。
        /// </summary>
        public void LoadAndConvert()
        {
            if (StrHelper.IsEmpty(m_FileName))
            {
                throw new Exception("檔案名稱尚未指定!");
            }
            if (m_Processor == null)
            {
                throw new Exception("在呼叫 BrailleDocument.Load 之前,請先指定 BrailleProcessor。");
            }

            Encoding enc = Encoding.Default;

            if (FileHelper.IsUTF8Encoded(m_FileName))
            {
                enc = Encoding.UTF8;
            }
            using (StreamReader sr = new StreamReader(m_FileName, enc, true))
            {
                try
                {
                    LoadAndConvert(sr);
                }
                finally
                {
                    sr.Close();
                }
            }
        }
示例#2
0
 /// <summary>
 /// 檢查指定的 BrailleWord 物件是否沒有包含任何有意義的資料(空方算有意義的資料)。
 /// </summary>
 /// <param name="brWord"></param>
 /// <returns></returns>
 public static bool IsEmpty(BrailleWord brWord)
 {
     if (StrHelper.IsEmpty(brWord.Text) && brWord.CellCount < 1)
     {
         // 文字為空字串,且沒有任何點字物件,即視為空的 BrailleWord 物件.
         return(true);
     }
     return(false);
 }
示例#3
0
        public void IsEmptyTest()
        {
            string input = " \t \r\n";

            bool expected = true;
            bool actual   = StrHelper.IsEmpty(input);

            Assert.AreEqual(expected, actual, "global::Huanlin.Text.StrHelper.IsEmpty did not return the expected value.");
        }
        /// <summary>
        /// 將一個中文字的注音組字字根碼轉換成點字碼串列,並加入指定的 BrailleWord 物件。
        /// 注意:若轉換成功,會同時加入注音碼和點字碼。
        /// </summary>
        /// <param name="phcode">一個中文字的注音組字字根碼</param>
        /// <param name="brWord">欲加入點字的 BrailleWord 物件</param>
        /// <returns>成功傳回 true,失敗傳回 false。</returns>
        public BrailleCellList CreatePhoneticCellList(string phcode)
        {
            if (StrHelper.IsEmpty(phcode) || phcode.Length < 4)
            {
                return(null);   // 不是中文字
            }
            // 先取出注音符號各部份。
            // TODO: 改成不用空白就能判斷結合韻,否則片語無法使用。
            string firstPhCode  = phcode.Substring(0, 1);       // 第一個注音符號
            string secondPhCode = phcode.Substring(1, 1);       // 第二個注音符號
            string thirdPhCode  = phcode.Substring(2, 1);       // 第三個注音符號
            string joinedPhCode = phcode.Substring(1, 2);       // 第二、三結合韻
            string tonePhCode   = phcode.Substring(3, 1);       // 音調

            // 取出注音符號各部份的點字碼。
            string firstBrCode  = _brailleTable.FindPhonetic(firstPhCode);
            string secondBrCode = _brailleTable.FindPhonetic(secondPhCode);
            string thirdBrCode  = _brailleTable.FindPhonetic(thirdPhCode);
            string toneBrCode   = _brailleTable.FindTone(tonePhCode);

            if (firstBrCode == null && secondBrCode == null && thirdBrCode == null)
            {
                return(null);
            }

            BrailleCellList cellList = new BrailleCellList();

            // 處理特殊的單音字。
            if (StrHelper.IsEmpty(secondPhCode) && StrHelper.IsEmpty(thirdPhCode))
            {
                string monoBrCode = _brailleTable.FindMono(firstPhCode);
                if (String.IsNullOrEmpty(monoBrCode))
                {
                    throw new Exception("無效的注音符號: " + phcode);
                }
                cellList.Add(monoBrCode);

                // 特殊單音字要附加 'ㄦ'
                string erBrCode = _brailleTable.FindPhonetic("ㄦ");
                if (String.IsNullOrEmpty(erBrCode))
                {
                    throw new Exception("點字對照表中無此符號: ㄦ");
                }
                cellList.Add(erBrCode);

                // 再加上聲調
                cellList.Add(toneBrCode);

                return(cellList);
            }

            // 處理結合韻。
            string joinedBrCode = _brailleTable.FindJoined(joinedPhCode);

            if (!String.IsNullOrEmpty(joinedBrCode)) // 是結合韻?
            {
                cellList.Add(firstBrCode);           // 加入第一個注音符號
                cellList.Add(joinedBrCode);          // 加入結合韻
                cellList.Add(toneBrCode);            // 加入聲調
                return(cellList);
            }

            // 不是特殊單音字,也不是結合韻:其他注音符號拼法。例如:"ㄋㄧ ˇ"。
            cellList.Add(firstBrCode);  // 加入第一個注音符號
            cellList.Add(secondBrCode); // 加入第二個注音符號
            cellList.Add(thirdBrCode);  // 加入第三個注音符號
            cellList.Add(toneBrCode);   // 加入聲調
            return(cellList);
        }
        /// <summary>
        /// 從堆疊中讀取字元,並轉成點字。只處理中文字和中文標點符號。
        /// </summary>
        /// <param name="charStack">字元堆疊。</param>
        /// <param name="context">情境物件。</param>
        /// <returns>傳回轉換後的點字物件串列,若串列為空串列,表示沒有成功轉換的字元。</returns>
        public override List <BrailleWord> Convert(Stack <char> charStack, ContextTagManager context)
        {
            if (charStack.Count < 1)
            {
                throw new ArgumentException("傳入空的字元堆疊!");
            }

            bool               done = false;
            char               ch;
            string             text;
            bool               isExtracted; // 目前處理的字元是否已從堆疊中移出。
            BrailleWord        brWord;
            List <BrailleWord> brWordList = null;
            int idx             = 0;
            int chineseStartIdx = -1;
            int chineseEndIdx   = -1;

            while (!done && charStack.Count > 0)
            {
                ch          = charStack.Peek(); // 只讀取但不從堆疊移走。
                isExtracted = false;

                // 小於跟大於符號是情境標籤,不處理(交由 ControlTagConverter 負責)。
                if (ch == '<' || ch == '>')
                {
                    break;
                }

                // 全形英文字母要轉成半形,並且由英文點字元件處理。
                if (CharHelper.IsFullShapeLetter(ch))
                {
                    charStack.Pop();
                    ch = CharHelper.FullShapeToAsciiLetter(ch);
                    charStack.Push(ch);
                    break;
                }

                // 全形數字要轉成半形,並且由英文點字元件處理。
                if (CharHelper.IsFullShapeDigit(ch))
                {
                    charStack.Pop();
                    ch = CharHelper.FullShapeToAsciiDigit(ch);
                    charStack.Push(ch);
                    break;
                }

                text = ch.ToString();

                // 處理雙字元的標點符號。
                if (ch == '…' || ch == '-' || ch == '─' || ch == '╴' || ch == '﹏')
                {
                    // 讀下一個字元,若是相同符號,則可略過;若不同,則下次迴圈仍需處理。
                    if (charStack.Count >= 2)
                    {
                        charStack.Pop();
                        char ch2 = charStack.Pop();
                        if (ch2 == ch)  // 如果是連續兩個刪節號或破折號。
                        {
                            text        = text + text;
                            isExtracted = true;
                        }
                        else
                        {
                            // 不是連續符號,把之前取出的字元放回堆疊。
                            charStack.Push(ch2);
                            charStack.Push(ch);
                            isExtracted = false;
                        }
                    }
                }
                else if (ch == '[')     // 處理以半形中括號包住的特殊符號.
                {
                    if (charStack.Count >= 3)
                    {
                        charStack.Pop();
                        char ch2 = charStack.Pop();
                        char ch3 = charStack.Pop();
                        if (ch3 == ']' && (ch2 == '↗' || ch2 == '↘'))
                        {
                            text        = text + ch2.ToString() + ch3.ToString();
                            isExtracted = true;
                        }
                        else
                        {
                            // 不是中括號包住的特殊符號,把之前取出的字元放回堆疊。
                            charStack.Push(ch3);
                            charStack.Push(ch2);
                            charStack.Push(ch);
                            isExtracted = false;
                        }
                    }
                }

                /* 特殊數字編號【1】已經改成直接定義在 xml 檔案 (2009-6-22).
                 *              else if (ch == '【')
                 *              {   // 特殊數字編號,用於選擇題的答案編號,例如: 【1】,見 ChineseBrailleTable.xml。
                 *                  if (charStack.Count >= 3)
                 *                  {
                 *                      charStack.Pop();
                 *                      char ch2 = charStack.Pop();
                 *                      char ch3 = charStack.Pop();
                 *                      if (Char.IsDigit(ch2) && ch3 == '】')   // 無論是半形或全形數字,Char.IsDigit 都會傳回 true。
                 *                      {
                 *                          isExtracted = true;
                 *                          if (CharHelper.IsFullShapeDigit(ch2))
                 *                          {
                 *                              ch2 = CharHelper.FullShapeToAsciiDigit(ch2);
                 *                          }
                 *                          text = ch.ToString() + ch2.ToString() + ch3.ToString();
                 *                      }
                 *                      else
                 *                      {
                 *                          charStack.Push(ch3);
                 *                          charStack.Push(ch2);
                 *                          charStack.Push(ch);
                 *                          isExtracted = false;
                 *                      }
                 *                  }
                 *              }
                 */
                brWord = InternalConvert(text);
                if (brWord == null)
                {
                    break;
                }

                if (!isExtracted)
                {
                    charStack.Pop();
                }

                if (!StrHelper.IsEmpty(text))   // 避免將空白字元也列入 Chinese。
                {
                    brWord.Language = BrailleLanguage.Chinese;
                }

                ApplyBrailleConfig(brWord); // 根據組態檔的設定調整點字轉換結果。

                if (brWordList == null)
                {
                    brWordList = new List <BrailleWord>();
                }
                brWordList.Add(brWord);

                // 記錄連續中文字元,以修正破音字的注音字根。
                if (brWord.Text.IsCJK())   // 如果是中文字元,要記錄連續的中文字元區間
                {
                    if (chineseStartIdx < 0)
                    {
                        chineseStartIdx = idx;
                        chineseEndIdx   = idx;
                    }
                    else
                    {
                        chineseEndIdx = idx;
                    }
                }
                else  // 不是中文字,則把之前紀錄的連續中文字取出,並修正其注音字根
                {
                    FixPhoneticCodes(brWordList, chineseStartIdx, chineseEndIdx);
                    chineseStartIdx = -1;
                    chineseEndIdx   = -1;
                }
                idx++;
            }

            // 處理這段中文字的最後一段連續中文字。
            if (chineseStartIdx >= 0)
            {
                FixPhoneticCodes(brWordList, chineseStartIdx, chineseEndIdx);
            }

            return(brWordList);
        }