Wednesday, August 30, 2006

ทดลองใช้ user32.dll เพื่อเรียกขนาด Resolution

จากการอ่านบทความเมื่อวานเกี่ยวกับการใช้งาน Win32API บน C# ผมก็ได้ทดลองนำไป
ใช้งานกับการเขียนโปรแกรมใช้งาน Win32API ซึ่ง API ตัวที่ผมเรียกใช้คือ user32.dll

สำหรับ Function ที่ผมเลือกที่จะใช้คือ SystemParameterInfo ซึ่งผมจะใช้ ฟังก์ชัน
นี้ในการเรียกค่า Resolution ของจอภาพมาดูครับว่าปัจจุบัน Desktop ของเราใช้
Resolution ของจอภาพไว้ที่เท่าไร

ด้านล่างจะเป็นการประกาศใน Visual Basic นะครับ ( จาก APIViewer )
Public Declare Function SystemParametersInfo Lib "user32" Alias "SystemParametersInfoA" (ByVal uAction As Long, ByVal uParam As Long, ByRef lpvParam As Any, ByVal fuWinIni As Long) As Long

สำหรับ Sourcecode ของโปรแกรมนะครับผมแปลงมาใส่ C# จากด้านบนเป็นดังนี้ครับ

แน่นอนครับลืมไม่ได้ถ้าจะใช้ WIN32API ต้องอ้างถึงตัวนี้
using System.Runtime.InteropServices;

จากนั้น
[DllImport("user32.dll",EntryPoint="SystemParametersInfo")]
private static extern int SystemParametersInfo(int uiAction,int uiParam,out rc pvParam,int fWinlni);

สำหรับตัวโปรแกรมผมออกแบบโดยมีฟอร์ม 1 ฟอร์มมี Label ไว้แสดง Resolution
และมีปุ่มกด เพื่อใช้เรียกฟังก์ชันให้ดึงค่า Resolution มาแสดงบน Label ที่กำหนด
ตัวอย่างโค๊ตที่จะทำงานเมื่อมีการกดปุ่มนะครับ

private void button1_Click(object sender, EventArgs e)
{
rc Rect;
int lngResult;
lngResult = SystemParametersInfo(48, 0,out Rect,0);

label1.Text = "";
label1.Text = "("+Rect.Left+")("+Rect.Top+"),("+Rect.Rigth+")("+Rect.Bottom+")";
}


** ข้อสังเกตุ **
จากการประกาศ rc Rect;
ตัวแปร rc ในที่นี้คือ Struct ซึ่งแปลงมาจาก Type ของ Visual Basic ใน APIViewer

CODE ประกาศ Struct ของ C#

struct rc
{
public int Left;
public int Top;
public int Rigth;
public int Bottom;
}

ตัวอย่างการเรียกใช้จาก Visual Basic

เริ่มแรกต้องประกาศใช้ก่อนดังนี้
Declare Function SystemParametersInfo Lib "user32.dll" _
Alias "SystemParametersInfoA"(ByVal uiAction As Long, _
ByVal uiParam As Long,pvParam as Any,ByVal fWinlni As Long) As Long

สำหรับ CODE ในปุ่มก็มีดังนี้ครับ

Private Sub Command1_Click()
Dim udiWorkArea As RECT
Dim lngResult As Long

lngResult = SystemParametersInfo(SPI_GETWORKAREA,0,udiWorkArea,0)

With udiWorkArea
Label1.Caption = "(" & .Right &","& .Bottom &")"
End With

End Sub


** หมายเหตุ 1 **
เมื่อเราเปิดจาก APIViewer ในส่วนของ Constant จะพบว่าตัวแปร RECT มีประเภทเป็น Type
ใน Visual Basic ซึ่งจะเท่ากับ Stuct เราจึงทำการประกาศ Struct ใน CODE C#

** หมายเหตุ 2 **
ในส่วนนี้ของ Visual Basic ( บรรทัดล่าง )
lngResult = SystemParametersInfo(SPI_GETWORKAREA,0,udiWorkArea,0)

จะเห็นว่าต่างจากของ C# คือ
lngResult = SystemParametersInfo(48, 0,out Rect,0);

เนื่องมาจาก SPI_GETWORKAREA ใน Visual Basic ตามเอกสารของ WIN32API ระบุว่า
เป็นตัวแปรแบบค่าคงที่ เท่ากับ 48

และที่ส่วนของ Parameter ที่ส่งมีคำว่า out Rect เนื่องจากในการประกาศใช้ Function
มีการกำหนดให้เป็น out rc เอาไว้ ดัง Code ด้านล่าง
[DllImport("user32.dll",EntryPoint="SystemParametersInfo")]
private static extern int SystemParametersInfo(int uiAction,int uiParam,out rc pvParam,int fWinlni);

จะเห็นว่าในส่วนที่ APIViewer แจ้งว่า Function มี Argument แบบ ByVal หรือ ByRef
เวลาเรานำมาประกาศใน C# เราต้องมี out นำหน้า datatype ตามด้วย ชื่อตัวแปร

** หมายเหตุ 3 **
จะสังเกตุว่า เราใช้ int ในตัวแปรของ C# แทนที่จะประกาศเป็น long เช่นเดียวกับ Visual Basic
นั้นก็เพราะขนาดของข้อมูลของ Visual Basic และ C# ไม่เท่ากัน

จบข่าวครับ . . .

Tuesday, August 29, 2006

การใช้ WIN32API ใน C#

[CODE]

using System;
using System.Runtime.InteropServices;

class win32intro
{
struct SYSTEMTIME {
public short wYear;
public short wMonth;
public short wDayOfWeek;
public short wDay;
public short wHour;
public short wMinute;
public short wSecond;
public short wMilliseconds;
}

[DllImport("kernel32.dll",EntryPoint="GetLocalTime")]
private static extern void GetLocalTime(out SYSTEMTIME lpSystemTime);



static void Main(string[] args)
{
SYSTEMTIME tm;
GetLocalTime(out tm);
Console.WriteLine("{0:0000}/{1:00}/{2:00} {3:00}:{4:00}:{5:00}:{6:0000}",
tm.wYear, tm.wMonth, tm.wDay, tm.wHour, tm.wMinute, tm.wSecond, tm.wMilliseconds);
}
}

[/CODE]


หมายเหตุ
ให้ระวังในการประกาศตัวแปร . . เพราะ WIN32API นั้นจะเทียบกับ Visual Basic
แต่ใน C# ขนาดของตัวแปรไม่เท่ากัน . .

integer ของ Visual Basic มีขนาด 16 bit
integer ของ C# มีขนาด 32 bit

Type ของ Visual Basic คือ Struct ของ C#

ส่วนรายละเอียดอื่นๆ ดูจาก Sourcecode หรืออ่านได้จาก

Reference
Twoguru.com

Monday, August 28, 2006

เริ่มต้นกับ AJAX จาก W3Schools

ผมคิดอยู่มานานว่าเทคโนโลยีอย่าง AJAX นั้นมันนำไปใช้จริงได้มีประโยชน์ไหมนะ
ความจริงแล้วมันมีอยู่หลายความคิดเห็นเกี่ยวกับเทคโนโลยี AJAX เนื่องจากบางความ
เห็นผู้เชียวชาญหลายท่านก็บอกว่า มันทำลายคุณสมบัติของ Browser

คุณสมบัติของ Browser ที่จะเสียไปหากใช้ AJAX
- ไม่สามารถเซฟหน้าเว็บเก็บได้
- ไม่สามารถทำ Favorite เวบหน้าที่ต้องการได้

แต่ว่ากับบางกรณีนั้นผมก็คิดว่ามันเข้าท่าดีนะ เช่นหน่วยงานที่มีการใช้งาน Intranet
ภายในองค์กร ( เช่นหน่วยงานของผม ) เพราะว่า Intranet มันเร็ว เพราะฉะนั้น
เรื่องเกี่ยวกับ Connection Speed ของ Internet จึงไม่ใช่ปัญหา

มาเริ่มกันเลยดีกว่าครับ ^^

#########################################################

AJAX

AJAX ย่อมาจาก Asynchonous Java and XML เป็นเทคโนโลยีในการแสดงข้อมูล
โดยใช้ JavaScript ร่วมกับ HTML และ XML โดย AJAX ไม่ใช่ภาษาคอมฯ ใหม่
แต่เป็นเพียงเทคนิคใหม่ในการแสดงเนื้อหาได้ รวดเร็ว และตอบสนองการใช้งานได้ดี สำหรับ
Web Application

โดย AJAX จะใช้ JavaScript ในการแลกเปลี่ยนข้อมูลระหว่าง WebServ และ WebBrowser

##########################################################

AJAX เป็นเทคโนโลยีของ Web Browser

AJAX เป็นเทคโนโลยีที่รันบน Web Browser มันใช้การ Transfer ข้อมูลระหว่าง Server และ
Browser แบบ Asynchonous ซึ่งเทคโนโลยีนี้จะทำให้ Internet Application
มีขนาดเล็กและค่อนข้างดีกว่าแบบเก่า
และเราสามารถที่จะพัฒนาได้ทันที โดยไม่ต้องหา Services Server อะไรมาเพิ่ม

##########################################################


สรุปว่าสิ่งที่ควรศึกษา . . .
- HTML
- JavaScript
- CSS
- XML
- ภาษาที่ใช้ในการ Program บนเวบเช่น PHP , ASP , ASP.net , JSP เป็นต้น

###########################################################

ไว้มาแปลใหม่วันหลัง

โปรเจค SnapShot V1.0

เมื่อประมาณต้นเดือนที่ทำงานซื้อกล้อง WebCam มา 1 ตัว เห็นเค้าบอกว่าจะนำมากล้องที่ซื้อ
มาใช้ร่วมกับโปรแกรม mrecord ของบริษัท PS Solution . .

ทีแรกผมก็เข้าใจว่า อ้อ . . ที่ระบุเสปคของกล้องคงเพราะกล้องสามารถใช้กับโปรแกรมได้เลย
แต่เอาเข้าจริงสรุปว่าให้ใช้กล้องถ่ายรูปเป็น JPG , BMP แล้วทำการ Import เข้าฐานข้อมูล
ด้วยการ Browse จากโปรแกรมของ Mrecord

ผมก็เลยไปค้นหาข้อมูลเกี่ยวกับการเขียนโปรแกรมต่อกล้อง Digital บน MS Windows ดู
สรุปว่าก็ไปเจอ WIN32API ที่สามารถนำมาใช้งานได้

เนื่องด้วยผมต้องพัฒนาให้โปรแกรมใช้งานบน Windows 98/ME และเสปคคอมฯ ที่ค่อนข้างต่ำ
จึงทำให้ผมตัดสินใจเลือกใช้ Visual Basic 6.0 มาใช้งานเนื่องจากคงเหมาะกว่าจะใช้ .net
แต่แน่นอนว่าเมื่อมีเวลาผมจะพัฒนาด้วย C#.net แต่ไม่รู้เมื่อไร ..

คอมพิวเตอร์ที่ใช้รันโปรแกรม ( เฉพาะ OS และ Ram )
- MS Windows 98/ME/XP
- RAM 128 MB Share VGA 32MB หรือ 8MB

สำหรับ WIN32API ที่เรานำมาใช้ใน โปรเจคนี้จะมีทั้งหมด 2 ตัวคือ
- user32
- apicap32.dll

ตัวอย่าง CODE ( ส่วนของค่าคงที่ และ การเรียกใช้ DLL )
Const ws_visible = &H10000000
Const ws_child = &H40000000
Const WM_USER = 1024
Const WM_CAP_EDIT_COPY = WM_USER + 30
Const wm_cap_driver_connect = WM_USER + 10
Const wm_cap_set_preview = WM_USER + 50
Const wm_cap_set_overlay = WM_USER + 51
Const WM_CAP_SET_PREVIEWRATE = WM_USER + 52
Const WM_CAP_SEQUENCE = WM_USER + 62
Const WM_CAP_SINGLE_FRAME_OPEN = WM_USER + 70
Const WM_CAP_SINGLE_FRAME_CLOSE = WM_USER + 71
Const WM_CAP_SINGLE_FRAME = WM_USER + 72
Const DRV_USER = &H4000
Const DVM_DIALOG = DRV_USER + 100
Const PREVIEWRATE = 30

Private Declare Function SendMessage Lib "user32" _
Alias "SendMessageA" (ByVal hWnd As Long, _
ByVal wMsg As Long, _
ByVal wParam As Long, _
ByVal lParam As Long) As Long
Private Declare Function capCreateCaptureWindow Lib "avicap32.dll" _
Alias "capCreateCaptureWindowA" (ByVal a As String, _
ByVal b As Long, _
ByVal c As Integer, _
ByVal d As Integer, _
ByVal e As Integer, _
ByVal F As Integer, _
ByVal g As Long, _
ByVal h As Integer) As Long

Dim hwndc As Long
Dim saveflag As Integer
Dim pictureindex As Integer
Dim filter1(-1 To 1, -1 To 1) As Single
Dim filter2(-1 To 1, -1 To 1) As Single
Dim temp As String

ตัวอย่าง CODE ( การบันทึกภาพ )
Dim bRet As Boolean
Dim szTest As String

'szTest = App.Path & "\scCapture.bmp" & Chr$(0)
szTest = App.Path & "\Capture\" + FileName + ".jpg" & Chr$(0)
bRet = SendMessage(hwndc, WM_CAP_EDIT_COPY, 0&, 0&)

If bRet Then
DoEvents
If Clipboard.GetFormat(vbCFBitmap) Then
PicWCam.Picture = Clipboard.GetData(vbCFBitmap)
SavePicture PicWCam.Image, szTest
DoEvents
Clipboard.Clear
End If
End If

ตัวอย่าง CODE ( Form Load )
On Error GoTo handler:
hwndc = capCreateCaptureWindow("CaptureWindow", _
ws_child Or ws_visible, _
0, _
0, _
PicWCam.Width, _
PicWCam.Height, _
PicWCam.hWnd, _
0)
If (hwndc <> 0) Then
temp = SendMessage(hwndc, wm_cap_driver_connect, 0, 0)
temp = SendMessage(hwndc, wm_cap_set_preview, 1, 0)
temp = SendMessage(hwndc, WM_CAP_SET_PREVIEWRATE, PREVIEWRATE, 0)

temp = SendMessage(Me.hWnd, WM_CAP_EDIT_COPY, 1, 0)
PicWCam.Picture = Clipboard.GetData
Else
MsgBox "ไม่สามารถติดต่อกล้องได้", vbCritical
End If
Exit Sub
handler:
End

สิ้นสุดคร๊าบบ . . . นั้นเป็นส่วนประกอบหลักๆในการใช้ Connect ไป WebCam และบันทึกภาพ
( Note กันลืมน่ะครับ )

Store Procedure

Store Procedure :: คือการเขียนโปรแกรมปนกับภาษา SQL ทิ้งไว้สำหรับประมวลผลบน
Database Server เองเลย ซึ่งการทำ Store Procedure จะช่วยเพิ่มความเร็วในการทำงาน
เพราะจะสามารถประมวลผลข้อมูลได้เร็วกว่า

ปกติแล้ว Store Procedure จะมีให้ใช้ในฐานข้อมูลเช่น MS SQL หรือ Oracle โดยจะมีชื่อเรียก
ที่แตกต่างกันออกไป

T/SQL ( Transaction SQL ) สำหรับ MS SQL
PL/SQL สำหรับ Oracle

โดยทั้ง MS SQL และ Oracle นั้นมี Store Procedure ให้ใช้ทั้งคู่ แต่ข้อเสียก็คือ
Store Procedure นั้นแต่ละบริษัทเป็นผู้ออกแบบซึ่งทำให้มันไม่สามารถใช้ร่วมกันได้
กล่าวคือ ต้องศึกษาการทำงานของแต่ละ DBMS ก่อนจะเขียน Store Procedure

แต่สำหรับ MS-SQL 2005 มีการฝัง CLR เข้าไปทำให้เราสามารถเขียนภาษาในกลุ่ม .net
เช่น C# , VB.net ปนกับ SQL เป็น T/SQL ใช้บน MS SQL ได้ ซึ่งช่วยให้ .net Dev
ทำงานกับ Store Procedure ได้ง่ายขึ้น ^^ ดีใจจังเลย

Tuesday, August 15, 2006

PHP สำหรับ .net

วันนี้อ่าน Blog ใน Thaidev.org แล้วเผอิญไปเห็นว่าในเวบของ CodePlex
บอกว่ามีโปรเจคนึงที่จะทำให้เราสามารถใช้ PHP ได้ใน .net Framework

Ref :: PHP For .net Framework

Saturday, August 12, 2006

การ Set Java ClassPath

วันนี้เจอปัญหาใหม่ๆ . . . เกี่ยวกับ Java ClassPath เลยได้คำตอบมาจาก Narisa แต่แปลกดีนะ
บางเครื่องต้องทำ บางเครื่องไม่ต้องทำ . . . . Sun ทำไมไม่ออกแบบให้มันติดตั้งง่ายกว่านี้นะ ไม่เข้าใจ
จริงๆ

การ Set Classpath ของ Java

Friday, August 11, 2006

Embled Windows Media Player in HTML

ตัวอย่างการฝัง Windows Media Player เข้าไปในเวบ เพื่อใช้สำหรับทำวิทยุออนไลน์
หรือฟังเพลงออนไลน์ ^-^

Refer :

http://www.mioplanet.com/rsc/embed_mediaplayer.htm
ช่วงนี้เห็นมีคนที่ใช้ Windows แบบ Pantip License อยู่ แล้วดันทะลึ่งไป Update : Windows Genuine Advantage
คราวนี้ . . . ก็ติดไอ่ตัวเตือนว่า ใช้ Windows เถื่อน - -''

ความจริงวิธีนี้ของ Microsoft ก็ทำให้ผู้ใช้หลายๆคนได้รู้ว่า . . ตัวพวกเขากำลังใช้ Software เถื่อนอยู่ . . .

สำหรับวิธีแก้ ให้ทำดังต่อไปนี้

HKEY_LOCAL_MACHINE -> SOFTWARE -> MICROSOFT -> ..

WindowsNT -> CurrentVersion -> WinLogon -> Notify

พอถึงตรงนี้ให้ลองหา . . Folder ชื่อ wgalogon

แล้วลบมันทิ้งไปซะ - -''

คราวนี้ก็ไปปิด Auto Update ให้เป็น Disable ซะแล้วก็ลบ system restore ด้วยล่ะ

เรียบร้อยแล้ว ^^