2013-04-26

Delphi 寫的程式 Build 到 Mac OS X 執行



為什麼這樣做?

說真的,用了 Object Pascal 那麼多年,還是用 Delphi 開發 Windows 的程式比較習慣。

這也是為什麼,目前商用軟體的廠商,還是採用 Delphi 開發系統應用程式佔了大多數的原因。

我為了這個目標,大概用了幾年的時間,想要在 Mac 上面開發商用軟體,試了很多種做法,現在 Delphi 可以用 LLVM 編譯,再傳到 Mac 上面,我看這樣的路會是最無痛,也是比較實際的方法了!

Borland(embarcadero) Delphi 這次不會像兩千年的 Kylix 了,挑對了作業系統,命運也會朝向好運的方向前進!

辦公室的軟體,移植到 Mac OS 的時間應該不遠了!


.

2013-04-19

UIImage 存放到 NSArray/NSMutableArray 內

最近學員遇到一個問題,要將 UIImage 放到 NSMutableArray 內,但是很不幸地會發生這樣的錯誤訊息:
ImageArray[5343:c07] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '*** -[__NSArrayM insertObject:atIndex:]: object cannot be nil'

不管是從 NSBundle 或是從 NSFileManager 取得 Documents 的都一樣。

載入如下:

NSArray *directoryContent = [[NSBundle mainBundle] pathsForResourcesOfType:@"png" inDirectory:nil];
NSMutableArray *items = [[NSMutableArray alloc] initWithCapacity:0];

for (NSString *imagePath in directoryContent) {
    UIImage *img = [UIImage imageNamed:imagePath];
    [items addObject:img];
}
NSLog(@"imagesArray:%@", items);

可是執行之後,就會得到上述的錯誤訊息。

錯誤的原因就在這句:
UIImage *img=[UIImage imageNamed: imagePath];

只要改成
UIImage *img = [UIImage imageWithContentsOfFile:imagePath];

錯誤就可以修正


最後正確的程式碼如下:

NSArray *directoryContent = [[NSBundle mainBundle] pathsForResourcesOfType:@"png" inDirectory:nil];
NSMutableArray *items = [[NSMutableArray alloc] initWithCapacity:0];

for (NSString *imagePath in directoryContent) {
    UIImage *img = [UIImage imageWithContentsOfFile:imagePath];
    [items addObject:img];
}
NSLog(@"imagesArray:%@", items);


善用你在 Xcode 的 Option+Click,你就可以找到答案了:

+ (UIImage *)imageWithContentsOfFile:(NSString *)path
Creates and returns an image object by loading the image data from the file at the specified path.
This method does not cache the image object.

+ (UIImage *)imageNamed:(NSString *)name
Returns the image object associated with the specified filename.
This method looks in the system caches for an image object with the specified name and returns that object if it exists


下載範例檔案
.

2013-04-01

Storyboard 有兩個 Segue 的問題

剛好有學員問到這樣的問題,我就拿該程式畫面在這裡做個圖文解說。
這個畫面連結了兩個 Segue
一般 Segue 都是要在  - (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender 內安排,如果有 Object 或 Value 要往下個 ViewController 傳遞的話,也是在這裡處理。


另外,如果只有一個 Segue 是從 UIButton 發生,可以這樣做:
- (IBAction)btnSyp:(id)sender {
    UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"MainStoryboard" bundle:nil];
    Game01VC *vc = [storyboard instantiateViewControllerWithIdentifier:@"CustomerAdd"];
    vc.Flag = 1;
}

但是,第二個 UIButton 就無法如預期發生。
- (IBAction)btnKiller:(id)sender {
    UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"MainStoryboard" bundle:nil];
    Game01VC *vc = [storyboard instantiateViewControllerWithIdentifier:@"CustomerAdd"];

    vc.Flag = 2;
}

所以,還是要回來以 prepareForSegue 處理。


先在 Storyboard 內設定好 Segue 的 Identifier 為 @"btnSyp" 與 @"btnKiller"


在第一個 UIButton 連結的 Segue 設定 Identifier 為 @"btnSyp"
另一個 UIButton 連結的 Segue 設定 Identifier 為 @"btnKiller"

在 prepareForSegue 內的程式如下:

-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
    Game01VC *vc = segue.destinationViewController;

// 原本在 -(IBAction)btnSyp:(id)sender 內的,移到這裡來,以這種方式做
    if ([segue.identifier isEqualToString:@"btnSyp"]) {
        vc.Flag = 1;
    }
    
// 原本在 -(IBAction)btnKiller:(id)sender 內的,移到這裡來,以這種方式做
    if ([segue.identifier isEqualToString:@"btnKiller"]) {
        vc.Flag = 2;
    }
}

如此,就可以讓下個 ViewController 收到 Object 或 Value 了。


.

2013-03-30

iOS Dev Club 聚會 2013-03-30 活動影片

張景隆分享 Passbook 的實作,向隅的朋友可以觀看影片。


很久沒有來的家銘,這段時間都在開發這個平台,InWedding



iOS Dev Club : iPhone/iPad/iPod touch 軟體應用開發
https://www.facebook.com/groups/iostw/

姻為妳 inWedding 粉絲頁
https://www.facebook.com/OurInWedding




2013-02-07

白領族用的行動設備,藍領族的呢?

http://www.macworld.com/article/2026881/expo-notes-servicepal-puts-ipads-in-hands-of-blue-collar-workers.html