code-prettify

2015年10月10日 星期六

C++ 改變螢幕解析度

Change Screen Resolution in Windows using C++

主要使用 Windows API
ChangeDisplaySettings

EnumDisplaySettings

首先使用 EnumDisplaySettings 取得目前的螢幕設定值
然後修改解析度的寬高
最後使用 ChangeDisplaySettings 更新螢幕設定值

=== 程式範例
#include "windows.h"
#include <string>
#include <iostream>

int main(int argc, char* argv[])
{
if (argc == 3)
{
try
{
unsigned long width = std::stoul(argv[1]);
unsigned long height = std::stoul(argv[2]);


DEVMODE *dm = new DEVMODE();
EnumDisplaySettings(NULL, ENUM_CURRENT_SETTINGS, dm);
dm->dmPelsWidth = width;
dm->dmPelsHeight = height;
ChangeDisplaySettings(dm, CDS_UPDATEREGISTRY);
}
catch (std::invalid_argument e)
{
std::cout << e.what() << std::endl;
}
}

return 0;
}



=== 資料來源
How to change screen resolution using QT, OpenGL, C++, and Linux?
http://stackoverflow.com/questions/11387724/how-to-change-screen-resolution-using-qt-opengl-c-and-linux

How to change screen resolution in Windows using Qt
http://eastfist.com/qt_tutorials/how-to-change-screen-resolution-in-windows-using-qt/

ChangeDisplaySettings function
https://msdn.microsoft.com/en-us/library/dd183411(VS.85).aspx

2015年10月4日 星期日

Qt 如何將 UTF-8 檔案轉存為 UTF-16

之前的文章介紹如何讀取 UTF-8 檔案。
Qt 如何從檔案讀取 UTF-8 的中文
這次介紹如何將 UTF-8 檔案轉存為 UTF-16。

使用 QFile 開啟檔案,
使用 QTextStream 處理編碼,

=== 完整範例
QFile fileIn("input.txt");
if (!fileIn.open(QIODevice::ReadOnly | QIODevice::Text))
{
qDebug() << "fileIn opne fail.";
return;
}

QFile fileOut("output.txt");
if (!fileOut.open(QIODevice::WriteOnly | QIODevice::Text))
{
qDebug() << "fileOut opne fail.";
return;
}

QTextStream in(&fileIn);
in.setCodec("UTF-8");
QTextStream out(&fileOut);
out.setCodec("UTF-16");

while (!in.atEnd()) {
QString line = in.readLine();
out << changeText(line);
}

fileIn.close();
fileOut.close();

qDebug() << "done";

=== 資料來源
Qt Documentation - QTextStream Class
http://doc.qt.io/qt-5/qtextstream.html

2015年10月1日 星期四

Qt PostgreSQL 範例

Qt PostgreSQL 範例

=== 測試環境
OS: Windows 7
Qt Verstion: 5.5.0
Compiler: Visual Studio 2013

OS: Arch Linux 4.1.6
Qt Version: 5.5.0
Compiler: GCC 5.2.0

=== 程式範例
=== 錯誤訊息
QSqlDatabase: QPSQL driver not loaded
QSqlDatabase: available drivers: QSQLITE QMYSQL QMYSQL3 QODBC QODBC3 QPSQL QPSQL7

在 Windows,確認下列檔案
MyAppDir\sqldrivers\qsqlpsql.dll
MyAppDir\libpq.dll
MyAppDir\libeay32.dll
MyAppDir\ssleay32.dll

在 linux,確認 qt project file 加上
INCLUDEPATH+=/usr/include/pgsql
LIBS+=-L/usr/lib -lpq

=== 資料來源
Qt Documentation - SQL Database Drivers
http://doc.qt.io/qt-5/sql-driver.html

Qt: SELECT-Query to PostgreSQL-Server always responses with NULL
http://stackoverflow.com/questions/13633055/qt-select-query-to-postgresql-server-always-responses-with-null

QT5: Failed to load psql driver in windows
http://stackoverflow.com/questions/20884010/qt5-failed-to-load-psql-driver-in-windows

2015年9月26日 星期六

Arch 安裝 PostgreSQL

第一步先安裝 PostgreSQL
sudo pacman -S postgresql

然後登入 postgres 帳號
sudo -i -u postgres

接著進行資料庫初始化
initdb --locale en_US.UTF-8 -E UTF8 -D '/var/lib/postgres/data'

如果發生錯誤,表示目前的 locale 不是 en_US.UTF-8
initdb: invalid locale name "en_US.UTF-8"

初始化資料庫後就可以啟動 PostgreSQL
sudo systemctl start postgresql.service
sudo systemctl enable postgresql.service

建立使用者
createuser --interactive

接著用剛剛建立的使用者帳號建立資料庫
createdb myDatabaseName

使用 psql 進入資料庫
psql -d myDatabaseName

允許遠端連線
修改 /var/lib/postgres/data/postgresql.conf 的內容
listen_addresses = '*'

接著在 /var/lib/postgres/data/pg_hba.conf 將原本的 IPv4設定為
host   all   all   my_remote_client_ip_address/32   md5

設定完之後,重新啟動 PostgreSQL
sudo systemctl restart postgresql



資料來源:
Archlinux Wiki - PostgreSQL
https://wiki.archlinux.org/index.php/PostgreSQL

2015年9月24日 星期四

Qt 如何從檔案讀取 UTF-8 的中文

首先開啟檔案,
然後使用 QTextStream,
記得使用 setCodec 設定編碼。

程式範例:
QFile file("utf8");
if (!file.open(QIODevice::ReadOnly | QIODevice::Text))
return;

QTextStream in(&file);
in.setCodec("UTF-8");
while (!in.atEnd()) {
QString line = in.readLine();
QTextStream qtout(stdout);
qtout << line << "\n";
}

資料來源:
http://stackoverflow.com/questions/5630114/how-to-read-utf-8-text-from-file-using-qt

2015年9月23日 星期三

Qt - 使用 qrand() 產生亂數 rand

Qt - 使用 qrand() 產生亂數 rand

max 最大值
min 最小值

qrand() % ((max + 1) - min) + min;

產生出來的亂數包含 max 及 min 兩者。

如果連續執行多次程式,會發現每次產生的亂數都是一樣的,
因為電腦產生的亂數,其實是偽亂數,所以想要讓每次的亂數不同,
還需要執行 qsrand 來設定亂數種子。

備註:使用 QTime::currentTime().msec() 現在時間當作種子來設定
備註:使用 QElapsedTimer 取得小於 ms 的時間刻度

資料來源:
Qt Documentation - <QtGlobal> - Global Qt Declarations
http://doc.qt.io/qt-5/qtglobal.html#qrand

How to generate random number between two numbers? Qt
http://qt-project.org/forums/viewthread/24262

Use of qsrand, random method that is not random
http://stackoverflow.com/questions/2767383/use-of-qsrand-random-method-that-is-not-random

Qt: Fast way to measure time?
http://stackoverflow.com/questions/244646/qt-fast-way-to-measure-time

Qt - 建立一個 Console 應用程式

想要用 Qt 建立一個 Console 應用程式,
只要像下列的範例就可以建立。

#include <QtCore/QCoreApplication>
#include "Foo/Foo.h"

int main(int argc, char* argv[])
{
QCoreApplication app(argc, argv);

Foo foo;

return app.exec();
}

資料來源:
How do I create a simple Qt console application in C++?
http://stackoverflow.com/questions/4180394/how-do-i-create-a-simple-qt-console-application-in-c

2015年9月21日 星期一

Arch Linux 安裝 ssh server

使用 Linux 常常會用到的功能 ssh

首先安裝 ssh server
pacman -S openssh

接著啟動服務
systemctl start sshd.service

可以設定開機自動啟動服務
systemctl enable sshd.service

如果是在 VM 底下操作的話,記得設定 port forwarding


2015年9月20日 星期日

SQL 在 Unicode 欄位設定 Unicode 文字

在 Unicode 欄位設定 Unicode 文字
必需滿足兩個條件

一、該 sql 檔案編碼為 UTF-8
這是常被忽略的一點,曾經因為檔案編碼為 Big5 而花費幾個小時找問題,
使用 SSMS 前,預設存檔編碼為 Big5,記得自行轉檔。

二、該文字前加上 N 前置詞
一個字串如果沒有加上前置詞,該字串會被當作非 Unicode 解讀,
造成存在 Unicode 欄位時變成亂碼

範例:

UPDATE GameServer.dbo.Game SET Name = N'可愛巧虎島'



資料來源:
在 SQL Server 中處理 Unicode 字串常數時,必需為所有的 Unicode 字串加上前置詞 N
https://support.microsoft.com/zh-tw/kb/239530

2015年8月4日 星期二

如何讓 Sublime Text 3 顯示目前編碼

上次提過將 Sublime Text 加入右鍵選單
這次遇到如何顯示檔案編碼 (encoding) 的問題,
其實也是從 notepad++ 轉用 Sublime Text 的習慣。

預設的 Sublime Text 3 的介面是這樣

首先選擇 Preferences / Settings - User

接著會出現使用者自訂設定檔

接著在大括號中輸入下列字串後存檔
"show_encoding": true,
成功!,右下角馬上就出現目前的編碼是 UTF-8 了!

2015年7月22日 星期三

2015 Fukushima Game Jam



2015 Fukushima Game Jam 即將在 08/22(六)~08/23(日) 舉行,歡迎大家報名參加。
日本 Fukushima Game Jam 網站

台灣 Fukushima & Faust Game Jam 2015
跟去年一樣,本次台灣也有三個場地,分別在台北、台中、高雄,
報名網址如下:
台北會場
台中會場
高雄會場

幾個常見問題:
目標:在 30 小時內,完成指定主題的遊戲
條件:想作遊戲的心,不需要特定技能,現場會組隊,大家一起做出好玩的遊戲
費用:無,所以請自備筆電,餐飲自理,住宿自理

參考資料
東北ITコンセプト 福島GameJam 2015 | Fukushima Game Jam
http://fgj.igda.jp/

來自全世界的 Global Game Jam 創意作品介紹 台灣業界開發者分享參賽經驗談
http://gnn.gamer.com.tw/3/110333.html

四人兩天開發的《Dora》- MIT Game Jam 心得分享
http://tzengyuxio.me/blog/2012/05/01/mit-game-jam-dora/

2012 Fukushima Game Jam(台北會場)活動概要
https://igdshare.org/fgj2012-taipei

Fukushima Game Jam 2013 通關報告
http://alimencave.blogspot.tw/2013/08/fukushima-game-jam-2013.html

陳禮國 / 遊戲製作的精神時光屋-Game Jam 如何激發無限創意
http://www.tgdf.tw/en/archives/676

FUKUSHIMA & FAUST GAME JAM 2014:《BBQ SENTAI》(烤肉戰隊)
http://gamingsummit.tumblr.com/post/93876707119/fgj-2014-bbq-sentai

2015年7月16日 星期四

ASP.NET API 加入 JSONP 支援

使用 Nuget 安裝 WebApiContrib.Formatting.Jsonp 套件

在 Global.asax 的 Application_Start 函式中加入

GlobalConfiguration.Configuration.Formatters.Insert(0, new JsonpMediaTypeFormatter(new JsonMediaTypeFormatter()));

在 App_Start/WebApiConfig.cs 的 Register 修改 Route 如下

config.Routes.MapHttpRoute(
   name: "DefaultApi",
   routeTemplate: "api/{controller}/{id}/{format}",
   defaults: new
   {
       id = RouteParameter.Optional,
       format = RouteParameter.Optional
   }
);

這樣就可以支援 Jsonp!

註:會自動判斷 Headers 的 Accept 參數,如果是 application/json 則會回傳 json 格式

資料來源:
WebApiContrib.Formatting.Jsonp
https://github.com/WebApiContrib/WebApiContrib.Formatting.Jsonp

2015年7月15日 星期三

Qt WebSocket

宣告 WebSocketServer
new QWebSocketServer("Web Server", QWebSocketServer::NonSecureMode, this)

使用 listen() 開始接受 client 連線

同樣是使用 newConnection() 接受新的 client 事件
使用 nextPendingConnection() 取得 client 的 socket

QWebSocket 使用 disconnected 斷線事件

因為 WebSocket 規範中有兩種資料傳送方式,純文字模式及二進制模式,
所以資料接收事件也分為兩種,分別為
textMessageReceived,參數為 QString message
binaryMessageReceived,參數為 QByteArray message

傳送資料也分為兩個函式,分別為
sendTextMessage
sendBinaryMessage

簡單範例

connect(m_pWebSocketServer, &QWebSocketServer::newConnection, [=]() {
qDebug() << "new client socket";

QWebSocket* socket = this->m_pWebSocketServer->nextPendingConnection();

connect(socket, &QWebSocket::disconnected, [=]() {
qDebug() << "client socket disconnected";

socket->deleteLater();
});

connect(socket, &QWebSocket::textMessageReceived, [=](QString message) {
qDebug() << "client textMessageReceived";

qDebug() << "Read: " << message;
qDebug() << "Send " << message;

socket->sendTextMessage(message);
socket->close();
});

connect(socket, &QWebSocket::binaryMessageReceived, [=](QByteArray message) {
qDebug() << "client processBinaryMessage";

qDebug() << "Read: " << message;
qDebug() << "Send " << message;

socket->sendBinaryMessage(message);
socket->close();
});
});

m_pWebSocketServer->listen(QHostAddress::Any, 8812);

資料來源
Echo Server Example
http://doc.qt.io/qt-5/qtwebsockets-echoserver-example.html

QWebSocketServer
http://doc.qt.io/qt-5/qwebsocketserver.html

2015年7月14日 星期二

Qt TcpSocket

Server 的部份使用 QTcpServer

呼叫 listen 函式開始接受 Client 連線,參數為 QHostAddress::Any, 8811

在 newConnection signal 接受 socket

QTcpSocket* socket = server->nextPendingConnection();

在 readyRead() signal 接收資料

QBtyeArray data = socket->readyAll()

使用 write() 傳送資料

簡單的範例:

  m_server = new QTcpServer();
connect(m_server, &QTcpServer::newConnection, [=]() { qDebug() << "new client socket"; QTcpSocket* socket = this->m_server->nextPendingConnection(); connect(socket, &QTcpSocket::disconnected, [=]() { qDebug() << "client socket disconnected"; socket->deleteLater(); }); connect(socket, &QTcpSocket::readyRead, [=]() { qDebug() << "client readyRead"; QString string = socket->readAll(); qDebug() << "Read: " << string; string = string.toUpper(); qDebug() << "Send " << string; socket->write(string.toLatin1()); socket->close(); }); }); m_server->listen(QHostAddress::Any, 8811); qDebug() << "server listen";


Client 直接使用 QTcpSocket

呼叮 connectToHost 與 server 連線
連上了會觸發 connected 訊號,斷線則是 disconnected
接收資料一樣是 readyRead

簡單的範例:

m_client = new QTcpSocket();

connect(m_client, &QTcpSocket::connected, [=]() {
qDebug() << "socket connected";

QString string = "Hi";
m_client->write(string.toLatin1());
qDebug() << "Send: " << string;
});

connect(m_client, &QTcpSocket::disconnected, [=]() {
qDebug() << "socket disconnected";
});

connect(m_client, &QTcpSocket::readyRead, [=]() {
qDebug() << "client readyRead";

QString string = m_client->readAll();
qDebug() << "Read: " << string;

m_client->close();
});

m_client->connectToHost("127.0.0.1", 8811);


資料來源:
Network Programming with Qt
http://doc.qt.io/qt-5/qtnetwork-programming.html

Sockets - Server & Client using QT
http://www.bogotobogo.com/cplusplus/sockets_server_client_QT.php

QTcpSocket Class
http://doc.qt.io/qt-5/qtcpsocket.html

2015年6月24日 星期三

複製所有檔案及資料夾指令

Windwos

xcopy source [Destination] /i /e /k /h

Linux

cp -R source dest

資料來源

Xcopy
https://www.microsoft.com/resources/documentation/windows/xp/all/proddocs/en-us/xcopy.mspx

xcopy functionality with linux?
http://www.linuxquestions.org/questions/linux-general-1/xcopy-functionality-with-linux-386643/

2015年6月17日 星期三

如何將 Sublime Text 3 加入右鍵選單中

從 Notepad++ 改用 Sublime Text 之後,最不習慣的地方就是在右鍵選單內,
將下列內容存成 run.bat 後,以管理員的權限執行,就會將 Sublime Text 加入右鍵選單

 @echo off
  SET st2Path=C:\Program Files\Sublime Text 3\sublime_text.exe

  rem add it for all file types
  @reg add "HKEY_CLASSES_ROOT\*\shell\Open with Sublime Text 3"         /t REG_SZ /v "" /d "Open with Sublime Text 3"   /f
  @reg add "HKEY_CLASSES_ROOT\*\shell\Open with Sublime Text 3"         /t REG_EXPAND_SZ /v "Icon" /d "%st2Path%,0" /f
  @reg add "HKEY_CLASSES_ROOT\*\shell\Open with Sublime Text 3\command" /t REG_SZ /v "" /d "%st2Path% "%%1"" /f

  rem add it for folders
  @reg add "HKEY_CLASSES_ROOT\Folder\shell\Open with Sublime Text 3"         /t REG_SZ /v "" /d "Open with Sublime Text 3"   /f
  @reg add "HKEY_CLASSES_ROOT\Folder\shell\Open with Sublime Text 3"         /t REG_EXPAND_SZ /v "Icon" /d "%st2Path%,0" /f
  @reg add "HKEY_CLASSES_ROOT\Folder\shell\Open with Sublime Text 3\command" /t REG_SZ /v "" /d "%st2Path% "%%1"" /f
  pause

資料來源
Add “Open with Sublime Text 3″ to Windows Explorer Context Menu
http://wordpress-corner.com/add-open-sublime-text-3-windows-explorer-context-menu/

2015年6月15日 星期一

Sevabot - Skype bot - Windows Install

一、從 git 取得 Sevabot

git clone git://github.com/opensourcehacker/sevabot.git


二、安裝設定

在 cmd 輸入下列指令

cd sevabot
powershell -NoProfile -ExecutionPolicy unrestricted -Command "add-content -path virtualenv.py -value(new-object net.webclient).DownloadString('https://raw.github.com/pypa/virtualenv/master/virtualenv.py')"
python virtualenv.py venv --no-setuptools

set-executionpolicy unrestricted
    . .\venv\Scripts\activate.ps1
這段意思似乎是將 activate.ps1 設定為「可執行」的樣子
具體行為不知道是什麼?所以我什麼也沒做

python setup.py develop

執行後在 python 目錄的 Scripts 資料夾 (C:\Python27\Scripts) 找到 sevabot.exe 及 sevabot-script.py,複製到 sevabot 目錄下。

接著從範本複製一份設定出來。
cp settings.py.example settings.py

最後執行 sevabot

sevabot.exe

這時候 skype 會出現第三方元件存取的詢問訊息,記得按允許,
同時會啟動 web service,預設在 localhost:5000

三、使用 sevabot 傳送訊息

啟動 browser 開啟 localhost:5000 會看到網頁



其中 Shared Secret 就在 settings.py 中的 SHARED_SECRET 設定 (圖中為 koskela)
之後使用 web api 傳送訊息的時候都要使用這組密碼


使用 POST 時,需要參數 shared_secret 及 message
使用 Postman 範例


使用 cURL 範例

curl -F "shared_secret=koskela" -F "message=Hi, This is test." http://localhost:5000/message/xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx/

資料來源

Sevabot - Skype bot 1.0 documentation
https://sevabot-skype-bot.readthedocs.org/en/latest/

Github - opensourcehacker/sevabot
https://github.com/opensourcehacker/sevabot

Installation fails on Windows: Pip and setuptools fail to install #94
https://github.com/opensourcehacker/sevabot/issues/94

2015年5月27日 星期三

bootstrap glyphicons-halflings-regular.woff 404 not found IIS

bootstrap glyphicons-halflings-regular.woff 404 not found IIS

網站發現一行錯誤訊息:
glyphicons-halflings-regular.woff 404 not found

檢查後發現,檔案確實存在,剩下的可能性就是 woff 副檔名 IIS 不認識,
要讓 IIS 認識相關檔案的話,可以在 web.config 加入下列設定

  <system.webServer>
    <staticContent>
      <remove fileExtension=".eot" />
      <remove fileExtension=".ttf" />
      <remove fileExtension=".otf"/>
      <remove fileExtension=".woff"/>
      <mimeMap fileExtension=".eot" mimeType="application/vnd.ms-fontobject" />
      <mimeMap fileExtension=".ttf" mimeType="font/ttf" />
      <mimeMap fileExtension=".otf" mimeType="font/otf" />
      <mimeMap fileExtension=".woff" mimeType="application/font-woff" />
    </staticContent>
  </system.webServer>

資料來源:
Twitter bootstrap glyphicons do not appear in release mode 404
http://stackoverflow.com/questions/21269884/twitter-bootstrap-glyphicons-do-not-appear-in-release-mode-404

IIS - RESOURCE INTERPRETED AS FONT BUT TRANSFERRED WITH MIME TYPE APPLICATION/X-FONT-WOFF
http://deanhume.com/home/blogpost/iis---resource-interpreted-as-font-but-transferred-with-mime-type-application-x-font-woff/4101

2015年5月21日 星期四

nginx 使用正則表達式將特定網址重導向

nginx 使用正則表達式將特定網址重導向

最近遇到一個問題,要將特定的網址重導向,
例如將 http://domain/data/1234/ 重導向為 http://domain/data/1234/data.json。

本來想說還要靠後端服務來處理,
後來想到 nginx 應該有支援重導向的功能,
可以使用 301 Redirect 設定:

location /data/1234/ {
    return 301 /data/1234/data.json
}

但是上面範例中的 1234 只是其中一個可能性,實際上是不定長度的數字,
所以接下來要使用正則表達式 (Regular Expression) 來解析想要的網址。

解析條件如下:
http://domain/data/{number}/

其中 http://domain 是根目錄,後面的 /data/ 是固定的,接著 {number} 是不定長度的數字,
最後結尾有個 / 是不一定要有的(考慮到有人可能不想打這個字),所以加上 ? 表示可有可無。

上述條件的 regex 表示如下:
^\/data/[0-9]+\/?

因為要將數字的部份當成變數,所以要加上 () 括號,
在 nginx 的設定檔 /etc/nginx/nginx.conf 加上

location ~ '^\/data/([0-9]+)\/?' {
    return 301 /data/$1/data.json
}

上面這樣就可以成功轉址,但是執行後卻發生錯誤了!

「此網站包含重新導向迴圈」

原來我們重導向後的網址 http://domain/data/1234/data.json 還是符合 regex 裡面的絛件啊!
於是要在條件的最後加上一個 $ 代表結尾,這樣就不會一直在迴圈中跑不出來嘍。

location ~^\/data\/([0-9]+)\/?$ {
    return 301 /data/$1/data.json
}

相關文章:
Arch Linux nginx 安裝

資料來源:
How to redirect single url in nginx?
http://stackoverflow.com/questions/18037716/how-to-redirect-single-url-in-nginx

Basic Nginx Configuration
https://www.linode.com/docs/websites/nginx/basic-nginx-configuration

2015年5月20日 星期三

Arch Linux 安裝 nginx

Arch Linux 安裝 nginx

安裝 nginx
# pacman -S nginx

預設設定為 localhost 80 port,
使用 systemd 來執行 nginx (一次性)
# systemctl start nginx.service
或者啟動此服務 (開機自動執行)
# systemctl enable nginx.service

這時候可以在 http://localhost 看到預設網頁了喔!


nginx 主要設定檔為 /etc/nginx/nginx.conf,可以使用 nano 編輯
# nano /etc/nginx/nginx.conf

預設網頁為 /usr/share/nginx/html/index.html,可以使用 cat 查詢
# cat /usr/share/nginx/html/index.html

相關文章:
nginx 使用正則表達式將特定網址重導向

資料來源:
Arch Wiki - nginx
https://wiki.archlinux.org/index.php/Nginx

Arch Wiki - systemd
https://wiki.archlinux.org/index.php/Systemd#Using_units

2015年5月18日 星期一

Arch Linux 文章列表

基本安裝:

VirtualBox 安裝 Arch Linux

Arch Linux 基本設定

Arch Linux 安裝 ssh server

選擇性安裝:

Arch Linux C++ / Qt 開發

Arch Linux 安裝 nginx

Arch 安裝 PostgreSQL

Arch 安裝 RabbitMQ

發生問題:

安裝 Arch Linux 發生錯誤 invalid of corrupted package (PGP signature)


Arch Linux C++ / Qt 開發

Arch Linux C++ / Qt 開發

要進行 C++ 開發,只要安裝基本開發套件
# pacman -S base-devel
使用 nano 新增 main.cpp 輸入下列文字:

#include <iosteam>

int main(int argc, char* argv[])
{
    std::cout << "Hello World!" << std::endl;

    return 0;
}

存檔後使用 g++ 編譯
# g++ main.cpp
編譯後會產生 a.out 檔案,執行
#./a.out
畫面上就會印出 Hello World! 文字

接著安裝 Qt 套件
# pacman -S qt
新增一個 qt 資料夾並進入
# mkdir qt
# cd qt
使用 nano 新增 main.cpp 輸入下列文字:

#include <QDebug>

int main(int argc, char* argv[])
{
    qDebug() << "Hello World!";

    return 0;
}

使用 qmake 產生專案檔
# qmake -project
使用 qmake 產生 Makefile
# qmake
使用 Makefile 編譯
# make
執行產生的 qt 檔案
# ./qt
畫面上會印出 Hello World! 的文字

相關文章:
Arch Linux 文章列表

資料來源:
Arch Linux
https://www.archlinux.org/

Arch Linux 臺灣社群
http://archlinux.tw/

2015年5月17日 星期日

Arch Linux 基本設定

Arch Linux 基本設定

本文接續前篇:
VirtualBox 安裝 Arch Linux



可以使用下列指令檢查網路是否正常
# ping -c 3 www.google.com

設定 root 密碼
# passwd

設定 hostname
echo arch > /etc/hostname

設定時區 (此範例將時區設定為台北時間)
ln -s /usr/share/zoneinfo/Asia/Taipei /etc/localtime

註:如果出現下列錯誤訊息,加上 -f 參數即可強制執行
ln: failed to create symbolic link '/etc/locatime': File exists



=== 設定 UTF-8 語系

設定支援語系,編緝要產生的語系
# nano /etc/locale.gen

將下列解除註解 (刪除開頭的 # 符號)
en_US.UTF-8 UTF-8

開始產生語系
# locale-gen

設定系統的語系為 UTF-8
localectl set-locale LANG=en_US.UTF-8



新增使用者 (
# useradd -m {username}
註:沒有加上 -m 參數的話,
不會建立使用者家目錄 /home/{username} 及相關檔案 .bash_logout .bash_profile, .bashrc

設定使用者密碼
# passwd {username}

刪除使用者
# userdel {username}

範例:
#useradd demo
#useradd demo

安裝 sudo
#pacman -S sudo

設定 sudo 的使用者
警告:永遠只用 visudo 指令來修改,不要直接修改檔案,
因為 visudo 指令會在修改完畢後進行檢查。
你可以使用預設的 vi 編輯器
# visudo
或者使用 nano 當編輯器
# EDITOR=nano visudo
簡單的將某一使用者加入 sudo 的方法是在
root ALL=(ALL) ALL 下面加入一行
{username} ALL=(ALL) ALL
例如:
demo ALL=(ALL) ALL

登出後使用新的使用者帳密登入
# logout



===
20160512 Update:
設定 UTF-8 語系

20160106 Update:
移除啟動 dhcp 服務 (移到安裝時進行)

相關文章:
Arch Linux 文章列表

資料來源:
Arch Linux
https://www.archlinux.org/

Arch Linux 臺灣社群
http://archlinux.tw/

鳥哥的 Linux 私房菜
http://linux.vbird.org/linux_basic/

安裝 Arch Linux 發生錯誤 invalid of corrupted package (PGP signature)

安裝 Arch Linux 發生錯誤 invalid of corrupted package (PGP signature)

今天安裝時發生下列錯誤:
error: dhcpcd: signature from "Anatol Pomozov <anatol.pomozov@gmail.com>" is unknown trust
:: File /mnt/var/cache/pacman/pkg/dhcpcd-6.7.1-1-x86_64.pkg.tar.xz is corrupter (invalid of corrupted package (PGP signature)).

這時候就要更新 key
# pacman-key --populate archlinux
# pacman-key --refresh-keys

之後再執行一次安裝即可
# pacstrap -i /mnt base

相關文章:
Arch Linux 文章列表

資料來源:
Arch Linux - [Solved] New install - invalid of corrupted package (PGP signature)
https://bbs.archlinux.org/viewtopic.php?id=195139

2015年5月10日 星期日

VirtualBox 安裝 Arch Linux

VirtualBox 安裝 Arch Linux

一、取得安裝檔 (iso)

Arch網站選擇一個站台下載 iso 檔案,建議使用 BT 下載
Release Info 顯示最新的版本資訊
BitTorrent Download (recommended) 是 BT 磁力連結及種子檔
HTTP Direct Downloads 開始是全球各地直接下載的連結

本文編輯時的版本:
Current Release: 2016.01.01
Included Kernel: 4.3.3

註:如果是現有的 arch linux,可以使用 pacman -Syu 指令直接升級

二、設定 VirtualBox

建立一個新的虛擬機,設定記憶體 512 MB,硬碟 16 GB。

三、開始安裝

啟動虛擬機後,掛載 iso 檔,會看到安裝畫面

按下 Enter 選擇第一項 Boot Arch Linux (x86_64) 之後進入安裝介面

首先進行網路連線測試,確認網路功能正常
# ping -c 3 www.google.com

將著使用 cgdisk 建立 GPT 分割區,
預計分別建立 10G 在  / (根目錄),4G在 /home,2G 在 /swap (共 16G)
# cgdisk /dev/sda

警告頁面,按下任何鍵後繼續,
會看到目前總共有16G 的 free space


首先建立第一個空間,10G
New / Enter (預設) / 10G / Enter (預設 8300) / Enter (預設空白)



移到下面的 6G free space 的位置,同樣的動作建立 4G 空間
New / Enter (預設) / 4G / Enter (預設 8300) / Enter (預設空白)

移到最後的 2G free space 的位置
New / Enter (預設) / 2G / Enter (預設 8300) / Enter (預設空白)

確認正確後寫入(警告訊息為此動作會破壞硬碟上的資料)
Write / Enter
最後離開 cgdisk
Quit

建立檔案系統
# mkfs.ext4 /dev/sda1
# mkfs.ext4 /dev/sda2

別忘了 swap
# mkswap /dev/sda3
# swapon /dev/sda3

使用 lsblk 來確認目前的分割區狀態
# lsblk /dev/sda

掛載分割區
# mount /dev/sda1 /mnt
# mkdir /mnt/home
# mount /dev/sda2 /mnt/home

使用 pacstrap 安裝基本系統
# pacstrap -i /mnt base

產生 fstab 檔案
# genfstab -U -p /mnt >> /mnt/etc/fstab
使用 nano 文字編緝器查看產生的資訊
# nano /mnt/etc/fstab
(Ctrl + X 離開 nano)

使用 chroot 進入剛安裝好的系統
# arch-chroot /mnt /bin/bash

 設定 BIOS 主機版開機載入程式
# pacman -S gptfdisk
# pacman -S syslinux
# syslinux-install_update -i -a -m

設定開機根目錄為 /dev/sda1 (預設為 /dev/sda3)
# nano /boot/syslinux/syslinux.cfg

設定網路,啟動 dhcp 服務
# systemctl enable dhcpcd.service

離開 chroot 並重啟系統
# exit
# umount -R /mnt
# poweroff

記得先退出 arch 安裝光碟

重開機後看到開機選項,5秒後自動進入 Arch Linux
接著登入 root 後就可以開始使用了


到此基本系統安裝完成,如果有興趣可以參考下一篇:
Arch Linux 基本設定

相關文章:
Arch Linux 文章列表

20150611 Update:
Arch 版本由 2015.05.01 改為 2015.06.01,硬碟空間由 8G 改為 16G
20160106 Update:
Arch 從 2015.06.01 更新為 2016.01.01
Kernel 從 4.0.4 更新為 4.3.3
新增啟動 dhcp 服務 (原本在基本設定時才進行)

資料來源:
Arch Linux
https://www.archlinux.org/

Arch Linux 臺灣社群
http://archlinux.tw/

2015年4月29日 星期三

Visual Studio Qt IntelliSense: 無法開啟來源檔案 "initializer_list"

Visual Studio Qt IntelliSense: 無法開啟來源檔案 "initializer_list"

完整的訊息如下:
IntelliSense: 無法開啟來源檔案 "initializer_list"
IntelliSense:  內嵌規範只能用於函式宣告
IntelliSense:  namespace "std" 沒有成員 "initializer_list"
IntelliSense:  必須是 ')'
IntelliSense:  必須是 ';'
IntelliSense:  class "QStringList" 沒有成員 "sort"

一開始因為有些專案會出現,有些不會,所以沒有發現原因,
後來發現原因是 Visual Studio 2013 指定平台工具組為 Visual Studio 2012,
也就是使用 VS 2013 為 IDE,但是 compiler toolchain 使用 VS 2012 進行編譯。

一些程式的寫法是用 Visual Studio 的版本來判斷是否支援某些寫法,像是 C++11 之類的,
這時候因為使用的 IDE 版本跟編譯器不一致,導致 VS 的 IntelliSense 誤判。

目前的解決方法是強制設定這些專案的 VS 版本為 2012,
在專案屬性宣告 _MSC_FULL_VER=170061030 即可。

2015年3月21日 星期六

googletest - Google C++ Testing Framework - Visual Studio 2013

本文介紹如何在 Visual Studio 2013 使用 Google C++ Testing Framework

首先取得 gtest,下載 gtest-1.7.0.zip
解壓縮之後,在 msvc 資料夾下可以找到 gtest, gtest-md 兩個方案檔,
兩個方案差別在 gtest 編譯屬性為 MT (MTd),而 gtest-md 為 MD (MDd),
這裡要選擇跟待測專案同樣的設定,關於 MD, MT 詳細資訊請見 MSDN


如果手邊沒有現有專案的話,先建立一個空專案在 C:\Project1,
因為 VS C++ 專案預設為 MD,所以接下來選擇 gtest-md 為範例。

直接點擊兩下gtest-md 方案,VS 會自動將 VS 2003 版本轉換為 VS2013 版本,
編譯之後,複製 msvc\gtest-md\Debug\gtestd.lib 及 C:\gtest-1.7.0\msvc\gtest-md\Release\gtest.lib
到 C:\Project1\Project1\gtest\lib
另外複製 C:\gtest-1.7.0\include 整個資料夾到 C:\Project1\Project1\gtest。



接著設定 Project1 的專案使用 googletest,分別是
其他 Include 目錄為 .\gtest\include
其他程式庫目錄為 .\gtest\lib
其他相依性為 gtest.lib




接著將 main.cpp 改為下列範例
#include "gtest/gtest.h"
 
int main(int argc, char* argv[])
{
 ::testing::InitGoogleTest(&argc, argv);
 return RUN_ALL_TESTS();
}
 
int add(int a, int b)
{
 return a + b;
}
 
TEST(AddTest, Test1) {
 EXPECT_EQ(3, add(1, 2));
}

編譯,執行成功!
恭喜可以開始進行 Unit Test 了!



註:如果使用 Visual Studio 2012 會遇到「error C2977: 'std::tuple' : 樣板 引數太多 」錯誤
可以參考這篇:error C2977: 'std::tuple' : too many template arguments


參考資料:
googletest - Google C++ Testing Framework
https://code.google.com/p/googletest/

Primer - Getting started with Google C++ Testing Framework
https://code.google.com/p/googletest/wiki/Primer

Samples - Google C++ Testing Framework Samples
https://code.google.com/p/googletest/wiki/Samples

2015年3月20日 星期五

error C2977: 'std::tuple' : too many template arguments

最近遇到「error C2977: 'std::tuple' : 樣板 引數太多 」的問題,
上網查詢之後發現是 Visual Studio 2012 不支援 variadic templates,
解決方案是在前置處理器定義加上 _VARIADIC_MAX 10
註:Visual Studio 2013 已支援


參考資料:
C2977: 'std::tuple' : too many template arguments (MSVC11)
http://stackoverflow.com/questions/8274588/c2977-stdtuple-too-many-template-arguments-msvc11