401 Востаннє редагувалося ProgramBandera (22.11.2021 16:35:36)

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

tchort написав:

Те, до чого вона має відношення, є вами.

Не знаю як у вас пане, а у мене не все що має відношення до мене є мною! Як я люблю таких спеців в галузі інформатики як ви і пан 0xDADA11C7. Що капець! Кудись влізуть, якусь дурню напишуть і абсолютно нічого по темі.
Якщо пан 0xDADA11C7 назвав мене індусом (добре хоч не москалем, хоча на таких форумах я б ніколи не дозволив би собі такого) то нехай пояснить чому.

ProgramBandera := Індус;
CASE 'Причина' OF
  1: Файл ресурсу великий - стільки не можна туди запихати по причині ......
  2: Файл ресурсу неправильно скомпільований, потрібно скомпілювати ось так....
  3: Файл ресурсу не правильно розміщений в DLL, його потрібно розмістити .....
  4: Сама DLL неправильно скомпільована, так як.....
  5: При компілюванні ресурсу зкомпілювали неправильний тип ресурсу...
ELSE
  Я вам поясню як потрібно робити в правильному випадку...
END;

Ато заходите дурню пишите не по темі, а потім ще й пояснюєте всякі ремарки один за одного. Я не на форумі філософії, мені не потрібно пояснювати вашу точку зору, до якої національності хтось когось відносить.

Пан koala дав правильний напрямок по зневадження (дебаггінгу). Більш за все в мене не правильно скомпільований файл ресурсу. От йому дякую.

402

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Ви самі сказали причину:

Напевно причина у великому файлі ресурсу!

Ви знаєте, коли программа вилітає саме через розмір ресурсу, то це індусія однозначно - бо завантажувач виконуваних файлів в операційній системі таких обмежень не має. Якби ви сказали, що підозрюєте про ушкодженість структури ресурсів - з ким не буває - всі помиляються. Хоча, відверто кажучи, ресурси або компілюються або ні, я б не зміг уявити як можна за допомогою стандартних засобів розробки, а саме компілятора ресурсів, створити непрацюючий ресурс, максимум в чому може помилитися програміст - це в назві ресурсу, його типі, ідентифікаторі, змісті ресурсу, а от створити недійсну структуру ресурсу за допомогою стандартних засобів розробки практично неможливо.

403 Востаннє редагувалося ProgramBandera (22.11.2021 17:07:10)

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

0xDADA11C7 написав:

максимум в чому може помилитися програміст - це в назві ресурсу, його типі, ідентифікаторі, змісті ресурсу, а от створити недійсну структуру ресурсу за допомогою стандартних засобів розробки практично неможливо.

Дякую за уточнення! Тобто якщо ресурс зкомпільовано, то його розмір допустимий для використання в DLL? З того що я нагуглив більш за все я неправильно зкомпілював тип ресурсу. Але це не точно. Буду далі шукати.
Хоча ось цією процедурою він відтворювався чудово.

procedure TForm1.DefinitionTextPlay(ResourceName: String; Editor: TCustomMemo);
var
 Text: TResourceStream;
 Play: Boolean;
 Buffer: TRichEdit;
begin
 Buffer := Nil;
 Text := Nil;
 Play := True;                  
 try
  try
   Text := TResourceStream.Create(HInstance, 'T ' + ResourceName,
                                  RT_RCData);
  except
   on e: EResNotFound do               
   begin
    Play := False;                     
    Text := TResourceStream.Create(HInstance, 'T Визначення не знайдено!', RT_RCData); 
   end;
  end;
  Buffer := TRichEdit.Create(Editor); 
  Buffer.Parent := Editor;            
  Buffer.Visible := True;
  Buffer.Lines.LoadFromStream(Text);  
  Editor.Lines.Add(Buffer.Text);    
  Editor.Lines.Add('');               
 finally
  Buffer.Free;                        
  Text.Free;                         
 end;
 if (Zvuk.Checked = True) and (Play = True) then
  PlaySound(PChar('S ' + ResourceName), 0, SND_RESOURCE or SND_ASYNC)
 else                               
  if (Zvuk.Checked = True) and (Play = True) then
  PlaySound('S Визначення не знайдено!', 0, SND_RESOURCE or SND_ASYNC);
end;

404

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Тобто якщо ресурс зкомпільовано, то його розмір допустимий для використання в DLL?

Практично так, але з єдиним нюансом, що ДЛЛ з виконуваним файлом, який цю ДЛЛ підвантажує, має уміщатися в адресовому просторі х86 плятформи (згруба це 4ГБ пам'яті). Якщо ви в ресурси запхали кіно в блю рей якості, то компілюйте вашу програму тільки для х64 плятформи.

Подякували: ProgramBandera, leofun012

405

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

ProgramBandera
Якщо у вас в Dll не лишилось коду, а самі лише ресурси, то пора переходити на zip-архів. Розпаковувати файли з нього можна в пам'ять, без збереження на диск.

P.S. Тему почистив. За наступні спроби офтопу почну банити.

Подякували: ProgramBandera, ch0r_t, leofun013

406

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Torbins написав:

ProgramBandera
Якщо у вас в Dll не лишилось коду, а самі лише ресурси, то пора переходити на zip-архів. Розпаковувати файли з нього можна в пам'ять, без збереження на диск.


Доброго вечора вам пане Torbins, і дякую! Я навіть не чув про таку можливість і ніде не зустрічав прикладів коду на таку тему. Якщо маєте будь-яке посилання, я б уважно його прочитав-би. Якщо щось не зрозумію то тоді запитаю тут у професіоналів.

407

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Ось це почитайте

Подякували: ProgramBandera1

408

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

У мене вийшов такий приклад:

procedure TForm1.Button1Click(Sender: TObject);
var
  zipf: TZipFile;
  id: Integer;
  tmp: TZipHeader;
  strm: TStream;
begin
  strm := nil;
  zipf := TZipFile.Create;
  try
    zipf.Open('Test.zip', zmRead);
    id := zipf.IndexOf('info.txt');
    if id > 0 then
    try
      zipf.Read(id, strm, tmp);
      Memo1.Lines.LoadFromStream(strm);
    finally
      strm.Free;
    end;
  finally
    zipf.Free;
  end;
end;
Подякували: ProgramBandera1

409

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Добрий вечір панове!
Підкажіть цей код можливо скоротити?

procedure TForm1.FormCreate(Sender: TObject);
begin
  index :=0;

  NewLineLength := 0;
  NewRowHeight := 0;
  Image1.Canvas.Font.Size := 14;
  Image1.Canvas.Font.Name := 'Monotype Corsiva';
  RowWidth('Дано:');


  RBGiven.Checked := True;  // Задаємо включення радіокнопки

  {Задаємо фон компонентів Image}
  Image1.Canvas.Brush.Color := clWhite;
  ITime.Canvas.Brush.Color := clWhite;
  IWay.Canvas.Brush.Color := clWhite;
  IMoving.Canvas.Brush.Color := clWhite;
  ISpeed.Canvas.Brush.Color := clWhite;
  {Кінець задавання фону компонентів Image}

  ITime.Canvas.Font.Size := 20;
  ITime.Canvas.Font.Style := [fsBold,  fsItalic];
  ITime.Canvas.Font.Name := 'Monotype Corsiva';
  ITime.Canvas.TextOut(6, -6, 't') ;

  IWay.Canvas.Font.Size := 20;
  IWay.Canvas.Font.Style := [fsBold,  fsItalic];
  IWay.Canvas.Font.Name := 'Monotype Corsiva';
  IWay.Canvas.TextOut(6, -6, 'l') ;

  IMoving.Canvas.Font.Size := 20;
  IMoving.Canvas.Font.Style := [fsBold,  fsItalic];
  IMoving.Canvas.Font.Name := 'Monotype Corsiva';
  IMoving.Canvas.TextOut(6, -6, 's') ;

  ISpeed.Canvas.Font.Size := 20;
  ISpeed.Canvas.Font.Style := [fsBold,  fsItalic];
  ISpeed.Canvas.Font.Name := 'Monotype Corsiva';
  ISpeed.Canvas.TextOut(6, -6, 'v') ;

end;

Цікавлять ось ці блоки коду:

 {Задаємо фон компонентів Image}
  Image1.Canvas.Brush.Color := clWhite;
  ITime.Canvas.Brush.Color := clWhite;
  IWay.Canvas.Brush.Color := clWhite;
  IMoving.Canvas.Brush.Color := clWhite;
  ISpeed.Canvas.Brush.Color := clWhite;
  {Кінець задавання фону компонентів Image}
ITime.Canvas.Font.Size := 20;
  ITime.Canvas.Font.Style := [fsBold,  fsItalic];
  ITime.Canvas.Font.Name := 'Monotype Corsiva';
  ITime.Canvas.TextOut(6, -6, 't') ;

  IWay.Canvas.Font.Size := 20;
  IWay.Canvas.Font.Style := [fsBold,  fsItalic];
  IWay.Canvas.Font.Name := 'Monotype Corsiva';
  IWay.Canvas.TextOut(6, -6, 'l') ;

  IMoving.Canvas.Font.Size := 20;
  IMoving.Canvas.Font.Style := [fsBold,  fsItalic];
  IMoving.Canvas.Font.Name := 'Monotype Corsiva';
  IMoving.Canvas.TextOut(6, -6, 's') ;

  ISpeed.Canvas.Font.Size := 20;
  ISpeed.Canvas.Font.Style := [fsBold,  fsItalic];
  ISpeed.Canvas.Font.Name := 'Monotype Corsiva';
  ISpeed.Canvas.TextOut(6, -6, 'v') ;

410

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Якось так:

var font: TFont;
begin
    font := TFont.Create;
    font.Size := 20;
    font.Style := [fsBold,  fsItalic];
    font.Name := 'Monotype Corsiva';
    for image in (ITime, IWay, IMoving, ISpeed) do with image.Canvas do begin
        Font.Assign(font);
        Brush.Color := clWhite;
        TextOut(6, -6, 'l') ;
    end;

Можливо, масив TImage-ів доведеться окремо проголошувати, я не певен, як воно в Delphi працює.

Подякували: ProgramBandera1

411 Востаннє редагувалося ProgramBandera (26.12.2021 11:35:17)

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Привіт панове!
При описі конструктора класу яке початкове значення краще задавати полям, константу Nil, чи змінну Null?

{ TPhysicalTime }
{ Клас Час }
constructor TPhysicalTime.Create;
const
  // Визначення – Час
  DEFINITION_TIME =
  'Час визначає тривалiсть iснування об’єктiв i послiдовнiсть змiн, якi в ' +
  'них вiдбуваються.' + #13#10 +
  'Час позначають лiтерою t.';
begin
  inherited Create; // Спочатку виконується батьківський конструктор
  fEnabledDefinition := folse;
  fDefinitionPhysicalPhenomenon := DEFINITION_TIME;
  fNamePhysicalPhenomenon := 'Час - t ';
  fValuePhysicalQuantity := Nil;  {Nil чи Null}
end;

чи

{ TPhysicalTime }
{ Клас Час }
constructor TPhysicalTime.Create;
const
  // Визначення – Час
  DEFINITION_TIME =
  'Час визначає тривалiсть iснування об’єктiв i послiдовнiсть змiн, якi в ' +
  'них вiдбуваються.' + #13#10 +
  'Час позначають лiтерою t.';
begin
  inherited Create; // Спочатку виконується батьківський конструктор
  fEnabledDefinition := folse;
  fDefinitionPhysicalPhenomenon := DEFINITION_TIME;
  fNamePhysicalPhenomenon := 'Час - t ';
  fValuePhysicalQuantity := Null; {Nil чи Null}
end;

Якесь треба їм задати одне із початкових значень, для того щоб в подальшому можна було робити вибір типу:

if PhysicalQuantity = Nil then
....

або

if PhysicalQuantity = Null then
....

Порадьте щось розумне будь-ласка, щоб в майбутньому я не ламав голову з помилками.

412

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Null - це Variant. Тип Variant призначений для представлення в одній змінній різних типів.
Nil - це напевно некоректний вказівник.
Якщо у вас змінна - вказівник (чи об'єкт) і вам треба зробити її невалідною, то єдиний варіант - nil. Variant.Null буде перетворено на nil компілятором, це просто зайві рухи, ще й неочевидні.

Подякували: ProgramBandera, Torbins2

413

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Насправді, під час створення класу, усім полям задаються значення за замовчуванням. Для вказівників це Nil, для чисел 0, для логічних змінних False, а для рядків - порожній рядок. Повторно задавати ті самі значення в конструкторі не обов'язково.

Подякували: ProgramBandera1

414 Востаннє редагувалося ProgramBandera (03.01.2022 23:41:07)

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Привіт панове! Якщо в мене в класі потрібно створити поле fObjectContainer типу TImage для візуального відображення картинок на формі як на малюнку:
https://replace.org.ua/uploads/images/6671/6d76872839d2be1c1290fc35bdaa48a0.bmp

То як це правильно зробити? Це потрібно додати в Uses клас Vcl.Controls. І створювати в батьківському класі конструктор, та в ньому якось через Parent створювати об'єкт? Чи це можливо зробити без конструктора в окремому методі, для того щоб при створенні об'єкту TImage текст вводити в же в дочірніх класах відповідний цим класам? Дивився відео в ютуб на цю тему, та ніяк не можу зрозуміти як мені в своєму коді це правильно зробити.

Я скину код пробного юніта. Можливо підкажете мені правильний напрямок відповідно до мого коду. Хотілося б це все описати в батьківському класі TPhysicalPhenomenon (Колір, Шрифт, Пензель) щоб в дочірніх класах вже окремим методом додавати відповідний текст на підготовлений об'єкт (t? l? s? v). 

unit Physics_Plus;

interface

uses
  System.Classes, System.SysUtils, Vcl.ExtCtrls, DataEntryUnit;

type

  TPhysicalTime = Class;
  TPhysicalPath = Class;
  TPhysicalMoving = Class;
  TPhysicalSpeed = Class;

  {Клас Фізичні явища.}
  TPhysicalPhenomenon = Class
    Private

      fObjectContainer: TImage;         // Контейнер для об'єкта фізичного явища

      fSoundWithResourceDLL: TResourceStream;   // Звук з ресурсу бібліотеки DLL

      fDefinitionPhysicalPhenomenon: String;      //Визначення фізичної величини
      fVisibilDefinition: Boolean;  // Виводити визначення - True або ні - False
      fIndexPhysicalPhenomenon: Word;                // Індекс фізичної величини

      fNamePhysicalPhenomenon: String;                // Назва фізичної величини
      fValuePhysicalPhenomenon: Extended;  // Цифрове значення фізичної величини
      fUnitsPhysicalPhenomenon: String;  //Одиниці вимірювання фізичної величини

      Protected

        Procedure SetVisibilDefinition (Bool: Boolean);
        Procedure SetIndex (Index: Word);
        Procedure SetValue (Value: Extended);
        Procedure SetUnits (Units: String);

        Function GetDefinition: String;
        Function GetVisibilDefinition: Boolean;
        Function GetIndex: Word;
        Function GetName: String;
        Function GetValue: Extended;
        Function GetUnits: String;

      Public

        property Physical_Definition: String read GetDefinition;
        property Physical_Definition_Visibil: Boolean read GetVisibilDefinition
                                                     write SetVisibilDefinition;
        property Physical_Index: Word read GetIndex write SetIndex;

        property Physical_Name: String read GetName;
        property Physical_Value: Extended read GetValue write SetValue;
        property Physical_Units: string read GetUnits write SetUnits;

      Published

    End;

  {Клас Час}
  TPhysicalTime = Class (TPhysicalPhenomenon)
    Private
     // fGeneralRowObject: String;
    Protected

    Public
    //  Тут будуть відповідні методи класу Час!

      constructor Create;
    Published

  End;

  {Клас Шлях - l.}
  TPhysicalPath = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Шлях!

      constructor Create;
    Published

  End;

  {Клас Переміщення - s.}
  TPhysicalMoving = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Переміщення!

      constructor Create;
    Published

  End;

  {Клас Швидкість - v.}
  TPhysicalSpeed = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Швидкість!

      constructor Create;
    Published

  End;

implementation

{ TPhysicalPhenomenon }

Procedure TPhysicalPhenomenon.SetVisibilDefinition(Bool: Boolean);
Begin
  fVisibilDefinition := Bool;
End;

Procedure TPhysicalPhenomenon.SetIndex(Index: Word);
Begin
  fIndexPhysicalPhenomenon := Index;
End;

Procedure TPhysicalPhenomenon.SetValue(Value: Extended);
Begin
  fValuePhysicalPhenomenon := Value;
End;

Procedure TPhysicalPhenomenon.SetUnits(Units: String);
Begin
  fUnitsPhysicalPhenomenon := Units;
End;

Function TPhysicalPhenomenon.GetDefinition: String;
Begin
  If (fVisibilDefinition = True) and (fIndexPhysicalPhenomenon = 0) then
    Result := fDefinitionPhysicalPhenomenon;
End;

Function TPhysicalPhenomenon.GetVisibilDefinition: Boolean;
Begin
  Result := fVisibilDefinition;
End;

Function TPhysicalPhenomenon.GetIndex: Word;
Begin
  Result := fIndexPhysicalPhenomenon;
End;

Function TPhysicalPhenomenon.GetName: String;
Begin
  If fIndexPhysicalPhenomenon = 0 then
    Result := fNamePhysicalPhenomenon + ' = '
  Else
    Result := fNamePhysicalPhenomenon + FloatToStr(fIndexPhysicalPhenomenon) +
              ' = ';
End;

Function TPhysicalPhenomenon.GetValue: Extended;
Begin
  Result := fValuePhysicalPhenomenon;
End;

Function TPhysicalPhenomenon.GetUnits: String;
Begin
  Result := fUnitsPhysicalPhenomenon;
End;

{ TPhysicalTime }

Constructor TPhysicalTime.Create;
Const
  DEFINITION_TIME =
  'Час визначає тривалiсть iснування об’єктiв i послiдовнiсть змiн, якi в ' +
  'них вiдбуваються. ' + #13#10 + 'Час позначають лiтерою t.' + #13#10;
Begin
  fDefinitionPhysicalPhenomenon := DEFINITION_TIME;
  fNamePhysicalPhenomenon := 'Час - t';
End;

{ TPhysicalPath }

Constructor TPhysicalPath.Create;
Const
  DEFINITION_PATH =
  'Шлях — фiзична величина, що дорiвнює довжинi траєкторiї, яку описує тiло ' +
  'за час руху.' + #13#10 + 'Шлях позначають малою латинською лiтерою l.' +
  #13#10;
Begin
  fDefinitionPhysicalPhenomenon := DEFINITION_PATH;
  fNamePhysicalPhenomenon := 'Шлях - l';
End;

{ TPhysicalMoving }

Constructor TPhysicalMoving.Create;
Const
  DEFINITION_MOVING =
  'Перемiщення  — фiзична величина, що характеризує змiну положення тіла у ' +
  'просторi та визначається напрямленим вiдрiзком, який сполучає положення ' +
  'рухомого тiла на початку i в кiнцi певного iнтервалу часу.' + #13#10 +
  'Переміщення s  — це вектор, що сполучає початкове положення тіла з його ' +
  'положенням у вибраний момент часу.' + #13#10;
Begin
  fDefinitionPhysicalPhenomenon := DEFINITION_MOVING;
  fNamePhysicalPhenomenon := 'Переміщення - s';
End;

{ TPhysicalSpeed }

Constructor TPhysicalSpeed.Create;
Const
  DEFINITION_SPEED = 'Швиидкість — фізична величина, що відповідає ' +
  'відношенню переміщення тіла до проміжку часу, за який це переміщення ' +
  'відбувалось.' + #13#10 + 'Швидкість — величина векторна, тобто вона має ' +
  'абсолютну величину і ' + 'напрямок.' + #13#10 + 'Швидкість позначають ' +
  'малою латинською лiтерою v.' + #13#10;
Begin
  fDefinitionPhysicalPhenomenon := DEFINITION_SPEED;
  fNamePhysicalPhenomenon := 'Швидкість - v';
End;

End.
Подякували: 0xDADA11C71

415

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Наслідування непотрібне використовується тоді, коли треба змінити поведінку об'єкта. Тут поведінка, як я розумію, однакова, різниця в значеннях кількох полів (літера, малюнок, визначення). Тобто все це мають бути об'єкти одного класу, просто в конструктори слід передавати різні дані.

416

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

koala написав:

Наслідування непотрібне використовується тоді, коли треба змінити поведінку об'єкта. Тут поведінка, як я розумію, однакова, різниця в значеннях кількох полів (літера, малюнок, визначення). Тобто все це мають бути об'єкти одного класу, просто в конструктори слід передавати різні дані.

Так пане koala! В батьківському класі потрібно створити об'єкт для image щоб туди закинути літеру, та при кліку на цьому об'єкті виконувалися певні дії методами дочірнього класу.  В дочірніх класах будуть свої методи обробки значень за певними формулами. Доброго дня.

417

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

ProgramBandera
В батьківському класі зробіть віртуальний конструктор. В дочірніх класах ви зможете його розширювати, якщо буде треба. В конструкторі можна створити усі об'єкти, які потім зможуть використовувати дочірні класи. А в деструкторі, відповідно, їх треба буде видалити. І ще раджу замінити TImage на TBitmap. Буде щось таке:

  TPhysicalPhenomenon = Class
    Private //Замініть на protected якщо захочете винести дочірні класи в окремий модуль
      fObjectContainer: TBitmap;         // Контейнер для об'єкта фізичного явища
      ...
    Protected
      ...
    Public
      constructor Create; virtual;
      destructor Destroy; override;
      ...
    End;

  TPhysicalTime = Class (TPhysicalPhenomenon)
    Private
      ...
    Protected
      ...
    Public
      constructor Create; override;
      ...
    Published
  End;
Подякували: ProgramBandera1

418 Востаннє редагувалося ProgramBandera (07.01.2022 01:23:06)

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

Зі святом панове!

Torbins написав:

В батьківському класі зробіть віртуальний конструктор. В дочірніх класах ви зможете його розширювати, якщо буде треба. В конструкторі можна створити усі об'єкти, які потім зможуть використовувати дочірні класи. А в деструкторі, відповідно, їх треба буде видалити. І ще раджу замінити TImage на TBitmap. Буде щось таке:

Пане Torbins для мене це нова тема і я вже геть заплутався. Якщо маєте час поясніть докладніше.
1) В батьківському класі зробіть віртуальний конструктор.  Так це я зрозумів

constructor Create; virtual;

2) В дочірніх класах ви зможете його розширювати, якщо буде треба.

Constructor Create; Override;

Тут в мене питання: А як тоді в описі дочірнього конструктора там якось Inherited; потрібно використовувати? Який взагалі там синтаксис коду буде?
3) В конструкторі можна створити усі об'єкти, які потім зможуть використовувати дочірні класи. От я і запитую як мені прописати код щоб з цього модуля можна було створити об'єкт на формі?

4) І ще раджу замінити TImage на TBitmap. Тут взагалі не зрозумів для чого це робити. Мені просто потрібно в об'єкті TImage ввести текст (літеру чи декілька) по заданих координатах, який візуально позначає фізичну величину.

З того що я зрозумів з літератури та відео в Ютуб, я створив об'єкт на формі методом CreateObject, хоча не розумію як це працює:

Procedure TPhysicalPhenomenon.CreateObject (Letter: String; Owner: TWinControl);
Begin
  fObjectContainer := Timage.Create(Owner);
  fObjectContainer.Parent := Owner;

  fObjectContainer.Width := 25;
  fObjectContainer.Height := 25;
  fObjectContainer.Top := 120;
  fObjectContainer.Left := 0;
  fObjectContainer.Canvas.Brush.Color := clWhite;
  fObjectContainer.Canvas.Font.Name := 'Monotype Corsiva';
  fObjectContainer.Canvas.Font.Style := [fsBold,  fsItalic];
  fObjectContainer.Canvas.Font.Size := 20;
  fObjectContainer.Canvas.TextOut(6, -6, Letter);
  fObjectContainer.ShowHint := True;
  fObjectContainer.Hint := 'Час';

End;

https://replace.org.ua/uploads/images/6671/9d827683f8d248a678bb6dbb7709d536.bmp

Та мені прийшлось поміняти дочірні конструктори. Вони стали з параметрами, чого дуже не хочеться але я не знаю як ще передати параметр власника.

  {Клас Час}
  TPhysicalTime = Class (TPhysicalPhenomenon)
    Private
     // fGeneralRowObject: String;
    Protected

    Public
    //  Тут будуть відповідні методи класу Час!

      constructor CreateTime (Owner: TWinControl);
    Published

  End;

  {Клас Шлях - l.}
  TPhysicalPath = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Шлях!

      constructor CreatePath (Owner: TWinControl);
    Published

  End;

  {Клас Переміщення - s.}
  TPhysicalMoving = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Переміщення!

      constructor CreateMoving (Owner: TWinControl);
    Published

  End;

  {Клас Швидкість - v.}
  TPhysicalSpeed = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Швидкість!

      constructor CreateSpeed (Owner: TWinControl);
    Published

  End;

Constructor TPhysicalTime.CreateTime (Owner: TWinControl);
Const
  DEFINITION_TIME =
  'Час визначає тривалiсть iснування об’єктiв i послiдовнiсть змiн, якi в ' +
  'них вiдбуваються. ' + #13#10 + 'Час позначають лiтерою t.' + #13#10;
Begin
  CreateObject('t',Owner);
  fDefinitionPhysicalPhenomenon := DEFINITION_TIME;
  fNamePhysicalPhenomenon := 'Час - t';
End;

{ TPhysicalPath }

Constructor TPhysicalPath.CreatePath (Owner: TWinControl);
Const
  DEFINITION_PATH =
  'Шлях — фiзична величина, що дорiвнює довжинi траєкторiї, яку описує тiло ' +
  'за час руху.' + #13#10 + 'Шлях позначають малою латинською лiтерою l.' +
  #13#10;
Begin
  CreateObject('l',Owner);
  fDefinitionPhysicalPhenomenon := DEFINITION_PATH;
  fNamePhysicalPhenomenon := 'Шлях - l';
End;

{ TPhysicalMoving }

Constructor TPhysicalMoving.CreateMoving (Owner: TWinControl);
Const
  DEFINITION_MOVING =
  'Перемiщення  — фiзична величина, що характеризує змiну положення тіла у ' +
  'просторi та визначається напрямленим вiдрiзком, який сполучає положення ' +
  'рухомого тiла на початку i в кiнцi певного iнтервалу часу.' + #13#10 +
  'Переміщення s  — це вектор, що сполучає початкове положення тіла з його ' +
  'положенням у вибраний момент часу.' + #13#10;
Begin
  CreateObject('s',Owner);
  fDefinitionPhysicalPhenomenon := DEFINITION_MOVING;
  fNamePhysicalPhenomenon := 'Переміщення - s';
End;

{ TPhysicalSpeed }

Constructor TPhysicalSpeed.CreateSpeed (Owner: TWinControl);
Const
  DEFINITION_SPEED = 'Швиидкість — фізична величина, що відповідає ' +
  'відношенню переміщення тіла до проміжку часу, за який це переміщення ' +
  'відбувалось.' + #13#10 + 'Швидкість — величина векторна, тобто вона має ' +
  'абсолютну величину і ' + 'напрямок.' + #13#10 + 'Швидкість позначають ' +
  'малою латинською лiтерою v.' + #13#10;
Begin
  CreateObject('v',Owner);
  fDefinitionPhysicalPhenomenon := DEFINITION_SPEED;
  fNamePhysicalPhenomenon := 'Швидкість - v';
End;

І створив я його в модулі програми на головній формі так (Нижній об'єкт на малюнку з літерою t) :

procedure TForm1.FormCreate(Sender: TObject);
var
  CHAS: TPhysicalTime;
begin
  CHAS := TPhysicalTime.CreateTime(Form1);

В наступному повідомленні скину весь код модуля. Дякую за ваш затрачений час панове!

P.S. Якщо пан koala запитає для чого це все робиться: це робиться для того щоб я зміг запрограмувати подію (Клік) на створеному об'єкті. Якщо це взагалі можливо зробити програмно (Хоча я десь читав що там якимось чином через клас TNotyfiEvent потрібно це робити, хоча можливо я і помиляюсь)! А після цього я вже буду проводити всі необхідні маніпуляції.

419

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

unit Physics_Plus;

interface

uses
  Winapi.Windows, Winapi.MMSystem, System.Classes, System.SysUtils,
  Vcl.Controls, Vcl.ExtCtrls, Vcl.Graphics, DataEntryUnit;

type

  TPhysicalTime = Class;
  TPhysicalPath = Class;
  TPhysicalMoving = Class;
  TPhysicalSpeed = Class;

  {Клас Фізичні явища.}
  TPhysicalPhenomenon = Class
    Private

      fObjectContainer: TImage;         // Контейнер для об'єкта фізичного явища

      fDefinitionPhysicalPhenomenon: String;      //Визначення фізичної величини
      fVisibilDefinition: Boolean;  // Виводити визначення - True або ні - False
      fIndexPhysicalPhenomenon: Word;                // Індекс фізичної величини

      fNamePhysicalPhenomenon: String;                // Назва фізичної величини
      fValuePhysicalPhenomenon: Extended;  // Цифрове значення фізичної величини
      fUnitsPhysicalPhenomenon: String;  //Одиниці вимірювання фізичної величини

    Protected

      Procedure SetVisibilDefinition (Bool: Boolean);
      Procedure SetIndex (Index: Word);
      Procedure SetValue (Value: Extended);
      Procedure SetUnits (Units: String);

      Function GetDefinition: String;
      Function GetVisibilDefinition: Boolean;
      Function GetIndex: Word;
      Function GetName: String;
      Function GetValue: Extended;
      Function GetUnits: String;

    Public

      Procedure CreateObject (Letter: String; Owner: TWinControl);

      Procedure PlayDefinition (NameSound: String);


      property Physical_Definition: String read GetDefinition;
      property Physical_Definition_Visibil: Boolean read GetVisibilDefinition
                                                     write SetVisibilDefinition;
      property Physical_Index: Word read GetIndex write SetIndex;

      property Physical_Name: String read GetName;
      property Physical_Value: Extended read GetValue write SetValue;
      property Physical_Units: string read GetUnits write SetUnits;

    Published

  End;

  {Клас Час}
  TPhysicalTime = Class (TPhysicalPhenomenon)
    Private
     // fGeneralRowObject: String;
    Protected

    Public
    //  Тут будуть відповідні методи класу Час!

      constructor CreateTime (Owner: TWinControl);
    Published

  End;

  {Клас Шлях - l.}
  TPhysicalPath = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Шлях!

      constructor CreatePath (Owner: TWinControl);
    Published

  End;

  {Клас Переміщення - s.}
  TPhysicalMoving = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Переміщення!

      constructor CreateMoving (Owner: TWinControl);
    Published

  End;

  {Клас Швидкість - v.}
  TPhysicalSpeed = Class (TPhysicalPhenomenon)
    Private

    Protected

    Public
    //  Тут будуть відповідні методи класу Швидкість!

      constructor CreateSpeed (Owner: TWinControl);
    Published

  End;

implementation

{ TPhysicalPhenomenon }

Procedure TPhysicalPhenomenon.CreateObject (Letter: String; Owner: TWinControl);
Begin
  fObjectContainer := Timage.Create(Owner);
  fObjectContainer.Parent := Owner;

  fObjectContainer.Width := 25;
  fObjectContainer.Height := 25;
  fObjectContainer.Top := 120;
  fObjectContainer.Left := 0;
  fObjectContainer.Canvas.Brush.Color := clWhite;
  fObjectContainer.Canvas.Font.Name := 'Monotype Corsiva';
  fObjectContainer.Canvas.Font.Style := [fsBold,  fsItalic];
  fObjectContainer.Canvas.Font.Size := 20;
  fObjectContainer.Canvas.TextOut(6, -6, Letter);
  fObjectContainer.ShowHint := True;
  fObjectContainer.Hint := 'Час';

End;


Procedure TPhysicalPhenomenon.PlayDefinition (NameSound: String);
{Метод звукового програвання визначення фізичної величини.}
Var
  DownloadLibrary: HMODULE;
Begin

  If AnsiCompareText(NameSound, 'Час') = 0 Then
    NameSound := 'S_Time'
  Else
  If AnsiCompareText(NameSound, 'Шлях') = 0 Then
    NameSound := 'S_Path'
  Else
  If AnsiCompareText(NameSound, 'Переміщення') = 0 Then
    NameSound := 'S_Moving'
  Else
  If AnsiCompareText(NameSound, 'Швидкість') = 0 Then
    NameSound := 'S_Speed';

  Try
    DownloadLibrary := LoadLibrary('LibrarySound.dll');
    PlaySound(PWideChar(NameSound), DownloadLibrary, SND_RESOURCE or SND_SYNC);
  Finally
    FreeLibrary(DownloadLibrary);
  End;
End;


Procedure TPhysicalPhenomenon.SetVisibilDefinition(Bool: Boolean);
Begin
  fVisibilDefinition := Bool;
End;

Procedure TPhysicalPhenomenon.SetIndex(Index: Word);
Begin
  fIndexPhysicalPhenomenon := Index;
End;

Procedure TPhysicalPhenomenon.SetValue(Value: Extended);
Begin
  fValuePhysicalPhenomenon := Value;
End;

Procedure TPhysicalPhenomenon.SetUnits(Units: String);
Begin
  fUnitsPhysicalPhenomenon := Units;
End;


Function TPhysicalPhenomenon.GetDefinition: String;
Begin
  If (fVisibilDefinition = True) and (fIndexPhysicalPhenomenon = 0) then
    Result := fDefinitionPhysicalPhenomenon;
End;

Function TPhysicalPhenomenon.GetVisibilDefinition: Boolean;
Begin
  Result := fVisibilDefinition;
End;

Function TPhysicalPhenomenon.GetIndex: Word;
Begin
  Result := fIndexPhysicalPhenomenon;
End;

Function TPhysicalPhenomenon.GetName: String;
Begin
  If fIndexPhysicalPhenomenon = 0 then
    Result := fNamePhysicalPhenomenon + ' = '
  Else
    Result := fNamePhysicalPhenomenon + FloatToStr(fIndexPhysicalPhenomenon) +
              ' = ';
End;

Function TPhysicalPhenomenon.GetValue: Extended;
Begin
  Result := fValuePhysicalPhenomenon;
End;

Function TPhysicalPhenomenon.GetUnits: String;
Begin
  Result := fUnitsPhysicalPhenomenon;
End;

{ TPhysicalTime }

Constructor TPhysicalTime.CreateTime (Owner: TWinControl);
Const
  DEFINITION_TIME =
  'Час визначає тривалiсть iснування об’єктiв i послiдовнiсть змiн, якi в ' +
  'них вiдбуваються. ' + #13#10 + 'Час позначають лiтерою t.' + #13#10;
Begin
  CreateObject('t',Owner);
  fDefinitionPhysicalPhenomenon := DEFINITION_TIME;
  fNamePhysicalPhenomenon := 'Час - t';
End;

{ TPhysicalPath }

Constructor TPhysicalPath.CreatePath (Owner: TWinControl);
Const
  DEFINITION_PATH =
  'Шлях — фiзична величина, що дорiвнює довжинi траєкторiї, яку описує тiло ' +
  'за час руху.' + #13#10 + 'Шлях позначають малою латинською лiтерою l.' +
  #13#10;
Begin
  CreateObject('l',Owner);
  fDefinitionPhysicalPhenomenon := DEFINITION_PATH;
  fNamePhysicalPhenomenon := 'Шлях - l';
End;

{ TPhysicalMoving }

Constructor TPhysicalMoving.CreateMoving (Owner: TWinControl);
Const
  DEFINITION_MOVING =
  'Перемiщення  — фiзична величина, що характеризує змiну положення тіла у ' +
  'просторi та визначається напрямленим вiдрiзком, який сполучає положення ' +
  'рухомого тiла на початку i в кiнцi певного iнтервалу часу.' + #13#10 +
  'Переміщення s  — це вектор, що сполучає початкове положення тіла з його ' +
  'положенням у вибраний момент часу.' + #13#10;
Begin
  CreateObject('s',Owner);
  fDefinitionPhysicalPhenomenon := DEFINITION_MOVING;
  fNamePhysicalPhenomenon := 'Переміщення - s';
End;

{ TPhysicalSpeed }

Constructor TPhysicalSpeed.CreateSpeed (Owner: TWinControl);
Const
  DEFINITION_SPEED = 'Швиидкість — фізична величина, що відповідає ' +
  'відношенню переміщення тіла до проміжку часу, за який це переміщення ' +
  'відбувалось.' + #13#10 + 'Швидкість — величина векторна, тобто вона має ' +
  'абсолютну величину і ' + 'напрямок.' + #13#10 + 'Швидкість позначають ' +
  'малою латинською лiтерою v.' + #13#10;
Begin
  CreateObject('v',Owner);
  fDefinitionPhysicalPhenomenon := DEFINITION_SPEED;
  fNamePhysicalPhenomenon := 'Швидкість - v';
End;

End.

420

Re: Програма розв'язування задач з фізики! Для учнів 7-го класу.

ProgramBandera написав:

Зі святом панове!

Torbins написав:

В батьківському класі зробіть віртуальний конструктор. В дочірніх класах ви зможете його розширювати, якщо буде треба. В конструкторі можна створити усі об'єкти, які потім зможуть використовувати дочірні класи. А в деструкторі, відповідно, їх треба буде видалити. І ще раджу замінити TImage на TBitmap. Буде щось таке:

Пане Torbins для мене це нова тема і я вже геть заплутався. Якщо маєте час поясніть докладніше.
1) В батьківському класі зробіть віртуальний конструктор.  Так це я зрозумів

constructor Create; virtual;

2) В дочірніх класах ви зможете його розширювати, якщо буде треба.

Constructor Create; Override;

Тут в мене питання: А як тоді в описі дочірнього конструктора там якось Inherited; потрібно використовувати? Який взагалі там синтаксис коду буде?

Якщо параметри конструктора ті самі, то достатньо просто "inherited;".

ProgramBandera написав:

4) І ще раджу замінити TImage на TBitmap. Тут взагалі не зрозумів для чого це робити. Мені просто потрібно в об'єкті TImage ввести текст (літеру чи декілька) по заданих координатах, який візуально позначає фізичну величину.

З того що я зрозумів з літератури та відео в Ютуб, я створив об'єкт на формі методом CreateObject, хоча не розумію як це працює:

Procedure TPhysicalPhenomenon.CreateObject (Letter: String; Owner: TWinControl);
Begin
  fObjectContainer := Timage.Create(Owner);
  fObjectContainer.Parent := Owner;

  fObjectContainer.Width := 25;
  fObjectContainer.Height := 25;
  fObjectContainer.Top := 120;
  fObjectContainer.Left := 0;
  fObjectContainer.Canvas.Brush.Color := clWhite;
  fObjectContainer.Canvas.Font.Name := 'Monotype Corsiva';
  fObjectContainer.Canvas.Font.Style := [fsBold,  fsItalic];
  fObjectContainer.Canvas.Font.Size := 20;
  fObjectContainer.Canvas.TextOut(6, -6, Letter);
  fObjectContainer.ShowHint := True;
  fObjectContainer.Hint := 'Час';

End;

Міняти TImage на TBitmap потрібно для того, щоб потім можна було переробити форму, і не боятись, що у вас десь в іншому місці (про яке ви уже встигли забути) записані константи розміру та положення картинок.

ProgramBandera написав:

P.S. Якщо пан koala запитає для чого це все робиться: це робиться для того щоб я зміг запрограмувати подію (Клік) на створеному об'єкті. Якщо це взагалі можливо зробити програмно (Хоча я десь читав що там якимось чином через клас TNotyfiEvent потрібно це робити, хоча можливо я і помиляюсь)! А після цього я вже буду проводити всі необхідні маніпуляції.

Створіть потрібний вам обробник події, та скопіюйте в свій клас.

В результаті має вийти щось таке:

  {Клас Фізичні явища.}
  TPhysicalPhenomenon = Class
    Private
      fObjectContainer: TBitmap;         // Контейнер для об'єкта фізичного явища
      ...
    Protected
      procedure PaintLetter(ALetter:Char);
      procedure HandleClick; virtual;
      ...
    Public
      constructor Create; virtual;
      destructor Destroy; override;
      procedure ClickHandler(Sender: TObject);
      property ObjectContainer: TBitmap read fObjectContainer;
      ...
    Published
  End;

  {Клас Час}
  TPhysicalTime = Class (TPhysicalPhenomenon)
    Protected
      procedure HandleClick; override;
    Public
      constructor Create; override;
    Published
  End;

  ...

implementation

{ TPhysicalPhenomenon }

Procedure TPhysicalPhenomenon.Create;
Begin
  fObjectContainer := TBitmap.Create;

  fObjectContainer.Width := 25;
  fObjectContainer.Height := 25;

  fObjectContainer.Canvas.Brush.Color := clWhite;
  fObjectContainer.Canvas.Font.Name := 'Monotype Corsiva';
  fObjectContainer.Canvas.Font.Style := [fsBold,  fsItalic];
  fObjectContainer.Canvas.Font.Size := 20;
End;

Procedure TPhysicalPhenomenon.Destroy;
Begin
  inherited;
  fObjectContainer.Free;
End;

Procedure TPhysicalPhenomenon.PaintLetter(ALetter:Char);
Begin
  fObjectContainer.Canvas.TextOut(6, -6, ALetter);
End;

Procedure TPhysicalPhenomenon.ClickHandler(Sender: TObject);
Begin
  HandleClick;
End;

Procedure TPhysicalPhenomenon.HandleClick;
Begin
  //дочірні об'єкти щось тут робитимуть
End;

...

{ TPhysicalTime }

Constructor TPhysicalTime.Create;
Const
  DEFINITION_TIME =
  'Час визначає тривалiсть iснування об’єктiв i послiдовнiсть змiн, якi в ' +
  'них вiдбуваються. ' + #13#10 + 'Час позначають лiтерою t.' + #13#10;
Begin
  inherited;
  PaintLetter('t');
  fDefinitionPhysicalPhenomenon := DEFINITION_TIME;
  fNamePhysicalPhenomenon := 'Час - t';
  //Сюди можна додати ініціалізацію поля, яке міститиме підказку замість fObjectContainer.Hint
End;

Procedure TPhysicalTime.HandleClick;
Begin
  ShowMessage('Клік по ' + fNamePhysicalPhenomenon);
End;

...

End.

Код в модулі з формою:

procedure TForm1.FormCreate(Sender: TObject);
var
  CHAS: TPhysicalTime;
begin
  CHAS := TPhysicalTime.Create;
  Image1.Picture := CHAS.ObjectContainer;
  Image1.Hint := CHAS.Physical_Name;
  Image1.OnClick := CHAS.ClickHandler;
Подякували: ProgramBandera1