Clang Syntax Example
C++
#include <iostream>
/* Multi-line comment test
Hello World!
*/
// If we increase row by 1, the offset will increase by sz (number of elements per row i.e. number of columns)
// If we increase col by 1, the offset will increase by 1
unsigned rowMajorOffset(unsigned row, unsigned col, unsigned sz)
{
return col + row * sz;
}
// If we increase col by 1, the offset will increase by sz (number of elements per column i.e. number of rows)
// If we increase row by 1, the offset will increase by 1
unsigned columnMajorOffset(unsigned row, unsigned col, unsigned sz)
{
return row + col * sz;
}
template <typename _ValueT, unsigned _R, unsigned _C, bool _ColumnMajor>
class Matrix {
protected:
enum { ColumnMajor = _ColumnMajor };
enum { R = _R };
enum { C = _C };
typedef _ValueT ValueT;
ValueT m_values[C*R];
public:
const ValueT & at (unsigned r, unsigned c) const
{
if (ColumnMajor)
return m_values[columnMajorOffset(r, c, R)];
else
return m_values[rowMajorOffset(r, c, C)];
}
ValueT & at (unsigned r, unsigned c)
{
if (ColumnMajor)
return m_values[columnMajorOffset(r, c, R)];
else
return m_values[rowMajorOffset(r, c, C)];
}
void loadTestPattern ()
{
for (unsigned r = 0; r < R; r += 1)
for (unsigned c = 0; c < C; c += 1)
at(r, c) = (r+1) * 1000 + (c+1);
}
void debug ()
{
using namespace std;
if (ColumnMajor)
cout << "Column-Major Matrix " << "(" << R << "," << C << ")" << " @ " << this << endl;
else
cout << "Row-Major Matrix " << "(" << R << "," << C << ")" << " @ " << this << endl;
cout << "Memory Offset: ";
for (unsigned i = 0; i < (R*C); i += 1)
cout << i << " ";
cout << endl;
cout << " Values: ";
for (unsigned i = 0; i < (R*C); i += 1)
cout << m_values[i] << " ";
cout << endl;
cout << "Standard Mathematical Notation:" << endl;
cout << " ";
for (unsigned c = 0; c < C; c += 1)
cout << "Col " << c << " ";
cout << endl;
for (unsigned r = 0; r < R; r += 1) {
cout << "Row " << r << " ";
for (unsigned c = 0; c < C; c += 1)
cout << at(r, c) << " ";
cout << endl;
}
cout << endl;
}
Matrix<ValueT, R, C, !ColumnMajor> transposeStorage () const
{
Matrix<ValueT, R, C, !ColumnMajor> result;
for (unsigned r = 0; r < R; r += 1)
for (unsigned c = 0; c < C; c += 1)
result.at(r, c) = at(r, c);
return result;
}
Matrix<ValueT, C, R, !ColumnMajor> transposeMatrix () const
{
Matrix<ValueT, C, R, !ColumnMajor> result;
memcpy(&result.at(0,0), m_values, sizeof(m_values));
return result;
}
};
int main (int argc, char * const argv[]) {
Matrix<float, 4, 2, false> rowMajorMatrix;
Matrix<float, 4, 2, true> columnMajorMatrix;
rowMajorMatrix.loadTestPattern();
rowMajorMatrix.debug();
columnMajorMatrix.loadTestPattern();
columnMajorMatrix.debug();
rowMajorMatrix = columnMajorMatrix.transposeStorage();
rowMajorMatrix.debug();
Matrix<float, 2, 4, false> transposedMatrix = columnMajorMatrix.transposeMatrix();
transposedMatrix.debug();
return 0;
}
Objective-C Header
//
// GHStatesEditor.h
// Goblin Hacker
//
// Created by Hermann Gundel on 18/01/08.
// Copyright 2008 Hermann Gundel. All rights reserved.
//
// This software was originally produced by Orion Transfer Ltd.
// Please see http://www.oriontransfer.co.nz for more details.
//
/*
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#import <Cocoa/Cocoa.h>
#import "GHEditorController.h"
@interface GHStatesEditor : GHEditorController {
IBOutlet NSTableView * statesTable;
}
@property(readonly) NSInteger blah;
+ (NSArray*) states;
- (NSInteger)numberOfRowsInTableView:(NSTableView *)tableView;
- (id)tableView:(NSTableView *)tableView objectValueForTableColumn:(NSTableColumn *)tableColumn row:(NSInteger)row;
- (void)tableView:(NSTableView *)tableView setObjectValue:(id)object forTableColumn:(NSTableColumn *)tableColumn row:(NSInteger)row;
- (unsigned char) cursed;
- (void) setCursed: (unsigned char)val;
- (NSString*) cursedState;
- (IBAction)bless: (id)sender;
- (IBAction)uncurse: (id)sender;
@end
Objective-C Implementation
//
// GHStatesEditor.m
// Goblin Hacker
//
//
#import "GHStatesEditor.h"
#import "GHSavedGameDocument+Character.h"
@implementation GHStatesEditor
+ (NSArray*) states
{
static NSArray * states = nil;
if (states == nil) {
NSString * statesPath = [[NSBundle mainBundle] pathForResource:@"states" ofType:@"plist"];
states = [[NSArray arrayWithContentsOfFile:statesPath] retain];
}
return states;
}
- (void) awakeFromNib {
// NSLog (@"Setting up states table... %@", [[self class] states]);
[statesTable setDataSource: self];
[statesTable reloadData];
}
- (NSInteger)numberOfRowsInTableView:(NSTableView *)tableView {
return [[[self class] states] count];
}
- (id)tableView:(NSTableView *)tableView objectValueForTableColumn:(NSTableColumn *)tableColumn row:(NSInteger)row {
NSDictionary *state = [[[self class] states] objectAtIndex:row];
if ([@"Value" isEqualTo:[tableColumn identifier]]) {
// offset is in the stat table for states
int offset = [[state valueForKey:@"Offset"] intValue];
// NSLog (@"Delivering value %@ for state %@", [NSNumber numberWithInt:[document characterStat:offset]],
// [state objectForKey:@"State"]);
return [NSNumber numberWithInt:[document characterStat:offset]];
} else {
// TODO: - use redColor for bad states (not sure if this is possible)
return [state objectForKey:@"State"];
}
}
- (void)tableView:(NSTableView *)tableView setObjectValue:(id)object forTableColumn:(NSTableColumn *)tableColumn
row:(NSInteger)row {
if ([@"Value" isEqualTo:[tableColumn identifier]]) {
// offset read from stat table
NSDictionary *state = [[[self class] states] objectAtIndex:row];
int val = [object intValue];
int offset = [[state valueForKey:@"Offset"] intValue];
// see if we have to set special "lighting flag"
if (([@"Cat's Eyes" isEqualTo:[state objectForKey:@"State"]]) && val) {
if ([document characterStat:54]) { // regard state of gravedigger's flame
[[document dataForIndex:27] setByteValue:12 atIndex:16];
//[document setByteValue:16 line:27 to:12];
} else {
//[document setByteValue:16 line:27 to:8];
[[document dataForIndex:27] setByteValue:8 atIndex:16];
}
}
if (([@"Gravedigger's Flame" isEqualTo:[state objectForKey:@"State"]]) && val) {
if ([document characterStat:52]) { // regard state of cat's eyes
//[document setByteValue:16 line:27 to:12];
[[document dataForIndex:27] setByteValue:12 atIndex:16];
} else {
//[document setByteValue:16 line:27 to:4];
[[document dataForIndex:27] setByteValue:4 atIndex:16];
}
}
[[[document undoManager] prepareWithInvocationTarget:tableView] reloadData];
[document setCharacterStat:offset to:val];
}
}
- (void)bless: (id)sender {
int c;
// just a quick hack, setting wanted states
// TODO: the states, that influence lighting, have to set some more info, probably line 27
// cat's eyes is a value of 8 on byte offset 16
// gravedigger is 4 > both on -> 12
// there are 5 interesting bytes starting byte offset 16 the next 4 bytes seem like float 0.62
// for cat's eyes and like float 0.92 for gravedigger's flame
c = [document characterStat:44]; // Air Shielded
[document setCharacterStat:44 to:1000+c];
c = [document characterStat:48]; // Enchanted Weapon
[document setCharacterStat:48 to:1000+c];
c = [document characterStat:52]; // Cat's Eyes
[document setCharacterStat:52 to:1000+c];
//[document setByteValue:16 line:27 to:8];
[[document dataForIndex:27] setByteValue:8 atIndex:16];
// do not switch on gravedigger, defies hide in shadows
// c = [document characterStat:54]; // Gravedigger's Flame
// [document setCharacterStat:54 to:1000+c];
c = [document characterStat:56]; // Blessed
[document setCharacterStat:56 to:1000+c];
c = [document characterStat:58]; // Haste
[document setCharacterStat:58 to:1000+c];
c = [document characterStat:60]; // Ogre Strength
[document setCharacterStat:60 to:1000+c];
c = [document characterStat:62]; // Invisible
[document setCharacterStat:62 to:1000+c];
c = [document characterStat:64]; // Leatherskin
[document setCharacterStat:64 to:1000+c];
c = [document characterStat:66]; // Nimbleness
[document setCharacterStat:66 to:1000+c];
c = [document characterStat:70]; // Reveal Map
[document setCharacterStat:70 to:1000+c];
c = [document characterStat:72]; // Stoneskin
[document setCharacterStat:72 to:1000+c];
c = [document characterStat:74]; // Keensight
[document setCharacterStat:74 to:1000+c];
c = [document characterStat:80]; // Enkindled Weapon
[document setCharacterStat:80 to:1000+c];
c = [document characterStat:82]; // Elemental Armor
[document setCharacterStat:82 to:1000+c];
c = [document characterStat:84]; // Chameleon
[document setCharacterStat:84 to:1000+c];
c = [document characterStat:86]; // Predator Sight
[document setCharacterStat:86 to:1000+c];
c = [document characterStat:90]; // Mana-Fortified
[document setCharacterStat:90 to:1000+c];
c = [document characterStat:92]; // Greater Protection
[document setCharacterStat:92 to:1000+c];
[statesTable reloadData];
}
- (void)uncurse: (id)sender {
// Curse and disease are in a 1-byte value lineOffset 27, byteOffset 41
// values: curse:128, fleshrot:64, insanity fever:32, blister pox:16,
// eye fungus:8, rusty knuckles:4, dungeon fever:2
[self setCursed:0];
//[self cursedState];
// just a quick hack, resetting unwanted states
[document setCharacterStat:42 to:0]; // Stunned
[document setCharacterStat:46 to:0]; // Poisoned
[document setCharacterStat:50 to:0]; // Entangled
[document setCharacterStat:68 to:0]; // Charmed
[document setCharacterStat:76 to:0]; // Paralyzed
[document setCharacterStat:78 to:0]; // Scared
[document setCharacterStat:88 to:0]; // Off-Balance
[statesTable reloadData];
}
- (unsigned char) cursed {
return [[document dataForIndex:27] byteValueAtIndex:41];
}
- (void) setCursed: (unsigned char)val {
[[document dataForIndex:27] setByteValue:val atIndex:41];
}
- (NSString*) cursedState {
unsigned char cursed = [self cursed];
if (cursed == 0) return @"";
if (cursed == 128) return @"Cursed";
if (cursed < 128) return @"Diseased";
else return @"Cursed+Diseased";
}
+ (void)initialize {
[self setKeys:[NSArray arrayWithObject:@"cursed"] triggerChangeNotificationsForDependentKey:@"cursedState"];
}
@end