Câu hỏi Delphi 7 hình thức, neo không hoạt động trong Vista


Phần mềm này được xây dựng trên Delphi 7.

Trên máy XP của tôi, biểu mẫu sẽ thay đổi kích cỡ như tôi mong đợi. Tuy nhiên, trên hai máy Vista, tôi có các thành phần với các neo được đặt thành [akLeft, akTop, akRight, akBottom], nhưng khi tôi thay đổi kích thước biểu mẫu, các thành phần không kéo dài với biểu mẫu, để trống khoảng trống và cạnh dưới . Trên máy XP, các thành phần được kéo giãn chính xác với biểu mẫu.

Vì vậy, có vẻ như máy Vista bỏ qua đặc tính neo. Bất kỳ ý tưởng gì gây ra điều này và làm thế nào để sửa chữa nó?

Cập nhật quan trọng (François):
Chúng tôi đã có cùng một vấn đề với D2007 ứng dụng và trên tất cả các cửa sổ x64.
Câu trả lời của Andreas thực sự là sự sửa chữa. Vì vậy, nó không phải là D7 cũng không liên quan đến Vista.


14
2017-08-31 00:01


gốc


Theo phiên bản Windows nào được chương trình biên dịch? - Argalatyr
Biên dịch XP / Delphi 7 - Robo
Xem câu trả lời của Argalatyr. Nó có ý nghĩa không? - Hemant
Francois: Vâng, giả sử rằng vấn đề của Robo là một trục trặc mà chúng ta chỉ gặp phải và không phải thứ gì đó không liên quan. - Mason Wheeler


Các câu trả lời:


Có thể nó liên quan đến vấn đề "tràn bộ đệm hạt nhân Windows" xảy ra nếu kiểm soát của bạn có nhiều cha mẹ. Và nếu bạn chạy nó trên một hệ thống 64 bit, tràn ngăn xếp hạt nhân xảy ra nhanh hơn nhiều. (thêm về điều này ở đây: http://news.jrsoftware.org/news/toolbar2000/msg07779.html)

Trên CodeCentral của Embarcadero là một giải pháp cho lỗi này (cũng được sao chép gần như 1: 1 vào VCL Delphi 2009): http://cc.embarcadero.com/Item/25646


12
2017-08-31 10:41



Tôi có ấn tượng rằng điều này chỉ áp dụng nếu bạn có quyền kiểm soát lồng nhau khoảng 20 cấp độ sâu? - Argalatyr
Nó phụ thuộc vào bao nhiêu cửa sổ WH_CALLWNDPROC móc được cài đặt trên toàn hệ thống. (Logitech ví dụ sử dụng WH_CALLWNDPROC móc, và như vậy hiện TActionManager). - Andreas Hausladen
Tôi chỉ cần chạy vào một trong những công việc và quản lý để theo dõi nó xuống vấn đề này nhờ vào bài viết của bạn ở đây. Cảm ơn vì thông tin và bản sửa lỗi, Andreas. Tuy nhiên, một lông trong nắp của bạn đã đáng kể. - Mason Wheeler
Xin lỗi vì trả lời cực kỳ muộn. Tôi đã thêm ControlResizeBugFix.pas vào dự án trong tệp .dpr, nhưng nó không có sự khác biệt. Các điều khiển vẫn không thay đổi kích thước trên máy tính Windows 7 64 bit của tôi. - Robo
OK, cố định. Nó đã được làm với một số thuộc tính OldCreateOrder của một số hình thức mặc định là true, và một số mặc định là sai, mà gây ra một số hình thức thay đổi kích thước mã để không hoạt động chính xác. Nếu tôi thay đổi thuộc tính thành false, hãy lưu biểu mẫu, sau đó mở lại nó, nó sẽ mặc định trở lại true trên một số biểu mẫu. - Robo


Nó có thể là do khung trong suốt được hiển thị bởi Vista. (Để cung cấp cho các cửa sổ khác nhau xuất hiện trong suốt giống nhau.

Hãy thử sử dụng "Align" (alClient) thay vì neo. Vì bạn đang sử dụng tất cả các neo, điều đó có ý nghĩa hơn.


2
2017-08-31 03:14



Điều đó sẽ không hoạt động vì điều khiển sẽ chiếm toàn bộ màn hình, bao gồm các điều khiển khác. - Robo
Ví dụ bạn có ghi nhớ bao gồm hầu hết màn hình của bạn và bạn có một số nút ở dưới cùng của biểu mẫu. Bạn nắm tay đặt một bảng và đặt thuộc tính Căn chỉnh của nó thành alBottom. Bạn đặt các điều khiển trên bảng điều khiển đó. Sau đó, bạn đặt điều khiển ghi nhớ và đặt thuộc tính căn chỉnh của nó thành alClient (điều này sẽ điền vào biểu mẫu nhưng rời khỏi bảng điều khiển phía dưới). - Hemant
+1 điều này không hoạt động (với bình luận bổ sung của Hemant). Xem mã làm việc trong câu trả lời của tôi như là một ví dụ (tôi đã chỉnh sửa câu trả lời của Hemant, nhưng lo lắng rằng có thể là thô lỗ). - Argalatyr
Nếu D7 đã có AlignWithMargins, alClient có thể hoạt động. - Uli Gerhardt


Trước khi neo được giới thiệu trong Delphi 4, chúng tôi đã thay đổi kích thước các thành phần động để đạt được hiệu quả tương tự. Bạn có thể dễ dàng di chuyển / điều chỉnh các thành phần trong biểu mẫu onresize biến cố.

Đặt biểu mẫu doublebuffered tài sản để true có thể giảm nhấp nháy, bằng cách đệm paint phương pháp. Tôi nhớ chúng tôi đã từng phải thực hiện chính bản thân mình!


2
2017-08-31 09:49





Là một thay thế cho thay đổi kích thước năng động, tôi đề xuất, dựa trên gợi ý của Hemant tôi đã tát cùng một số mã làm việc (bên dưới). Chỉ cần tạo ứng dụng biểu mẫu VCL, thả vào tpanel không chạm vào bất kỳ cạnh nào của biểu mẫu (theo mặc định, Align = alNone) và thay thế Unit1 bằng mã bên dưới. Khi bạn chạy nó, bạn sẽ thấy 4 tấm màu vàng bao quanh một tấm ban đầu được thêm vào và bảng điều khiển trung tâm sẽ thay đổi kích thước với biểu mẫu (như thể tất cả các neo là true).

unit Unit1;

interface

uses
  Windows, Classes, Controls, Forms, ExtCtrls, Graphics;

type
  TPanelPos = (ppLeft, ppRight, ppTop, ppBottom);
  TForm1 = class(TForm)
    Panel1: TPanel;
    procedure FormCreate(Sender: TObject);
    procedure FormDestroy(Sender: TObject);
  private
    { Private declarations }
    Panels : array[TPanelPos] of tpanel;
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.FormCreate(Sender: TObject);
var
  PanelPos : TPanelPos;
begin
  for PanelPos := ppLeft to ppBottom do
  begin
    Panels[PanelPos] := tpanel.Create(Form1);
    Panels[PanelPos].Parent := Form1;
    Panels[PanelPos].Color := clYellow;
    case PanelPos of
     ppLeft :
       begin
         Panels[PanelPos].Align := alLeft;
         Panels[PanelPos].Width := Panel1.Left - 1;
       end;
     ppRight :
       begin
         Panels[PanelPos].Align := alRight;
         Panels[PanelPos].Width := Form1.Width - Panel1.Left - Panel1.Width;
       end;
     ppTop :
       begin
         Panels[PanelPos].Align := alTop;
         Panels[PanelPos].Height := Panel1.Top - 1;
       end;
     ppBottom :
       begin
         Panels[PanelPos].Align := alBottom;
         Panels[PanelPos].Height := Form1.Height - Panel1.Top - Panel1.Height;
       end;
    end;
    Panel1.Align := alClient;
  end;
end;

procedure TForm1.FormDestroy(Sender: TObject);
var
  PanelPos : TPanelPos;
begin
  for PanelPos := ppLeft to ppBottom do
    Panels[PanelPos].Free;
end;

end.

1
2017-08-31 22:14



Đoạn trích đẹp và triệt để! - Hemant


Thử chạy chương trình trong chế độ tương thích XP trên Vista. Các chương trình được biên dịch bởi Delphi 7 có thể không hỗ trợ đầy đủ chế độ gốc của Vista (không có gì ngạc nhiên ở đó).


0
2017-08-31 02:55



Các khách hàng sẽ muốn chạy nó trong Vista bản địa hơn là chế độ tương thích, hy vọng có một số cách để có được xung quanh đó. - Robo
Hiểu. Xin lỗi tôi không có nhiều đề nghị nữa - tôi không còn sử dụng D7 nữa và phản hồi của tôi tóm tắt sự hiểu biết của tôi về tình huống này. Tôi hy vọng bạn tìm thấy một giải pháp! - Argalatyr
Nếu bạn muốn hỗ trợ Vista đầy đủ, bạn sẽ phải nâng cấp. Đó là một tính năng kể từ Delphi 2007. Trên thực tế, nếu bạn thực sự muốn ở lại hiện tại, bạn nên có Delphi 2010, xuất hiện vào tuần trước. Nó có hỗ trợ đầy đủ cho Windows 7 cũng như Vista. - Mason Wheeler
Mason: đó là sự thật, nhưng nó không thực sự trả lời câu hỏi. Có những lý do đáng tin cậy để gắn bó với một phiên bản cũ cho một số dự án, và việc tìm kiếm một cách để đáp ứng các thông số kỹ thuật trong những hạn chế đó là một thách thức trong thế giới thực. - Argalatyr


Có vẻ đây là câu hỏi khá cũ, dù sao đây là giải pháp duy nhất cho vấn đề này trong Vũ trụ: Sử dụng phương pháp định kích thước lập trình Windows cũ bằng cách sử dụng API bẫy WM_SIZE và WM_SIZING, đó là phần mềm không thể đọc được và sẽ hoạt động trong mọi Windows mà bạn biết .

Tất nhiên điều này có nghĩa là bạn phải sử dụng chủ yếu GetClientRect () để xác định witdhs và chiều cao và sau đó thay đổi kích thước điều khiển dựa trên các giá trị như vậy, chắc chắn rằng âm thanh có vẻ như cố gắng để đốt cháy một tàu vũ trụ nhưng nó là tốt nhất.

Nếu không, bạn có thể làm một cái gì đó thực tế hơn và nhanh chóng trong một quy trình thay đổi kích cỡ như:

Control1.Left := Control2.Left + (buttonControl.Width div 2) - (buttonControl3.Width div 2);
//for example widths
Control4.Width    := (Control.Width * 4) + (Control.Left * 8) + 54 ;

Tôi thực hiện loại mã hóa và chức năng đó trong tất cả các phiên bản Windows bất kể nó là phiên bản nào.

Bạn chỉ cần một số giá trị trên độ phân giải màn hình để tham khảo thực hiện một việc như sau:

iCXSCREEN := GetSystemMetrics(SM_CXSCREEN);
iCYSCREEN := GetSystemMetrics(SM_CYSCREEN);

    if ((iCXSCREEN = 1280) and (iCYSCREEN = 720)) or  ((iCXSCREEN = 1280) and (iCYSCREEN = 700)) or ((iCXSCREEN = 1280) and (iCYSCREEN = 600)) then begin

// blah blah

end;

Hy vọng giúp đỡ người khác!

Chúc mừng!


0
2018-05-21 20:09