Some newb questions

P.S. Please create new forum topics for unrelated questions :slight_smile: This thread is getting long and we talk about multiple things at the same time :slight_smile:

even when implementation uses things only in the scope of implementation section.

Well, this means that behind the hood FPC publishes ALL the symbols in implementation section to the linker, so those variable were not actually private to the unit. I am not sure that would be a good design itself. There probably can be leakers and hacks, mnaybe using RTTI or OS structures, to hook into “private” things.

Unrelated example is Delphi BPLs, conceived in times where SuperObject was a trendy pattern and years before “keep everything private until absolutely needed to make them public” became a trend for the sake of program management and avoiding spaghetti. And for all my love to BPLs and hate of FPC lacking BPLs… I was bitten myself when programs modules started using “implementation details” they should never have, because it was not possible ot hide them using BPLs, like declaring some units to be BPL-private…

I found one more instance of it

Actually, so did i, if you looked into the patch :slight_smile:

I don’t understand how it compiled

I have a speculation, because of that error message talking bad abuut relative paths.
I speculate FPc has the include files cache like TDictionary<TFilePath, TBytes> and uses verbatim path as a key, without converting it to absolute or to project-root-relative first.

So if there is some unit in the project, that correctly references those include files by the same relative path, and that units are compiled before the erratic ones, then the cache is alreayd warmed up and actual loading does not happen and error is not triggered.

Just speculation, planned to make few simplistic Laz projects to verify it, but did not had time yet.

Please create new forum topics for unrelated questions

Always right to say, and often hard to do. This is really a “road notes” of a newb trying to get his mind over Castle Engine. I really can not predict all the topics this journey can spawn, and if such a subtopic would turn a one-liner or a complex conversation in its own right…

It can easily devolve into the opposite problem, dozens of separate threads, each being oneliner :frowning:

I can only wish this was a tree-like forum not flat one…

on generics/inlines

it is intermediate code, neither source pascal code, nor CPU code

It is indeed possible with program-wide compilation (into CPU code) like it is de facto done in Java. .Net and other JIT-VMs.
Or when the project is compiled into a single monolite .exe

Now, remembering that FPC can not into BPLs… well, perhaps i was overgeneralizing.

But look back into Delphi.

  1. The goal of TurboPascal still shared by “native” Delphi compiler was to be very fast. FPC shares that being one-pass compiler.
  2. You can not store inlines/generics as source code in PPUs (DCUs and DCPs in Delphi), as they would be affected by compiler options, like $A1, $A2… - that dirty ABI is not same as API problem.
  3. Neither you can have all-finished x86 code

So, consider all that from a DCP/BPL perspective. Actually, two BPLs one using another.
Inline function has to be kept in DCU/DCP as intermediate code, referencing non-public symbol of DLL(BPL).
You have to either fake privateness and publish that private variable as DLL public symbol, or you can not compile inline function outside of its declaring BPL

Now, making few steps back, what about global properties again? they can not be backed by the variable sadly, but can they be backed by an inlined getter function ? :slight_smile:

I wonder if FPC has the same setup for float co-processor (80x87) as Delphi or different.

What makes me alert is this line from Delphi:

function CreateWindowExW(.....
var
  FPUCW: Word;
begin
  FPUCW := Get8087CW;
  Result := _CreateWindowExW(....
  Set8087CW(FPUCW);
end;

I speculate they had some problems with MMX-powered 32-bit x86 processors.

https://castle-engine.io/manual_lazarus_control.php

This article has some talk about Castle’s forms vs LCL forms. But there is a related topic, that seems not covered at all: Castle’s TCastleApplication vs LCL’s TApplication.

Obviously, for a project only using LCL Forms it would be natural to also use LCL Applicaiton and same common sense for astle-Forms-only app.

But for an application that mixes both LCL Forms and CastleBaseForm - which would be cons and pros of choosing either application class?

P.S. One more thing for me to investigate is whether there is a natural idiomatic way to set Z-Order beteeen LCL and Castle windows.

P.P.S. Lazarus demo error (obsolete path)

D:\DelphiProjects\Libs\Games\castle-engine\examples\lazarus\load_model_and_camera_manually\mainf.pas

Should be

  Scene.Load('../../3d_rendering_processing/multiple_viewports/data/bridge_level/bridge_final.x3dv');

Such mixed approach is not allowed. Neither LCL (in which our TCastleControl works) nor TCastleWindow are prepared to handle the situation that they only handle some application forms, and other library handles other forms. That would be technically quite difficult (although possible in theory, but one/both of LCL would need to expose proper hooks), as native OS / GUI libraries don’t help with this ---- they have some process-central resources, an event loop specific to a process etc.

So you use CGE Application from CastleWindow unit if you use TCastleWindowBase for your window(s).

Or you use LCL Application from LCL Forms if you use LCL form, with TCastleControlBase.

You cannot do both.

That is also why we have separate packages castle_window.lpk (for the former) and castle_components.lpk (a betterr name would be castle_lcl.lpk) for the latter. You should not use both of these packages at the same time.

This should be documented clearly on Engine on a form (VCL, FMX, LCL) using TCastleControl | Manual | Castle Game Engine , adding this to TODO.

Thanks, fixed.

I copied the data to example and refer to it by castle-data:/bridge_level/bridge_final.x3dv, this is my approach for new programs. It makes more natural example to users (self-contained), and it avoids breaking these paths by rearranging unrelated examples. It increases CGE download size a bit, but the gains are worth it.

P.S. Please create new topics for new questions. We do not want to have a never-ending thread “Some newb questions” with multiple unrelated questions – this makes it hard to follow / learn to others.

Such mixed approach is not allowed.

Thanks for clarifying. Guess that better be explicitly spelled somewhere there.

Please create new topics for new questions

this makes it hard to follow / learn to others

Mmmm… would it really be better? Those are really one-timers.
Learn from it ? Like learning from git commit history…

I reported an obsolete line, you fixed it, case closed and no one would ever need it again.
I asked a question lacking from docs, you update that in docs, no one would ever need this thread for it again.

To spend a separate forum thread on it? Or issue number in tracker?
All options are evil, jsut which one is lesser evil then?
Both seems too much for such a miniscule issue. It is just do and forget.

Frankly, was thinking just about e-mail, but don’t know one :slight_smile:

bc i kind of found one more overlooked example :slight_smile:
i can land it into a tracker, but then “everyone subscribed to tracker would get notified”, right?

And there probably would be more obsolete examples found as i am “testing water” when have time.
Should every of them warrant a separate forum thread? A separate tracker issue? They all would be trivial fix-and-forget kind!

Trivial fixes can indeed be submitted as new GitHub issue instead of new forum thread. As you did

– this is the way to go. Yes, we want many threads or many GitHub issues. It is always better than one long thread when it is hard to follow what needs to be done after some time.

And you never know when an issue is trivial, and when it explodes into something more difficult and needed discussion :slight_smile: Having that contained in a separate forum thread or GitHub issue “makes room” for such conversation, without worry that they are hard to follow (when multiple topics are mixed in a single thread/issue).

That is OK. When you have a useful issue, useful question, useful whatever – go ahead and post about it. If you have 20 good questions, make 20 good forum threads or GitHub issues. I can only applaud in such case. Useful things are not a “noise”, they are what we want (and people who subscribe to repo or forum want to hear about them).

To put this in context, your note probably comes from my answer in [Docking editor] Sometimes blank windows remain, after closing the project · Issue #348 · castle-engine/castle-engine · GitHub , when I asked you to not report progress this way. This was when you made 16 GitHub comments in 4 hours and they were not really useful, you reported “live” your debugging session. In such case, writing a good summary in much better (and easier to follow) than a lot of small comments, some of which only you really understood, some of them just talked about LCL or ranted about how something is uncomfortable in LCL/Lazarus debugger.