網誌

【3D建模-DSM教學】Android機器人

【3D建模-DSM教學】Android機器人

【3D建模-DSM教學】Android機器人

先找並下載一張平面的Android機器圖案,用來進行機器人的輪廓繪製參考。

androidman

把圖案拖拉至DSM的設計上

dsmtutorialandroidman-step1

我們要用軸拉動的方式,拉出一個半球形,如下二圖所示,將Android機器人頭部以剖半的方式將臉的輪廓線條繪出來(使用直線工具與曲線工具)。

dsmtutorialandroidman-step2

dsmtutorialandroidman-step3

 

當畫出一個扇形的封閉曲線後,我們可以使用拉動的功能來做出立體的模型,拉動的基本是從面進行拉動,不過此時,我們用拉動的繞軸方式,拉出一個半圓的模型來。

做法:先用拉動功能點選扇形的面(變色),然後再如圖選取繞軸方塊,再選要拉動的扇形邊,此時邊會出現旋轉箭頭,用滑鼠動拉動…。

dsmtutorialandroidman-step4

dsmtutorialandroidman-step5

 

dsmtutorialandroidman-step6

 

dsmtutorialandroidman-step7

dsmtutorialandroidman-step8

dsmtutorialandroidman-step9

dsmtutorialandroidman-step10

dsmtutorialandroidman-step11

Android身體部份,以及手及腳部份也是如此處理。

手和腳先做一邊,另一邊可用移動複製的方式進行複製,做法是選取要移動複製的物件,然後按住”ctrl”鍵進行物件的拖拉…。

接下來,我們要繪製Android機器人眼睛。

dsmtutorialandroidman-step12

dsmtutorialandroidman-step13

dsmtutorialandroidman-step14

 

dsmtutorialandroidman-step15

這個有點難度,因為我們無法在一個球面/曲面上繪製基本圖案,我們要用投影實體的方式,在一個平面上繪出二個眼睛表面,再把這二個眼睛表面投影到Android機器人頭部。

我們先把Andorid機器人平面圖叫出來,然後依照圖上的眼睛繪製出二個眼睛表面。

再把二個眼睛表面拉出來,位置在Android機器人頭部的前方。

注意,由於眼睛拉出來投射,因為角度投射會造成投射到頭部的眼睛會斜斜的…,投射出來的眼睛會讓Android機器人看起來變邪惡。

我們要修正一下,重點:

1.拉出來的眼睛要離頭部模型越近越好

2.再分別調整左右眼表面的角度,使其貼合頭部曲線

dsmtutorialandroidman-step16

dsmtutorialandroidman-step18

dsmtutorialandroidman-step19

dsmtutorialandroidman-step20

dsmtutorialandroidman-step21

dsmtutorialandroidman-step22

dsmtutorialandroidman-step23

完成眼睛的繪製!

接下來是機器人的天線繪製。(留點功課給大家,賸下的天線自己想怎麼畫了…)

dsmtutorialandroidman-step24

 

【繪製教學錄影】

【3D建模-DSM教學】繞軸拉動與相關應用

【3D建模-DSM教學】繞軸拉動與相關應用

【3D建模-DSM教學】繞軸拉動與相關應用

基本操作

我們用描圖的方式描繪出所要的蘋果輪廓線,使用google找一張適合的apple圖片。

dsm-revolve-slide-1

複製圖片!

dsm-revolve-slide-2

將圖片貼至DSM草圖中。

dsm-revolve-slide-3

使用雲形曲線繪製出蘋果的半邊輪廓線(不要整顆蘋果的輪廓線)

dsm-revolve-slide-4

 

繪製好的輪廓線:

dsm-revolve-slide-5

 

進入3D模式,選取拉動功能:

dsm-revolve-slide-6

選取「繞軸」功能

dsm-revolve-slide-7

 

選取要旋轉的軸心線,出現繞軸的圖形提示:

dsm-revolve-slide-8

 

使用滑鼠以繞圓的方式來拖拉繞軸的圖示,此時可看見平面已經開始繞圓的方式成形:

dsm-revolve-slide-9

 

最後形成一顆漂亮的蘋果!

dsm-revolve-slide-10

教學錄影第一段-繪製圖形輪廓

教學錄影第2段-使用繞軸來成形蘋果

蛋形體

心形體

【3D建模-DSM教學】神奇寶貝球的繪製

【3D建模-DSM教學】神奇寶貝球的繪製

【3D建模-DSM教學】神奇寶貝球的繪製

 

用球體畫出一個100mm的球體

建出2個平面,將球體切分為2個半球

將2個半球挖空心,作法:使用球體從軸心(三個軸都需變色),並且以減去的方式拉出95mm的球體。

再用上面類似的步驟,但以未合併的方式拉出95mm的內核

切到顯示,設定三個部份的顏色,內核為黑色,上半球體為紅色,下半球體為白色。

以軸心為平面,畫出一個圓形,切到3D模式,將圓平面以減去的方式從球心拉出。

製作可開闔的神奇寶貝球

檔案下載:http://www.thingiverse.com/thing:411193 pokemon-stls-thingiverse 製作教學1: 製作教學2: 延伸閱讀: 大師球 http://www.thingiverse.com/thing:462723 master-pokemon-ball

【程式設計-C#】魔方陣

【程式設計-C#】魔方陣

【程式設計-C#】魔方陣

魔方陣的解法/演算法:

設有奇數方陣,3×3, 5×5…, nxn

要將1~nxn的數值填入此方陣中,使得此方陣的各列、各行、斜行/列上的數值加總為相等。

Step 1: 將1置放於方陣的第1列中間位置

設N= 2  … nxn

Step 2: 往左上角找候選的位置來放入N,此時左上角的位置,會有底下2種狀況

狀況1: 左上角的位置跑出陣列外,此時,我們將左上角位置另一端位置做為新候選位置。

狀況2:若候選位置上已經被佔據了(已有數值),此時,我們將原本數值位置的下方位置,做為新候選位置。

Step 3: 將數值N放入候選位置/新候選位置 (找到的可放置數值位置)。

Step 4:N加1,重覆Step 2與Step 4,直到N等於nxn。


if & 取餘數循環版

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace WindowsFormsApplication2
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void makeMagicMatrix1(int matrixSize)
        {
            int[,] Matrix = new int[99, 99];
            int row = 0;
            int col = matrixSize / 2;
            Matrix[row, col] = 1;

            for (int stepper = 2; stepper <= matrixSize * matrixSize; stepper++)
            {
                row--;col--; //往左上角移動,二維陣列行與列索引皆減1
                //判斷是否出界,小於0為出界的條件
                if (row < 0) row = matrixSize - 1;
                if (col < 0) col = matrixSize - 1;

                if (Matrix[row, col] != 0) //判斷要放置的位處若不是空的話,需要進行倒退的的動作
                {
                    row = (row + 2);
                    col = (col + 1);
                    //倒退後,也有可能出界,大於matrixSize-1為出界的條件
                    if (row >= matrixSize) row = row - matrixSize;
                    if (col >= matrixSize) col = col - matrixSize;
                }
                Matrix[row, col] = stepper;
            }

            string outStrng = "";

            for (int i = 0; i < matrixSize; i++)
            {
                for (int j = 0; j < matrixSize; j++)
                {
                    outStrng += Matrix[i, j].ToString().PadLeft(2, ' ') + "   ";

                }
                outStrng += "\r\n";
            }
            label2.Text = outStrng;
            label2.Location = new Point((this.panel2.Width - label2.Width) / 2, 0); //置中label2

        }


        private void makeMagicMatrix2(int matrixSize)
        {
            int[,] Matrix = new int[99, 99];
            int row = 0;
            int col = matrixSize / 2;
            Matrix[row, col] = 1;

            for (int stepper = 2; stepper <= matrixSize * matrixSize; stepper++)
            {
                row = (row - 1 + matrixSize) % matrixSize;
                col = (col - 1 + matrixSize) % matrixSize;
                if (Matrix[row, col] != 0)
                {
                    row = (row + 2) % matrixSize;
                    col = (col + 1) % matrixSize;
                }
                Matrix[row, col] = stepper;
            }

            string outStrng = "";

            for (int i = 0; i < matrixSize; i++)
            {
                for (int j = 0; j < matrixSize; j++)
                {
                    outStrng += Matrix[i, j].ToString().PadLeft(2, ' ') + "   ";

                }
                outStrng += "\r\n";
            }
            label2.Text = outStrng;
            label2.Location = new Point((this.panel2.Width - label2.Width) / 2, 0); //置中label2

        }

        private void button1_Click(object sender, EventArgs e)
        {
            int matrixSize = Convert.ToInt32(textBox1.Text);
            makeMagicMatrix1(matrixSize);
        }
    }
}

 

magicmatrixflow

2018/10/24 程式碼

const int n = 5;
int[,] M = new int[n, n];
int row = 0, col = n / 2;
M[row, col] = 1; //將1放入第1列中間位置           
for (int N = 2; N <= n * n; N++)
{
    //狀況1
    row = (row - 1 + n) % n; col = (col - 1 + n) % n;
    //狀況2
    if (M[row, col] != 0) //要放的位置上已經有數值
    {
        row = (row + 2) % n; col = (col + 1) % n;
    }
    M[row, col] = N; //將N放入決定好的位置
}
//輸出魔方陣
for (int r = 0; r < n; r++)
{
    for (int c = 0; c < n; c++)
    {
        Console.Write("{0, 4}", M[r, c]);
    }
    Console.WriteLine();
}
公告:全國銀髮長照4.0設計競賽 – 弘光科技大學 資訊管理系

公告:全國銀髮長照4.0設計競賽 – 弘光科技大學 資訊管理系

公告:全國銀髮長照4.0設計競賽 – 弘光科技大學 資訊管理系

全國銀髮長照4.0設計競賽

一、競賽宗旨:

本競賽結合銀髮族食衣住行育樂等各種需求與工業4.0創新精神為主軸,鼓勵青年學子進行創新與開發,藉此培育國家未來產業之人才為宗旨。

二、主辦單位:

弘光科技大學 文化創意產業系、資訊管理系(依筆劃順)

三、承辦單位:弘光科技大學資訊管理系,由涂聖忠老師擔任總召集人。

四、協辦單位:TTPA 臺灣遠距藥事照護協會

五、参加資格:全國高中職、大專院校學生(含研究所)及教師。

六、競賽方式:個人或團體,依競賽規定完成①線上報名、②上傳或繳交實體作品。

七、報名方式:

(一)線上報名:

https://goo.gl/forms/dN4yfIl5f1m2p3hv2

(二)上傳作品:

https://script.google.com/macros/s/AKfycbynBZVDqgcdjf01_gq7OyF2CuLQ3MITe-r5QJxD7xvPmNmRB1k/exec

(三)實體作品:請寄至433臺中市台灣大道六段1018號 弘光科大資管系林佳真。

(四)實體作品請於得獎公布後兩週內自行取回,或附足回送掛號郵票,逾期將銷毀處理。

八、活動官網:http://pweb.hk.edu.tw/~tsj/40/40.pdf,或本校文創、資管系網頁。

九、報名期間:105.11.1(二)~105.12.9(五)截止。

十、得獎公告:105.12.23(五),公告於官網及 弘光科大文創系、資管系網頁。

十一、競賽類別及獎項:

(一)類別:分高中職、大專院校、教師三組競賽,每獎項再分企劃設計程式設計實體作品等三類。

(二)獎項

1.醫護項:各類別取前三名,及佳作若干名,頒發獎狀。

2.居家項:各類別取前三名,及佳作若干名,頒發獎狀。

3.娛樂項:各類別取前三名,及佳作若干名,頒發獎狀。

4.教育項:各類別取前三名,及佳作若干名,頒發獎狀。

5.動畫項:各類別取前三名,及佳作若干名,頒發獎狀。

6.美術項:各類別取前三名,及佳作若干名,頒發獎狀。

7.工藝項:各類別取前三名,及佳作若干名,頒發獎狀。

8.其他項:各類別取前三名,及佳作若干名,頒發獎狀。

十二、競賽諮詢:(04)26318652#5415 涂老師 (tsj@sunrise.hk.edu.tw)

十三、其他說明:

1.主辦單位保留內容變更之權利。

2.參賽者須尊重他人智財權,若有違反則取消參賽資格。

3.協辦單位得以給予額外之獎項,但不列入本次競賽之正式獎項。

弘光科技大學 資訊管理系

來源: 公告:全國銀髮長照4.0設計競賽 – 弘光科技大學 資訊管理系

【資料結構】堆疊

【資料結構】堆疊

【資料結構】堆疊

 

堆疊(Stack)是一種後進先出(Last In First Out, LIFO)的有序串列,亦即資料處理的方式都是在同一邊進行,也就是由相同的一端來進行插入與刪除動作。而我們日常生活中,也有一些是堆疊的例子,例如堆盤子、書本裝箱…等,都是一層一層的堆上去,如果想要取出箱子中某一本書,也只能從最上面開始取出。

 

定義

1.一群相同性質元素的組合,即有序串列(ordered List) 。

2.具有後進先出 (Last In First Out, LIFO) 的特性。

3.將一個項目放入堆疊的頂端,這個動作稱為Push(加入)。

4.從堆疊頂端拿走一個項目,這個動作稱為Pop(取出)。

5.Push/Pop的動作皆發生在同一端,則稱此端為Top(頂端)。

6.要取出資料時,則只能從Top(頂端)取出,不能從中間取出資料。

 

 

【堆疊的操作示範】

 

堆疊常用的操作

  1.  Push  :加入新項目到堆疊的頂端。
  2. Pop  :取出堆疊頂端一個項目。
  3. TopItem  :查看堆疊頂端的項目內容。
  4. IsEmpty  :判斷堆疊是否為空,若為空則傳回真(True),否則傳回假(False)。
  5. IsFull  :判斷堆疊是否為滿,若為滿則傳回真(True),否則傳回假(False)。

【C#-Stack類別】

Stack.Push 方法 (Object)

using System;
using System.Collections; //C#的Stack所在的命名空間
public class SamplesStack
{

    public static void Main()
    {

        // Creates and initializes a new Stack. 建立並初始化一個新的堆疊
        Stack myStack = new Stack();
        myStack.Push("The");
        myStack.Push("quick");
        myStack.Push("brown");
        myStack.Push("fox");

        // Displays the Stack. //印出堆疊內容
        Console.Write("堆疊元素::");
        PrintValues(myStack, '\t'); //呼叫下方PrintValues方法

        // Removes an element from the Stack. 從堆疊裏移除一個元素
        Console.WriteLine("(Pop)\t\t{0}", myStack.Pop());

        // Displays the Stack. 印出堆疊內容
        Console.Write("堆疊元素::");
        PrintValues(myStack, '\t');

        // Removes another element from the Stack. 從堆疊裏移除另一個元素
        Console.WriteLine("(Pop)\t\t{0}", myStack.Pop());

        // Displays the Stack. 印出堆疊內容
        Console.Write("堆疊元素::");
        PrintValues(myStack, '\t');

        // Views the first element in the Stack but does not remove it.
        //檢視堆疊裏的第一個元素,但不移除該元素,注意動作與pop不同
        Console.WriteLine("(Peek)\t\t{0}", myStack.Peek());

        // Displays the Stack.
        Console.Write("堆疊元素::");
        PrintValues(myStack, '\t');
    }


    public static void PrintValues(IEnumerable myCollection, char mySeparator)
    {
        foreach (Object obj in myCollection) //對每一個在myCollection集合裏的物件obj
            Console.Write("{0}{1}", mySeparator, obj);
        Console.WriteLine();
    }

}


/* 
程式輸出:
堆疊元素::     fox     brown   quick   The
(Pop)           fox
堆疊元素::     brown   quick   The
(Pop)           brown
堆疊元素::     quick   The
(Peek)          quick
堆疊元素::     quick   The
請按任意鍵繼續 . . .
*/

 

【堆疊在運算式上的應用】

在日常生活中,我們所使用的四則運算都屬於中序(infix order)運算式,亦即運算子位於兩個運算元之間的表示法。但是,此種表示法電腦並無法直接的處理,因為中序式可能會含有括號,並且運算子可能有不同的優先順序權。因此,若要使用電腦來處理運算式時,則必須要先將「中序式」轉換成「後序式」(postfix order)。

算術式表示的方式有三種:

  1. 中序(Infix)表示法: A+B
  2. 前序(prefix)表示法: +AB
  3. 後序(postfix)表示法: AB-

【中序(Infix)表示法】

【定義】數學上的表示方式,就是屬於中序式,它是把運算子放在兩個運算元的中間。

【表示式】<運算元1 > <運算子> <運算元2 >

【例如】A+B。

【缺點】電腦無法一次依序讀取運算式,因運算式可能含有括號,且未定義運算子優先順序。

 

【前序 (prefix)表示法】

【定義】指將中序表示法中的運算子和運算元重新調整順序,只是運算子的順序是在運算元前面。

【表示式】<運算子> <運算元1 > <運算元2 >

【例如】+AB。

 

【後序 (postfix)表示法】

【定義】後序表示法和前序表示法相類似,使得運算子放於運算元後面的表示法。

【表示式】<運算元1 > <運算元2 > <運算子>

【例如】AB+。

【優點】 不必使用括號,方便電腦使用。

 

【運算式的轉換】

大部份的運算式(expression)都是由運算元(operand)與運算子(operator)所組成。

【例如】A*B+(C/D)-E   其中: A,B,C,D,E為運算元(operand),  +,-,*,/為運算子(operator)

【運算原則】

  • Œ括號內先處理
  • 優先權較高的運算子先執行
  • Ž同優先權者,則由結合性,來決定是由左而右,還是由右而左執行。

 

【中序式→前序式】

假設有一個中序式為:A×B+C×D,欲轉換成前序式,其步驟如下:

1.先用括號將優先順序分出來

((A×B)+(C×D))

2.將運算子移到左括號右邊

Œ((×AB)+(×CD))

(+(×AB)(×CD))

3.把括弧全部拿掉,即為所得。

+×AB×CD

 

【中序式→後序式】

假設有一個中序式為:A×B+C×D,欲轉換成後序式,其步驟如下:

1.先用括號將優先順序分出來

((A×B)+(C×D))

2.將運算子移到右括號左邊

Œ((AB×)+(CD×))

((AB×)(CD×)+)

3.把括弧全部拿掉,即為所得。

AB×CD×+

練習:

1.  A+B*C-D/E

Ans:  依優先順序括上括弧

(A+(B*C))-(D/E))

後序式係將運算子移到右括號左邊

(A(BC*)+)(DE/)-)

去掉括弧:

ABC*+DE/-

 

2. (A+B)*C/(D-E/F)

Ans:  依優先順序括上括弧

(((A+B)*C)/(D-(E/F)))

後序式係將運算子移到右括號左邊

(((AB+)C*)(D(EF/)-)/)

去掉括弧:

AB+C*DEF/-/

後序式求解:

設A=1, B=2, C=3, D=4, E=5, F=2,求下面後序式的值為何?

1.AB*C-DE**

=(((AB*)C-)(DE*)*)

=(((A*B)-C)*(D*E))

=(((1*2)-3)*(4*5))

=-20

2.ABC*+DE/-

=((A(BC*)+)(DE/)-)

=((A+(B*C))-(D/E))

=((1+(2*3))-(4/5))

=1+6-0.8

=6.2

3.AB+C*DEF/-/

=(((AB+)C*)(D(EF/)-)/)

=(((A+B)*C)/(D-(E/F)))

=(((1+2)*3)/(4-(5/2)))

=3*3/(4-2.5)

=9/1.5

=6

以上方法是我們人員用來進行的中序轉後序/前序的快速方法,應付考試相當快捷,但是,若要用程式來實現轉換方法,需要特定的資料結構來協助,一般來說有二種作法:堆疊與二元樹。

考試時,一般不會考程式,所以不用特別注意堆疊的演算法,大家要記得的是去括弧法與二元樹法。(考試必考!)

 

【C# – 中序到後序的轉換程式】

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
 
namespace Infix
{
   class Program
   {
 
      static bool InfixToPostfixConvert(ref string infixBuffer, out string postfixBuffer)
      {
         int priority = 0;
         postfixBuffer = "";
 
         Stack<Char> s1 = new Stack<char>();
 
         for (int i = 0; i < infixBuffer.Length; i++)
         {
            char ch = infixBuffer[i];
            if (ch == '+' || ch == '-' || ch == '*' || ch == '/')
            {
               // check the precedence
               if (s1.Count <= 0)
                  s1.Push(ch);
               else
               {
                  if (s1.Peek() == '*' || s1.Peek() == '/')
                     priority = 1;
                  else
                     priority = 0;
                  if (priority == 1)
                  {
                     if (ch == '+' || ch == '-')
                     {
                        postfixBuffer += s1.Pop();
                        i--;
                     }
                     else
                     { // Same
                        postfixBuffer += s1.Pop();
                        i--;
                     }
                  }
                  else
                  {
                     if (ch == '+' || ch == '-')
                     {
                        postfixBuffer += s1.Pop();
                        s1.Push(ch);
                     }
                     else
                        s1.Push(ch);
                  }
               }
            }
            else
            {
               postfixBuffer += ch;
            }
         }
         int len = s1.Count;
         for (int j = 0; j < len; j++)
            postfixBuffer += s1.Pop();
         return true;
      }
 
      static void Main(string[] args)
      {
         string infixBuffer = "";
         string postfixBuffer = "";
 
         if (args.Length == 1)
         {
            infixBuffer = args[0];
           
            InfixToPostfixConvert(ref infixBuffer, out postfixBuffer);
            System.Console.WriteLine("InFix  :\t" + infixBuffer);
            System.Console.WriteLine("PostFix:\t" + postfixBuffer);
         }
         else
         {
            infixBuffer = "a+b*c";
 
            InfixToPostfixConvert(ref infixBuffer, out postfixBuffer);
            System.Console.WriteLine("InFix  :\t" + infixBuffer);
            System.Console.WriteLine("PostFix:\t" + postfixBuffer);
            System.Console.WriteLine();
           
            infixBuffer = "a+b*c/d-e";
            InfixToPostfixConvert(ref infixBuffer, out postfixBuffer);
            System.Console.WriteLine("InFix  :\t" + infixBuffer);
            System.Console.WriteLine("PostFix:\t" + postfixBuffer);
            System.Console.WriteLine();
           
            infixBuffer = "a+b*c/d-e+f*h/i+j-k";
            InfixToPostfixConvert(ref infixBuffer, out postfixBuffer);
            System.Console.WriteLine("InFix  :\t" + infixBuffer);
            System.Console.WriteLine("PostFix:\t" + postfixBuffer);
            System.Console.WriteLine();
         }        
      }
   }
}

/* 程式輸出
中序  : a+b*c
後序:   abc*+

中序  : a+b*c/d-e
後序:   abc*d/+e-

中序  : a+b*c/d-e+f*h/i+j-k
後序:   abc*d/+e-fh*i/+j+k-

請按任意鍵繼續 . . .

*/