1 | program DBCExport;
|
---|
2 |
|
---|
3 | {$mode Delphi}{$H+}
|
---|
4 |
|
---|
5 | uses
|
---|
6 | {$IFDEF UNIX}{$IFDEF UseCThreads}
|
---|
7 | cthreads,
|
---|
8 | {$ENDIF}{$ENDIF}
|
---|
9 | Classes, SysUtils, CustApp,
|
---|
10 | USqlDatabase, UDBC, Variants;
|
---|
11 |
|
---|
12 | type
|
---|
13 |
|
---|
14 | { TDBCExport }
|
---|
15 | TDBCExport = class(TCustomApplication)
|
---|
16 | private
|
---|
17 | procedure ParseParameters;
|
---|
18 | protected
|
---|
19 | procedure DoRun; override;
|
---|
20 | public
|
---|
21 | DBC: TDBC;
|
---|
22 | Database: TSqlDatabase;
|
---|
23 | DBCFileName: string;
|
---|
24 | NewDBCFileName: string;
|
---|
25 | ColumnTypeDefinition: string;
|
---|
26 | LastIndexStringColumns: integer;
|
---|
27 | IndexTable: array of integer;
|
---|
28 | SQLquery: string;
|
---|
29 | DisplayData: Boolean;
|
---|
30 | constructor Create(TheOwner: TComponent); override;
|
---|
31 | destructor Destroy; override;
|
---|
32 | procedure WriteHelp; virtual;
|
---|
33 | procedure ShowDBC;
|
---|
34 | procedure LoadDBC;
|
---|
35 | procedure SaveDBC;
|
---|
36 | procedure ReplaceText;
|
---|
37 | procedure CreateIndexTable(var DbRows: TDbRows);
|
---|
38 | function GetIDbyEntry(Entry: Integer; var DBRows: TDBRows): Integer;
|
---|
39 | end;
|
---|
40 |
|
---|
41 | { TDBCExport }
|
---|
42 |
|
---|
43 | procedure TDBCExport.ParseParameters;
|
---|
44 | begin
|
---|
45 | if HasOption('h', 'help') then begin
|
---|
46 | WriteHelp;
|
---|
47 | Halt;
|
---|
48 | end;
|
---|
49 | if HasOption('f', 'file') then begin
|
---|
50 | DBCFileName := GetOptionValue('f', 'file');
|
---|
51 | NewDBCFileName := Copy(DBCFileName, 1, Length(DBCFileName) -
|
---|
52 | Length(ExtractFileExt(DBCFileName))) + '-2.dbc';
|
---|
53 | end else begin
|
---|
54 | WriteLn('Source DBC file not specified.');
|
---|
55 | Halt;
|
---|
56 | end;
|
---|
57 | if HasOption('n', 'newfile') then begin
|
---|
58 | NewDBCFileName := GetOptionValue('n', 'newfile');
|
---|
59 | end;
|
---|
60 | if HasOption('c', 'coltypedef') then begin
|
---|
61 | ColumnTypeDefinition := GetOptionValue('c', 'coltypedef');
|
---|
62 | end;
|
---|
63 | if HasOption('d', 'display') then begin
|
---|
64 | DisplayData := True;
|
---|
65 | end;
|
---|
66 |
|
---|
67 | if HasOption('s', 'schema') then begin
|
---|
68 | Database.Database := GetOptionValue('s', 'schema');
|
---|
69 | end else Database.Database := 'wowpreklad';
|
---|
70 | if HasOption('u', 'user') then begin
|
---|
71 | Database.UserName := GetOptionValue('u', 'user');
|
---|
72 | end else Database.UserName := 'root';
|
---|
73 | if HasOption('p', 'password') then begin
|
---|
74 | Database.Password := GetOptionValue('p', 'password');
|
---|
75 | end else Database.Password := '';
|
---|
76 | if HasOption('t', 'host') then begin
|
---|
77 | Database.Hostname := GetOptionValue('t', 'host');
|
---|
78 | end else Database.Hostname := 'localhost';
|
---|
79 | if HasOption('a', 'Charset') then begin
|
---|
80 | Database.Encoding := GetOptionValue('a', 'Charset');
|
---|
81 | end else Database.Encoding := 'utf8';
|
---|
82 | if HasOption('q', 'sql_query') then begin
|
---|
83 | SQLquery := GetOptionValue('q', 'sql_query');
|
---|
84 | SQLquery := StringReplace(SQLquery, '\ ', ' ', [rfReplaceAll]);
|
---|
85 | SQLquery := StringReplace(SQLquery, '\`', '`', [rfReplaceAll]);
|
---|
86 | WriteLn(SQLquery);
|
---|
87 | end;
|
---|
88 | end;
|
---|
89 |
|
---|
90 | procedure TDBCExport.DoRun;
|
---|
91 | begin
|
---|
92 | ParseParameters;
|
---|
93 | LoadDBC;
|
---|
94 | ShowDBC;
|
---|
95 | ReplaceText;
|
---|
96 | SaveDBC;
|
---|
97 | Terminate; // Stop program loop
|
---|
98 | end;
|
---|
99 |
|
---|
100 | constructor TDBCExport.Create(TheOwner: TComponent);
|
---|
101 | begin
|
---|
102 | inherited Create(TheOwner);
|
---|
103 | StopOnException := True;
|
---|
104 | Database := TSqlDatabase.Create;
|
---|
105 | end;
|
---|
106 |
|
---|
107 | destructor TDBCExport.Destroy;
|
---|
108 | begin
|
---|
109 | Database.Destroy;
|
---|
110 | inherited Destroy;
|
---|
111 | end;
|
---|
112 |
|
---|
113 | procedure TDBCExport.WriteHelp;
|
---|
114 | begin
|
---|
115 | WriteLn('Usage: ', ExtractFileName(ExeName), ' [options]');
|
---|
116 | WriteLn(' -h --help Show this help');
|
---|
117 | WriteLn(' -u --user Database user name, default root');
|
---|
118 | WriteLn(' -p --password Database password name');
|
---|
119 | WriteLn(' -s --schema Database schema name, default wowpreklad');
|
---|
120 | WriteLn(' -t --host Database host name, default localhost');
|
---|
121 | WriteLn(' -a --Charset Database Charset, default utf8');
|
---|
122 | WriteLn(' -f --file Source DBC file name');
|
---|
123 | WriteLn(' -n --newfile New created DBC file name');
|
---|
124 | WriteLn(' -c --coltypedef DBC column type definition string (usage index1:type1, index2:type2,...)');
|
---|
125 | WriteLn(' where 0 - uint32, 1 - sint32, 2 - float, 3 - string, 4 - byte)');
|
---|
126 | WriteLn(' -d --display Display DBC data');
|
---|
127 | WriteLn(' -q --sql_query SQL select when entry is ID first column in dbc file and text1,text2... is texts columns');
|
---|
128 | // SELECT T.entry as entry,T.Text as text1 FROM (SELECT * FROM gametips WHERE (Complete = 1) AND ((Language = 1)) AND (User IN (459,670,602,462,1,400,638,592,624,610,769,331,131,704,2,499,641,660,578,337,304,277,208,613,768,754,590,606,26,618,739,503,601,607,585,596,765,320,547,687)) AND VersionStart <= 9947 AND VersionEnd >= 9947) AS T GROUP BY T.entry
|
---|
129 | end;
|
---|
130 |
|
---|
131 | procedure TDBCExport.ShowDBC;
|
---|
132 | var
|
---|
133 | X, Y: Integer;
|
---|
134 | Text: string;
|
---|
135 | begin
|
---|
136 | with DBC do begin
|
---|
137 | // Display DBC data
|
---|
138 | if DisplayData then
|
---|
139 | for Y := 0 to Length(Cells) - 1 do begin
|
---|
140 | Text := '';
|
---|
141 | for X := 0 to Length(Cells[Y]) - 1 do
|
---|
142 | if VarIsStr(Cells[Y, X]) then Text := Text + '"' + Cells[Y, X] + '", '
|
---|
143 | else Text := Text + IntToStr(Cells[Y, X]) + ', ';
|
---|
144 | WriteLn(Text);
|
---|
145 | end;
|
---|
146 | end;
|
---|
147 | end;
|
---|
148 |
|
---|
149 | procedure TDBCExport.LoadDBC;
|
---|
150 | var
|
---|
151 | I: Integer;
|
---|
152 | begin
|
---|
153 | DBC := TDBC.Create;
|
---|
154 | with DBC do begin
|
---|
155 | if FileExists(DBCFileName) then begin
|
---|
156 | LoadFromFile(DBCFileName);
|
---|
157 |
|
---|
158 | // Load strings for string columns
|
---|
159 | for I := 1 to Length(ColumnTypeDefinition) do
|
---|
160 | if ColumnTypeDefinition[I] = 's' then begin
|
---|
161 | LoadColumnStrings(I - 1);
|
---|
162 | LastIndexStringColumns := I;
|
---|
163 | end;
|
---|
164 | end else WriteLn('File ' + DBCFileName + ' not exists.');
|
---|
165 | end;
|
---|
166 | end;
|
---|
167 |
|
---|
168 | procedure TDBCExport.SaveDBC;
|
---|
169 | begin
|
---|
170 | with DBC do begin
|
---|
171 | if FileExists(DBCFileName) then
|
---|
172 | if not DirectoryExists(ExtractFileDir(NewDBCFileName)) then
|
---|
173 | mkdir(ExtractFileDir(NewDBCFileName));
|
---|
174 | SaveToFile(NewDBCFileName);
|
---|
175 | Free;
|
---|
176 | end;
|
---|
177 | end;
|
---|
178 |
|
---|
179 | // Function get data from database and replace text in DBC
|
---|
180 | procedure TDBCExport.ReplaceText;
|
---|
181 | var
|
---|
182 | DBRows : TDbRows;
|
---|
183 | Text: string;
|
---|
184 | X, Y, I, Entry: Integer;
|
---|
185 | IndexRowData: Integer;
|
---|
186 | begin
|
---|
187 | with DBC do begin
|
---|
188 | if (SQLquery <> '') then begin
|
---|
189 | Database.Connect;
|
---|
190 | DBRows := Database.Query(SQLquery);
|
---|
191 |
|
---|
192 | CreateIndexTable(DBRows);
|
---|
193 |
|
---|
194 | for Y := 0 to Length(DBC.Cells) - 1 do begin
|
---|
195 | Entry := Cells[Y, 0];
|
---|
196 | if (Length(IndexTable) > Entry) then
|
---|
197 | IndexRowData := IndexTable[entry]
|
---|
198 | else IndexRowData := 0;
|
---|
199 |
|
---|
200 | I := 1;
|
---|
201 | if (IndexRowData <> 0) then begin
|
---|
202 | for X := 1 to Length(ColumnTypeDefinition) do begin
|
---|
203 | if ColumnTypeDefinition[X] = 's' then begin
|
---|
204 | Text := DBRows.Data[IndexRowData - 1].Values['Text' + IntToStr(I)];
|
---|
205 | SetString(Y, X - 1, Text);
|
---|
206 | I := I + 1;
|
---|
207 | if (LastIndexStringColumns = X) then Break;
|
---|
208 | end;
|
---|
209 | end;
|
---|
210 | end;
|
---|
211 | end;
|
---|
212 | DBRows.Destroy;
|
---|
213 | end;
|
---|
214 | end;
|
---|
215 | end;
|
---|
216 |
|
---|
217 | // Create table index = entry, value = Index-1 DBRows, notfound = 0
|
---|
218 | procedure TDBCExport.CreateIndexTable(var DbRows: TDbRows);
|
---|
219 | var
|
---|
220 | I: Integer;
|
---|
221 | Count, Entry: Integer;
|
---|
222 | begin
|
---|
223 | try
|
---|
224 | Count := DBRows.Count;
|
---|
225 | for I := 1 to Count do begin
|
---|
226 | Entry := StrToInt(DBRows.Data[I - 1].Values['Entry']);
|
---|
227 |
|
---|
228 | if (I = 127) then SetLength(IndexTable, Entry + 1);
|
---|
229 |
|
---|
230 | if (Length(IndexTable) - 1 < Entry) then
|
---|
231 | SetLength(IndexTable, Entry + 1);
|
---|
232 |
|
---|
233 | IndexTable[Entry] := I;
|
---|
234 | end;
|
---|
235 | except
|
---|
236 | end;
|
---|
237 | end;
|
---|
238 |
|
---|
239 | function TDBCExport.GetIDbyEntry(Entry: Integer; var DBRows: TDBRows): Integer;
|
---|
240 | var
|
---|
241 | I: Integer;
|
---|
242 | begin
|
---|
243 | try
|
---|
244 | for I := 0 to DBRows.Count - 1 do begin
|
---|
245 | if (StrToInt(DBRows.Data[i].Values['Entry']) = Entry) then begin
|
---|
246 | Result := I;
|
---|
247 | Exit;
|
---|
248 | end;
|
---|
249 | end;
|
---|
250 | except
|
---|
251 | end;
|
---|
252 | Result := -1;
|
---|
253 | end;
|
---|
254 |
|
---|
255 | var
|
---|
256 | Application: TDBCExport;
|
---|
257 |
|
---|
258 | {$IFDEF WINDOWS}{$R DBCExport.rc}{$ENDIF}
|
---|
259 |
|
---|
260 | {$R DBCExport.res}
|
---|
261 |
|
---|
262 | begin
|
---|
263 | Application := TDBCExport.Create(nil);
|
---|
264 | Application.Run;
|
---|
265 | Application.Free;
|
---|
266 | end.
|
---|
267 |
|
---|