1

QTJambi と Webkit に非常に永続的な問題があります。

これが私がやりたいことです。

HTML ファイルにコード化された Web インターフェースをロードし (動作します)、Javascript と Java 間の対話を行い (これも動作します)、画像 (2D ゲームの風景) を表示する別のウィジェットの上に透明な背景を持つ Web インターフェースを表示し、 Web インターフェイスが静的である限り、これも機能します。

問題は、Web インターフェイスが変更されたときに発生します (DOM および css 操作)。変更すると、以前の Web ビューのレンダリングはクリアされず、新しいレンダリングが上書きされます。だから、私はそのようなレンダリングを持っています:

グラフィックバグの画像

私はそれがどのように機能するかを理解しています。背景色の長方形が表示され、以前のレンダリングが非表示になり、新しいレンダリングが表示されます。ただし、背景色は透明です。だからそれは何も隠しません。

コンポジション モードで Web で見つけた解決策をいくつか試しましたが、うまくいきません。同じ問題または黒い画面があります。

これが私のコードです。

HTML ファイル :

<html>
<head>
   <meta charset="utf-8" />

   <style>
       #body
       {
           position: absolute; 
           left: 0px; 
           right: 0px; 
            top: 0px; 
           bottom: 0px; 
           overflow: hidden;
       }


        #button
        {
            position: absolute; 
            left: 20px; 
            top: 20px; 
            background-color: rgba(255, 100, 100, 0.1); 
            padding: 10px; 
            box-shadow: 0px 2px 5px rgb(0, 0, 0); 
            border-radius: 5px; 
        }

       #token
        {
            position: absolute; 
            left: 200px; 
            top: 20px; 
            background-color: rgba(100, 255, 100, 0.1); 
            padding: 10px; 
            box-shadow: 0px 2px 5px rgb(0, 0, 0); 
            border-radius: 5px; 
        }

       #console
       {
           background-color: rgba(100, 100, 255, 0.1); 
           position: absolute; 
           left: 20px; 
           right: 20px; 
           top: 100px; 
           bottom: 20px; 
           padding: 10px; 
           overflow: auto; 
       }
   </style>

</head>

<body>

    <div id="button" >Appeler Java</div> <!-- Le bouton rouge qui appelle Java --> <!-- This red button calls Java -->
    <div id="console" >Console. <br /></div> <!-- Le bloc bleu où on affiche les messages --> <!-- Messages are displayed in this blue block. -->
    <div id="token" >Je bouge.</div> <!-- Le petit bloc vert qui bouge tout seul --> <!-- The moving green block. -->

    <script type="text/javascript" >

        // Fonction javascript appelée par Java au chargement de la page 
        // Java calls this Javascript function when the HTML file is loaded. 
        var fromJavaToJavascript = function()
        {
            document.getElementById("console").appendChild(document.createTextNode("J'ai été appelé par le Java. ")); 
            document.getElementById("console").appendChild(document.createElement("br")); 
        }; 

        // Mon image qui doit recevoir la QPixmap 
        //var qPixmap = new Image(); 

        var readImage = function()
        {
            document.getElementById("console").appendChild(document.createTextNode("Je reçoit une image de java. " + qPixmap)); 
            document.getElementById("console").appendChild(document.createElement("br")); 
        }; 

        window.onload = function()
        {
            var count = 0; 

            // Fonction qui appelle Java et déclenchée par le bouton rouge 
            // When the red button is clicked, it calls this javascript function which calls a Java function. 
           document.getElementById("button").onclick = function()
           {
               count++; 

               // On affiche l'incrément dans le bouton rouge 
               // Text in red button is updated. 
               while (document.getElementById("button").firstChild)
                   document.getElementById("button").removeChild(document.getElementById("button").firstChild); 

               document.getElementById("button").appendChild(document.createTextNode("Appeler Java " + count)); 

               // On affiche un message dans le bloc bleu 
               // New message is displayed in the blue block. 
               document.getElementById("console").appendChild(document.createTextNode("Je dois appeler le Java. " + javaObject)); 
               document.getElementById("console").appendChild(document.createElement("br")); 

               // On appelle Java
               // Call Java. 
               javaObject.submit(); 
           }; 

            var initPos = 20; 

            // Le bloc vert bouge tout seul. 
            // The green block is moving. 
            var timer = setInterval(function()
            {
                initPos = initPos + 5; 

                document.getElementById("token").style.top = initPos + "px"; 

            }, 500); 
        }; 

    </script>

</body>
</html>

メインフレーム:

public class WebBrowserTestFrame extends QMainWindow
{
    protected QGraphicsView view; 
    protected QGraphicsScene scene;
    protected WebBrowserTestQWebView browser; 
    protected QGridLayout gridLayout; 

    public WebBrowserTestFrame()
    {
        this.gridLayout = new QGridLayout(); 

        // Le widget où on affiche une image
        // This widget displays an image 
        this.scene = new QGraphicsScene(); 
        QPixmap image = new QPixmap("resources/tests/Coin-coin.jpg"); 
        this.scene.addPixmap(image); 
        this.view = new QGraphicsView(scene); 

        // Le widget qui charge le fichier HTML
        // This widget loads an HTML file 
        this.browser = new WebBrowserTestQWebView(this.view);
        QPalette palette = this.browser.palette(); 
        palette.setBrush(QPalette.ColorRole.Base, new QBrush(new QColor(Qt.GlobalColor.transparent)));
        this.browser.setPalette(palette); 
        this.browser.setAttribute(Qt.WidgetAttribute.WA_OpaquePaintEvent, false);

        // On superpose les 2 widgets 
        // The 2 widgets are stacked 
        this.gridLayout.addWidget(this.view, 0, 0); 
        this.gridLayout.addWidget(this.browser, 0, 0); 

        // On attache le tout à la fenêtre principale 
        // Widgets are appended to the main frame 
        QWidget widget = new QWidget(); 
        widget.setLayout(this.gridLayout); 
        this.setCentralWidget(widget); 
        this.setWindowTitle("Hello WebKit");

        // Evénements de la Web view
        // Web view events 
        this.browser.loadStarted.connect(this, "loadStarted()");
        this.browser.loadProgress.connect(this, "loadProgress(int)");
        this.browser.loadFinished.connect(this, "loadDone()");
        this.browser.urlChanged.connect(this, "urlChanged(QUrl)");

        // On charge la page
        // Load the HTML file 
        QApplication.invokeLater(new Runnable()
        {
            @Override
            public void run()
            {
                File htmlFile = new File("resources/interfaces/javascript/test.html"); 

                if (htmlFile.exists())
                    browser.load(new QUrl("file://" + htmlFile.getAbsolutePath()));
                else 
                    System.out.println("Le fichier n'existe pas"); 
            }
        }); 
    }

    public void loadStarted() 
    {
        System.out.println("Load started"); 
    }

    public void loadDone() 
    {
        WebBrowserTestJavascript javascript = new WebBrowserTestJavascript(); 
        this.browser.page().mainFrame().addToJavaScriptWindowObject("javaObject", javascript); 
        this.browser.page().mainFrame().evaluateJavaScript("fromJavaToJavascript()"); 
    }

    public void loadProgress(int x) 
    {
        System.out.println("Loading: " + x + " %"); 
    }

    public void urlChanged(QUrl url) 
    {
        System.out.println("Url changed : " + url); 
    }
}

QWebView から継承されたクラス:

public class WebBrowserTestQWebView extends QWebView
{
    @Override
    public void paintEvent(QPaintEvent event)
    {
        // On tente d'effacer l'ancien affichage de la web view et c'est là que ça coince. 
        // Clears the previous web view rendering and here is the problem 
        QPainter painter = new QPainter(this); 
        painter.setCompositionMode(QPainter.CompositionMode.CompositionMode_Source); 
        painter.fillRect(event.rect(), Qt.GlobalColor.transparent); 
        painter.setCompositionMode(QPainter.CompositionMode.CompositionMode_SourceOver); 

        super.paintEvent(event); 
    }
}

前もって感謝します。:)

4

1 に答える 1

1

私はついに自分で解決策を見つけました。本当に簡単でした。^^'

Web ビューの背景を透明に設定するコードを WebBrowserTestFrame クラスから削除し、WebBrowserTestQWebView クラスの paintEvent メソッドに配置しました。このような :

    public class WebBrowserTestQWebView extends QWebView
{
    @Override
    public void paintEvent(QPaintEvent event)
    {
        QPalette palette = this.palette(); 
        palette.setBrush(QPalette.ColorRole.Base, new QBrush(new QColor(Qt.GlobalColor.transparent)));
        this.setPalette(palette); 
        this.setAttribute(Qt.WidgetAttribute.WA_OpaquePaintEvent, false);
        super.paintEvent(event); 
    }
}

そして、それは私のために働きます!:D

これが最終的に期待されるレンダリングです

于 2016-12-20T21:36:06.650 に答える