Last active
February 4, 2021 15:41
-
-
Save croxis/9789973 to your computer and use it in GitHub Desktop.
CEFPython for Panda3D
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| from cefpython3 import cefpython | |
| import os | |
| import sys | |
| from panda3d.core import loadPrcFileData | |
| loadPrcFileData("", "Panda3D example") | |
| loadPrcFileData("", "fullscreen 0") | |
| loadPrcFileData("", "win-size 1024 768") | |
| import direct.directbase.DirectStart | |
| from panda3d.core import CardMaker, Texture | |
| settings = { | |
| "log_severity": cefpython.LOGSEVERITY_INFO, # LOGSEVERITY_VERBOSE | |
| #"log_file": GetApplicationPath("debug.log"), # Set to "" to disable. | |
| "release_dcheck_enabled": True, # Enable only when debugging. | |
| # This directories must be set on Linux | |
| "locales_dir_path": cefpython.GetModuleDirectory()+"/locales", | |
| "resources_dir_path": cefpython.GetModuleDirectory(), | |
| "browser_subprocess_path": "%s/%s" % ( | |
| cefpython.GetModuleDirectory(), "subprocess") | |
| } | |
| class ClientHandler: | |
| """A client handler is required for the browser to do built in callbacks back into the application.""" | |
| browser = None | |
| texture = None | |
| def __init__(self, browser, texture): | |
| self.browser = browser | |
| self.texture = texture | |
| def OnPaint(self, browser, paintElementType, dirtyRects, buffer, width, height): | |
| img = self.texture.modifyRamImage() | |
| if paintElementType == cefpython.PET_POPUP: | |
| print("width=%s, height=%s" % (width, height)) | |
| elif paintElementType == cefpython.PET_VIEW: | |
| img.setData(buffer.GetString(mode="rgba", origin="bottom-left")) | |
| else: | |
| raise Exception("Unknown paintElementType: %s" % paintElementType) | |
| def GetViewRect(self, browser, rect): | |
| width = self.texture.getXSize() | |
| height = self.texture.getYSize() | |
| rect.append(0) | |
| rect.append(0) | |
| rect.append(width) | |
| rect.append(height) | |
| return True | |
| def GetScreenPoint(self, browser, viewX, viewY, screenCoordinates): | |
| print("GetScreenPoint()") | |
| return False | |
| def OnLoadEnd(self, browser, frame, httpStatusCode): | |
| return | |
| self._saveImage() | |
| def OnLoadError(self, browser, frame, errorCode, errorText, failedURL): | |
| print("load error", browser, frame, errorCode, errorText, failedURL) | |
| '''def setBrowserSize(window=None): | |
| """Use something like this to set a full screen UI. Texture and browser size should equal window size. Also remember to set panda textures to ignore power of 2""" | |
| width = int(round(base.win.getXSize() * 0.75)) | |
| height = int(round(base.win.getYSize() * 0.75)) | |
| texture.setXSize(width) | |
| texture.setYSize(height) | |
| browser.WasResized() | |
| #browser.SetSize(cefpython.PET_VIEW, width, height)''' | |
| def messageLoop(task): | |
| cefpython.MessageLoopWork() | |
| return task.cont | |
| cefpython.g_debug = True | |
| cefpython.Initialize(settings) | |
| texture = Texture() | |
| texture.setXSize(1024) | |
| texture.setYSize(1024) | |
| texture.setCompression(Texture.CMOff) | |
| texture.setComponentType(Texture.TUnsignedByte) | |
| texture.setFormat(Texture.FRgba4) | |
| cardMaker = CardMaker("browser2d") | |
| cardMaker.setFrame(-0.75, 0.75, -0.75, 0.75) | |
| node = cardMaker.generate() | |
| #For UI attach to render2d | |
| nodePath = render.attachNewNode(node) | |
| nodePath.setTexture(texture) | |
| windowHandle = base.win.getWindowHandle().getIntHandle() | |
| windowInfo = cefpython.WindowInfo() | |
| #You can pass 0 to parentWindowHandle, but then some things like context menus and plugins may not display correctly. | |
| windowInfo.SetAsOffscreen(windowHandle) | |
| #windowInfo.SetAsOffscreen(0) | |
| # By default window rendering is 30 fps, let's change | |
| # it to 60 for better user experience when scrolling. | |
| browserSettings = {} | |
| # Using non about:blank in constructor results in error before render handler callback is set. | |
| # Either set it before/during construction, or set it after then call LoadURL after it is set. | |
| browser = cefpython.CreateBrowserSync( | |
| windowInfo, browserSettings, | |
| navigateUrl="http://www.panda3d.org") | |
| browser.SendFocusEvent(True) | |
| browser.SetClientHandler(ClientHandler(browser, texture)) | |
| def on_load_end(*args, **kwargs): return # Example of one kind of call back | |
| browser.SetClientCallback("OnLoadEnd", on_load_end) | |
| browser.WasResized() | |
| ''' IMPORTANT: there is a bug in CEF 3 that causes js bindings to be removed when LoadUrl() is called (see http://www.magpcss.org/ceforum/viewtopic.php?f=6&t=11009). A temporary fix to this bug is to do the navigation through javascript by calling: GetMainFrame().ExecuteJavascript('window.location="http://google.com/"'). ''' | |
| #browser.GetMainFrame().ExecuteJavascript('window.location="http://www.panda3d.org"') | |
| #browser.GetMainFrame().LoadUrl("http://wwww.panda3d.org") | |
| #base.accept("window-event", setBrowserSize) | |
| taskMgr.add(messageLoop, "CefMessageLoop") | |
| run() | |
| cefpython.Shutdown() | |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| """Putting data into a frame""" | |
| from cefpython3 import cefpython | |
| import os | |
| import sys | |
| from panda3d.core import loadPrcFileData | |
| loadPrcFileData("", "Panda3D example -- Set Javascript") | |
| loadPrcFileData("", "fullscreen 0") | |
| loadPrcFileData("", "win-size 1024 768") | |
| import direct.directbase.DirectStart | |
| from panda3d.core import CardMaker, Texture | |
| settings = { | |
| "log_severity": cefpython.LOGSEVERITY_INFO, # LOGSEVERITY_VERBOSE | |
| #"log_file": GetApplicationPath("debug.log"), # Set to "" to disable. | |
| "release_dcheck_enabled": True, # Enable only when debugging. | |
| # This directories must be set on Linux | |
| "locales_dir_path": cefpython.GetModuleDirectory()+"/locales", | |
| "resources_dir_path": cefpython.GetModuleDirectory(), | |
| "browser_subprocess_path": "%s/%s" % ( | |
| cefpython.GetModuleDirectory(), "subprocess") | |
| } | |
| html = """<html> | |
| <body> | |
| <script language="JavaScript"> | |
| function setFrameCount(counter){ | |
| document.getElementById("framecount").innerHTML=counter; | |
| } | |
| </script> | |
| <h1>""" + sys.version + """</h1><br /> | |
| Message: | |
| <script> | |
| document.write(window.sometext); | |
| </script><br /> | |
| Number of Frames: <span id="framecount"></span> | |
| </body> | |
| </html>""" | |
| class ClientHandler: | |
| """A client handler is required for the browser to do built in callbacks back into the application.""" | |
| browser = None | |
| texture = None | |
| def __init__(self, browser, texture): | |
| self.browser = browser | |
| self.texture = texture | |
| def OnPaint(self, browser, paintElementType, dirtyRects, buffer, width, height): | |
| img = self.texture.modifyRamImage() | |
| if paintElementType == cefpython.PET_POPUP: | |
| print("width=%s, height=%s" % (width, height)) | |
| elif paintElementType == cefpython.PET_VIEW: | |
| img.setData(buffer.GetString(mode="rgba", origin="bottom-left")) | |
| else: | |
| raise Exception("Unknown paintElementType: %s" % paintElementType) | |
| def GetViewRect(self, browser, rect): | |
| width = self.texture.getXSize() | |
| height = self.texture.getYSize() | |
| rect.append(0) | |
| rect.append(0) | |
| rect.append(width) | |
| rect.append(height) | |
| return True | |
| def GetScreenPoint(self, browser, viewX, viewY, screenCoordinates): | |
| print("GetScreenPoint()") | |
| return False | |
| def OnLoadEnd(self, browser, frame, httpStatusCode): | |
| return | |
| self._saveImage() | |
| def OnLoadError(self, browser, frame, errorCode, errorText, failedURL): | |
| print("load error", browser, frame, errorCode, errorText, failedURL) | |
| def messageLoop(task): | |
| cefpython.MessageLoopWork() | |
| """Call a specific javascript function and pass any parameters to it.""" | |
| browser.GetMainFrame().CallFunction("setFrameCount", task.frame) | |
| return task.cont | |
| def setVariable(name, value): | |
| """Sets a javascript value in the main frame""" | |
| jsBindings.SetProperty(name, value) | |
| cefpython.g_debug = True | |
| cefpython.Initialize(settings) | |
| texture = Texture() | |
| texture.setXSize(1024) | |
| texture.setYSize(1024) | |
| texture.setCompression(Texture.CMOff) | |
| texture.setComponentType(Texture.TUnsignedByte) | |
| texture.setFormat(Texture.FRgba4) | |
| cardMaker = CardMaker("browser2d") | |
| cardMaker.setFrame(-0.75, 0.75, -0.75, 0.75) | |
| node = cardMaker.generate() | |
| #For UI attach to render2d | |
| nodePath = render.attachNewNode(node) | |
| nodePath.setTexture(texture) | |
| windowHandle = base.win.getWindowHandle().getIntHandle() | |
| windowInfo = cefpython.WindowInfo() | |
| #You can pass 0 to parentWindowHandle, but then some things like context menus and plugins may not display correctly. | |
| windowInfo.SetAsOffscreen(windowHandle) | |
| #windowInfo.SetAsOffscreen(0) | |
| browserSettings = {} | |
| # Using non about:blank in constructor results in error before render handler callback is set. | |
| # Either set it before/during construction, or set it after then call LoadURL after it is set. | |
| browser = cefpython.CreateBrowserSync( | |
| windowInfo, browserSettings, | |
| navigateUrl="http://www.panda3d.org") | |
| browser.SendFocusEvent(True) | |
| browser.SetClientHandler(ClientHandler(browser, texture)) | |
| def on_load_end(*args, **kwargs): return # Example of one kind of call back | |
| browser.SetClientCallback("OnLoadEnd", on_load_end) | |
| browser.GetMainFrame().LoadString(html, "http://fake") | |
| browser.WasResized() | |
| ''' IMPORTANT: there is a bug in CEF 3 that causes js bindings to be removed when LoadUrl() is called (see http://www.magpcss.org/ceforum/viewtopic.php?f=6&t=11009). A temporary fix to this bug is to do the navigation through javascript by calling: GetMainFrame().ExecuteJavascript('window.location="http://google.com/"'). ''' | |
| #browser.GetMainFrame().ExecuteJavascript('window.location="http://www.panda3d.org"') | |
| #browser.GetMainFrame().LoadUrl("http://wwww.panda3d.org") | |
| #base.accept("window-event", setBrowserSize) | |
| """Sets up bindings to access javascript variabels and functions. Also is used for calling back into python.""" | |
| jsBindings = cefpython.JavascriptBindings(bindToFrames=False, bindToPopups=True) | |
| jsBindings.SetProperty("sometext", "A message from python land! Hello!") | |
| browser.SetJavascriptBindings(jsBindings) | |
| taskMgr.add(messageLoop, "CefMessageLoop") | |
| run() | |
| cefpython.Shutdown() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment