TField.Clear does not work on a DateTime field, like it does for say an integer field.
So how do I set the field to null?
I'm using Delphi 2010.
Currently I do this;
IBDataset1.FieldByName('EUL_START_DATE').Clear;
However the field does not get set to null, it still contains a date value.
I think this explains it, but i don't want to go messing with core delphi files.
http://qc.embarcadero.com/wc/qcmain.aspx?d=78920
What if i need to reinstall Rad Studio. I would have to remember all these little patches.
In the unit IBCustomDataset from line 3480 comment out the following lines;
//if TIBStringField(Field).EmptyAsNull then
// rdFields[FMappedFieldPosition[Field.FieldNo - 1]].fdIsNull := True
//else
//begin
// rdFields[FMappedFieldPosition[Field.FieldNo - 1]].fdDataLength := 0;
// rdFields[FMappedFieldPosition[Field.FieldNo - 1]].fdIsNull := False;
//end
and add in the following lines;
//NewCode IbCustomDataSet.pas Line 3480
begin
if (Field is TIBStringField) and
(not TIBStringField(Field).EmptyAsNull) then
begin
rdFields[FMappedFieldPosition[Field.FieldNo - 1]].fdDataLength := 0;
rdFields[FMappedFieldPosition[Field.FieldNo - 1]].fdIsNull := False;
end
else
rdFields[FMappedFieldPosition[Field.FieldNo - 1]].fdIsNull := True;
end
//End New Code
solution found here;
http://qc.embarcadero.com/wc/qcmain.aspx?d=78920
Tested, seem to work ok.
Just remember to make a note if you need to reinstall rad studio, this patch will need to be re-applied.
Related
I am trying to extract the Name of a person out of my database, containing two tables, with only having the ID (primary key).
I am struggling to come up with a solution, although I do have notes that I've written and the logic seems to check out (to me at least).
if P1Score > P2Score
then winner := P1ID
else winner := P2ID
winner in tblGames = the ID of winner in tblPlayers
WinnerName := first name of Winner + surname of Winner in tblPlayers
So this is my logic, obviously it's missing a lot, but I can't seem to expand on it much more
I have the ID of the person from tblGames, but now I'm struggling to understand how to use that ID to extract the Name and Surname from my tblPlayers and assign it to a variable, so I can put it into the Winner Column of tblGames.
I have tried a few things using my own thought process, but I do not know enough about Delphi and databases to actually implement it correctly.
BEGIN
if (StrToInt(P1_score) - StrToInt(P2_score) = 0) then
Draw := True
else
Draw:= False;
if StrtoInt(P1_Score) > StrToInt(P2_Score) then
winnerID := P1_ID
else
winnerID := P2_ID;
with dmTournament do
begin
tblGames.Insert;
tblGames['Player1_Id'] := StrToInt(P1_ID);
tblGames['Player2_ID'] := StrToInt(P2_ID);
tblGames['Player1_score'] := StrToInt(P1_Score);
tblGames['Player2_Score'] := StrToInt(P2_Score);
tblGames['Draw'] := Draw;
tblGames['Winner'] := WinnerName; //How do I get WinnerName(?)
tblGames.Post;
end;
END;
You don't need to do a lot of code. You can let MySQL engine do job for you. Execute the following quires in same order they appeared. This will update the table data as you want.
/* 1: Set all games to draw */
UPDATE Games SET draw = true;
/* 2: Update when Player1 is winner :*/
UPDATE Games, Players SET
Games.draw = false,
Games.winner = CONCAT(Players.first_name, ' ', Players.last_name)
WHERE
(Games.player1_score > Games.player2_score) AND (Games.player1_id=Players.ID);
/* 3: Update when Player2 is winner */
UPDATE Games, Players SET
Games.draw = false,
Games.winner = CONCAT(Players.first_name, ' ', Players.last_name)
WHERE
(Games.player2_score > Games.player1_score) AND (Games.player2_id=Players.ID);
Please help me to translate the code. I don't know C++ well, but I know Delphi syntax well. I want to translate code from MSDN:
Step 6. Add Support for COM.
static WCHAR g_wszName[] = L"My RLE Encoder";
CFactoryTemplate g_Templates[] =
{
{
g_wszName,
&CLSID_RLEFilter,
CRleFilter::CreateInstance,
NULL,
NULL
}
};
and
int g_cTemplates = sizeof(g_Templates) / sizeof(g_Templates[0]);
I realized that the first line is a variable. But when translated, it does not work. Error:
This is a string and you defined it as WCHAR.
Next comes the description of the structure, but I do not know such a form.
The last line is also a variable, but it has a / and two values.
In general, I kind of understood the meaning, but do not understand how to write it.
The code roughly translates to Delphi as follows:
const
g_wszName: PWideChar = 'My RLE Encoder';
var
g_Templates: array[0..0] of CFactoryTemplate;
...
g_Templates[0].m_Name := g_wszName;
g_Templates[0].m_ClsID := #CLSID_RLEFilter;
g_Templates[0].m_lpfnNew := #CRleFilter.CreateInstance;
g_Templates[0].m_lpfnInit := nil;
g_Templates[0].m_pAMovieSetup_Filter := nil;
and
var
g_cTemplates: Integer;
...
//g_cTemplates := SizeOf(g_Templates) div SizeOf(g_Templates[0]);
g_cTemplates := Length(g_Templates);
Am working an a small app in Delphi7 but am puzzles on how to use a combination of 3 check boxes
Example: if check.box1 and checkbox2 checked run system application with these prefs
or if checkbox1 only checked run system application with these prefs or if checkbox2 only checked run with these prefs
It sounds like you're having trouble getting started writing what you need, which is basically a series of if..then..else flow-control statements based on compound boolean expressions. You probably want a structure like the one below. I'm not going to show you the entire thing, because it's best for you to work it out for yourself, but this should give you the idea:
if (CheckBox1.Checked) and (CheckBox2.Checked) and not (CheckBox3.Checked) then
begin
// do one thing
end
else
begin
if (CheckBox1.Checked) and not (CheckBox2.Checked) and not (CheckBox3.Checked) then
begin
// do another thing
end
else
// etc
end;
If you're familiar with enumerated types, you might do better to declare one and use that to derive the selected preferences and then act upon them. The point of doing that is twofold: to increase the clarity of your code (at the expense of your code being longer, of course); and to separate the logic for calculating which preference the user has selected from the code which acts upon it.
Something like
type
TRunPreference = (rpNone, rpOne, rpTwo, rpThree, rpFour,
rpFive, rpSix, rpSeven, rpEight);
// rpOne..rpEight are for the 8 permutations of three booleans
// and the rpNone is to provide for initialising the variable
// with something which isn't one of the desired values
var
RunPreference : TRunPreference;
procedure TForm1.Button1Click(Sender: TObject);
begin
RunPreference := rpNone;
if (CheckBox1.Checked) and (CheckBox2.Checked) and not (CheckBox3.Checked) then
begin
RunPreference := rpOne;
end
else
begin
if (CheckBox1.Checked) and not (CheckBox2.Checked) and not (CheckBox3.Checked) then
begin
RunPreference := rpTwo;
end
else
; //
end;
case RunPreference of
rpNone :
; // do nothing
rpOne :
begin
// Act on rpOne
end;
rpTwo :
begin
// Act on rpTwo
end;
// etc
end; { Case of RunPreference }
end;
Inspired by MartynA's solution, and because I prefer compact code, here's how I would do it:
// For the three (sets of?) preferences, define bit values, and
// a variable to hold the combination of the selected preferences:
const
PrefA=1; PrefB=2; PrefC=4;
var
prefs: byte;
procedure TForm12.Button2Click(Sender: TObject);
begin
// whether a preference should be active or not becomes a simple `OR` function
// based on each checkbox's state
prefs := 0;
if CheckBox1.Checked then prefs := prefs or PrefA;
if CheckBox2.Checked then prefs := prefs or PrefB;
if CheckBox3.Checked then prefs := prefs or PrefC;
// then use a `case` statement to run according the preference combination
// The values like `PrefA or PrefC` can be used instead of numeric values,
// since they can be resolved at compile time.
// Whether they improve readability or not is ... (disputable)
case prefs of
0:
ShowMessage('Running without preferences');
PrefA:
ShowMessage('Running with PrefA alone');
PrefB:
ShowMessage('Running with PrefB alone');
PrefA or PrefB:
ShowMessage('Running with PrefA and PrefB');
PrefC:
ShowMessage('Running with PrefC alone');
PrefA or PrefC:
ShowMessage('Running with PrefA and PrefC');
PrefB or PrefC:
ShowMessage('Running with PrefB and PrefC');
PrefA or PrefB or PrefC:
ShowMessage('Running with PrefA and PrefB and PrefC');
end;
end;
If you need to check in your code whether a preference is active or not, you can do it like:
if (prefs and PrefB) then
// do whatever requires PrefB to be selected
I am using insertion sort to sort a stringlist (EmailingListArray below).
EmailingListArray[1] is an array that contains names.
EmailingListArray[2] contains corresponding emails.
I am sorting EmailingListArray[1] and when something changes within it, it also changes the second array, so they are sorted together.
An awkward way of doing things, I know, but it's for coursework and I wanted to put an insertion sort in somewhere to try get an extra mark :L
Here's my code
//quick check to make sure array contains correct values
for first := 0 to EmailingListArray[1].Count do
ShowMessage(EmailingListArray[1][first]);
//then sort
First := 0;
Last := EmailingListArray[1].Count;
for CurrentPointer := First +1 to Last-1 do
begin
CurrentValue := EmailingListArray[1][CurrentPointer];
CurrentValue2 := EmailingListArray[2][CurrentPointer];
Pointer := CurrentPointer + 1;
while ((EmailingListArray[1][Pointer] > CurrentValue) AND (Pointer > 0)) do
begin
EmailingListArray[1][Pointer+1] := EmailingListArray[1][Pointer];
EmailingListArray[2][Pointer+1] := EmailingListArray[2][Pointer];
pointer := Pointer -1;
end;
EmailingListArray[1][Pointer + 1] := CurrentValue;
EmailingListArray[2][Pointer + 1] := CurrentValue;
end;
//show message at the end for a check
ShowMessage('hello?');
The message "hello?" isn't being displayed for some reason :S.
The program isn't crashing or anything so it really should atleast display "hello?" at the end.
It isn't sorting my arrays either.
Neither am I sure if the algorithm is written correctly, I got it out of our textbook.
Any help would be much appreciated!
If you want to get a good mark:
Avoid giving misleading names for your variables:
CurrentPointer should be called CurrentIndex or CurrentPosition as it is an index and not a Pointer
Pointer is to be avoided (reserved for Pointer type) and more so because it is not a Pointer; should be WorkIndex or WorkPosition
Read the Insertion sort algorithm (wikipedia has a simple pseudocode for array indexed from 0) and implement it properly:
WorkIndex := CurrentIndex - 1; // - not + in your "Pointer := CurrentPointer + 1;"
Get your Index range from 0 to Count-1 for a TStrings.
Don't mix up the 2 arrays:
EmailingListArray[2][WorkIndex + 1] := CurrentValue2; // not CurrentValue
Update: Missed the bad while condition for zero based array.
2bis. While condition should be with >=0, not >0
while ((EmailingListArray[1][WorkIndex] > CurrentValue) AND (WorkIndex >= 0)) do
I want to enable Lua-Scripting (Lua 5.1) in my Delphi application. For this purpose I use the header Files of Thomas Lavergne.
Now I try to register a userdata type following this example: http://www.lua.org/pil/28.2.html
At the "new array function" it uses the command *luaL_getmetatable*.
static int newarray (lua_State *L) {
int n = luaL_checkint(L, 1);
size_t nbytes = sizeof(NumArray) + (n - 1)*sizeof(double);
NumArray *a = (NumArray *)lua_newuserdata(L, nbytes);
luaL_getmetatable(L, "LuaBook.array");
lua_setmetatable(L, -2);
a->size = n;
return 1; /* new userdatum is already on the stack */
}
Unfortunately the *luaL_getmetatable* Function is marked al old at my header File and commented out. I tried to activate it again but as expected I will get an error because the dll entrancepoint couldn't be found.
This is the Delphi-translation of that example (using another non array datatype)
Type
tMyType = tWhatever;
pMyType = ^tMyType;
{...}
Function newusertype(aState : pLua_State) : LongInt; cdecl;
Var
NewData : pMyType;
Begin
Result := 0;
NewData := lua_newuserdata(aState, SizeOf(tMyType ));
NewData^ := GetInitValue;
luaL_getMetaTable(aState, 'myexcample.mytype'); // Error/unknown function
lua_setmetatable(aState, -2);
Result := 1;
End;
Now I'm looking for an replacement of luaL_getMetaTable. I haven't found any information about one. In fact I haven't found any information that luaL_getMetaTable is outdated but it seems to be :(.
use lua_newmetatable(aState, 'myexample.mytype'). The thing is (if you only want to continue if the metatable already exists) you'll need to evaluate whether it returns a 0! If it returns 0, then it's wanting to create the metatable... in which case you can lua_pop(aState, 1).
Just remember that lua_newmetatable is a function returning an Integer (which in reality should be a Boolean).
Otherwise you can wait a few weeks for me to release Lua4Delphi version 2, which makes all of this super easy (and the Professional version actually automates the registration of Delphi Types and Instances with Lua)