วันอาทิตย์ที่ 24 สิงหาคม พ.ศ. 2557

Lab 1 - Star

"จะไปเป็นดาวววววโดดเด่นบนฟากฟ้าาาาา~~"

ถ้าพูดถึงดาว แต่ละคนก็มีดาวในจินตนาการตัวเองอยู่

แต่สำหรับผมแล้ว ถ้าพูดถึงดาว ผมนึกถึงสิ่งนี้

ไคบะ : เทิร์นของข้า ขอสังเวยมอนสเตอร์ 3 ตัว เพื่อเรียก Blue Eye White Dragon !!
ยูกิ : หึ เจ้าจบสิ้นแล้ว ขอเปิดการ์ดกับดัก "คำสาปดาวหกแฉก" !!
ไคบะ : ม่ายยยยยยยยยยยยยยยยยยยยย~~~

ใช่แล้วครับ มันคือ การ์ดกับดัก "คำสาปดาวหกแฉก" จากการ์ตูนเรื่อง YU-GI-OH แม้เรื่องนี้มันจะเป็นการ์ตูนที่เก่าแล้ว แต่การ์ดใบนี้ ผมยังจำมันได้เสมอ

ว่าแล้ว ผมก็ใช้ Processing วาดรูปเลียนแบบการ์ดใบนี้เอาซะเลย


ส่วนนี่ก็คือ code ของผม

 void setup()
{
  // initialization
  size(300,300);
  background(0);
  strokeWeight(4);
  stroke(255,255,0);
  translate(width/2,height/2);
  // variable
  int CenterStarX,CenterStarY;
  int WidthStar,HeightStar;
  int d;

  int SpaceBetweenCircle;
  float RVertical,RSqrt,RCircle;
  // assign variable
  CenterStarX = 0;
  CenterStarY = 0;
  WidthStar = 160;
  HeightStar = 184;
  d = 100; //space between base of both triangle
  SpaceBetweenCircle = 40; //space between inside and outside circle
  RVertical = HeightStar/2; //radius from center of star to top vertex of star
  RSqrt = sqrt((pow((d/2),2))+(pow((WidthStar/2),2))); //radius from center of star to side vertex of star
  if(RVertical > RSqrt)
  {
    RCircle = RVertical;
  }
  else
  {
    RCircle = RSqrt;
  }
  // draw outside circle
  fill(0,120,0);
  ellipse(CenterStarX,CenterStarY,(RCircle*2)+(SpaceBetweenCircle*2),(RCircle*2)+(SpaceBetweenCircle*2));
  // draw inside circle
  fill(0,0,100);
  ellipse(CenterStarX,CenterStarY,(RCircle*2),(RCircle*2));
  // draw top vertex triangle
  noFill();
  triangle(CenterStarX,CenterStarY-(HeightStar/2)+3,CenterStarX-(WidthStar/2)+3,CenterStarY+(d/2),CenterStarX+(WidthStar/2)-3,CenterStarY+(d/2));
  // draw bottom vertex triangle
  noFill();
  triangle(CenterStarX,CenterStarY+(HeightStar/2)-3,CenterStarX-(WidthStar/2)+3,CenterStarY-(d/2),CenterStarX+(WidthStar/2)-3,CenterStarY-(d/2));
}


ขอบ่นแปปนึง

อย่างแรกเลย ผมเกลียดระบบพิกัดแกน X,Y ของ Processing มากเลย
ทำไมรึ ? ก็เพราะว่ามันไม่เหมือนกับระบบพิกัดฉากในวิชาคณิตศาสตร์ไงล่ะครับ
จุด (0,0) ไปอยู่มุมซ้ายบนของ background ผมเลยใช้คำสั่ง translation(width/2,height/2) เพื่อให้จุด (0,0) อยู่ตรงกลาง
และก็อีกอย่างที่ทำให้ผมเกลียดมัน คือ แกน Y เมื่อเลื่อนขึ้นด้านบน แทนที่จะเป็นค่า +Y ดันเป็น -Y ซะอย่างงั้น


ช่างมันเถอะ !! เรามาต่อกันดีกว่า

รูปดาวรูปนี้ เพิ่มใช้เป็นสามเหลี่ยม 2 รูปกลับหัวแล้วมาซ้อนกัน อีกทั้งยังใส่วงกลม 2 วงซ้อนกัน จนกลายเป็นดาวอย่างที่เห็น

ต่อมา จาก code ด้านบน เราสามารถแก้อะไรได้บ้าง




CenterStarX : พิกัด X ของจุดศูนย์กลางของดาว
CenterStarY : พิกัด Y ของจุดศูนย์กลางของดาว
HeightStar : ความสูงของดาว
WidthStar : ความกว้างของดาว
d : ระยะห่างระหว่างฐานของสามเหลี่ยม






แล้วจากการที่เราสามารถปรับขนาดของดาวได้ ทำให้บางครั้งยอดแหลมของดาวอาจจะทะลุออกนอกวงกลมไป ทำให้ผมต้องทำการปรับขนาดของวงกลมให้พอดีกับยอดของดาว แต่ถ้าให้ผมมานั่งปรับเองทุกครั้งที่ปรับขนาดของดาว ก็คงจะเหนื่อย ผมก็เลยต้องเขียนโปรแกรมให้วงกลมปรับขนาดเอง

อย่างแรก เราต้องหารัศมีของวงกลมก่อน โดยรัศมีของวงกลม คือ ตั้งแต่จุดศูนย์กลางของดาว จนถึงยอดแหลมของดาว แต่ทว่า มันมีตั้งหลายยอดแหลม แล้วจะใช้รัศมีของยอดแหลมไหนล่ะ

งั้นเอาอย่างงี้ละกัน ผมดูคร่าวๆแล้ว มันมีรัศมีอยู่ 2 ค่า คือ รัศมีจากจุดศูนย์กลางไปยอดแนวตั้ง กับ รัศมีจากจุดศูนย์กลางไปยอดด้านข้าง




จากรูป RVertical = HeightStar/2
ส่วน RSqrt หาโดยทฤษฏีบทที่แสนยาก (หรอ)
ด้วยทฤษฏีบทของพีทาโกรัส
RSqrt^2 = (d/2)^2 + (WidthStar/2)^2
เพระาฉะนั้น
RSqrt = sqrt((d/2)^2 + (WidthStar/2)^2)




แล้วทีนี้ เราจะใช้รัศมีค่าไหนในการสร้างวงกลมล่ะ ?
สิ่งที่ผมต้องการ ก็แค่ต้องการไม่ให้ยอดแหลมใดๆเกินออกมานอกวงกลม ดังนั้น ผมจึงเลือกใช้รัศมีที่มีค่ามากที่สุดมาเป็นรัศมีของวงกลม ด้วย code นี้

if(RVertical > RSqrt)
  {
    RCircle = RVertical;
  }
  else
  {
    RCircle = RSqrt;
  }


ทีนี้ ผมก็จะได้ค่า RCircle มาเป็นรัศมีของวงกลมวงในแล้ว เย้ๆ

ส่วนวงกลมวงนอก ผมก็สร้างตัวแปรชื่อ SpaceBetweenCircle เพื่อเก็บค่าระยะห่างระหว่างวงกลมวงนอกและวงกลมวงใน
เวลาผมสร้างวงกลมวงนอก ผมก็นำ RCircle มาบวกกับ SpaceBetweenCircle แค่นี้ผมก็ได้วงกลมวงนอกแล้ว

แต่สุดท้าย เวลาสร้างรูป ผมต้องสร้างวงกลมวงนอกก่อน ตามด้วยวงกลมวงใน และปิดท้ายด้วยสร้างดาว เป็นอันเสร็จสมบูรณ์ เย้