前提・実現したいこと
htmlで遊べるゲームを作るためのエディタをhtml+TypeScriptで作っています。
テクスチャを分割して、独自のSpriteオブジェクトとして保存する機能を作ろうと思いました。
とりあえず、新規ウインドウに画像を表示してサイズをInputElementの初期値として登録したいです。
発生している問題・エラーメッセージ
エディタ本体のウインドウでは見ずらいと感じたので、サブウインドウとして小さな別窓を開いて、別のhtmlファイルを読み込ませて表示するところまではできたのですが、そのサブウインドウのloadイベントに登録した関数が起動しなくて困っています。
そもそも、webpack-dev-server --mode=developmentコマンドでローカルホストを使って実行するとちゃんと、loadイベントが起動するんです。
webpackコマンドでjsファイルを作成させると、イベントが通らなくなります。
エラーコード等が表示されず、よくわかりません。
該当のソースコード
少し長いですが、関係ありそうなところは全て載せます。
ソース
TypeScript
1/*main.ts*/ 2 3import GameEditorManager from "./GameEditorManager" 4 5window.onload=function() 6{ 7 GameEditorManager.Run(); 8} 9
TypeScript
1/*GameEditorManager.ts*/ 2/*インポート*/ 3//---------------------------------------------------------------------------------------------------------------------------- 4import {TextureSplitting} from "./TextureSplitting" 5 6//---------------------------------------------------------------------------------------------------------------------------- 7 8/*本体*/ 9//---------------------------------------------------------------------------------------------------------------------------- 10class GameEditorManager 11{ 12 /*変数*/ 13 private gameView:HTMLCanvasElement|null; 14 private gameCameraView:HTMLCanvasElement|null; 15 constructor() 16 { 17 this.gameView=document.createElement("canvas"); 18 this.gameCameraView=document.createElement("canvas"); 19 20 this.gameView.width=innerWidth*0.4; 21 this.gameView.height=innerHeight; 22 23 this.gameCameraView.width=innerWidth*0.4; 24 this.gameCameraView.height=innerHeight; 25 26 27 let gamecon:CanvasRenderingContext2D=<CanvasRenderingContext2D>this.gameView.getContext("2d"); 28 gamecon.fillStyle="black"; 29 gamecon.fillRect(0,0,innerWidth*0.4,innerHeight); 30 31 let cameracon:CanvasRenderingContext2D=<CanvasRenderingContext2D>this.gameCameraView.getContext("2d"); 32 cameracon.fillStyle="#a0d8ef"; 33 cameracon.fillRect(0,0,innerWidth*0.4,innerHeight); 34 35 document.body.appendChild(this.gameCameraView); 36 document.body.appendChild(this.gameView); 37 38 this.DADSetup(); 39 } 40 41 private DADSetup() 42 { 43 document.body.ondragover=(e:DragEvent)=> 44 { 45 e.stopPropagation(); 46 e.preventDefault(); 47 if(e.dataTransfer) 48 { 49 e.dataTransfer.dropEffect="copy"; 50 } 51 52 } 53 54 document.body.ondrop=(e:DragEvent)=> 55 { 56 e.stopPropagation(); 57 e.preventDefault(); 58 if(e.dataTransfer) 59 { 60 let file:FileList=e.dataTransfer.files; 61 62 for(let i:number=0;i<file.length;i++) 63 { 64 let reader:FileReader=new FileReader(); 65 reader.readAsDataURL(file[i]); 66 67 //読み込み中の%表示 68 reader.onprogress=(e:ProgressEvent)=> 69 { 70 //(ロード済みのサイズ)/(ファイルの総サイズ) 71 let sizeRate:number=Math.floor(e.loaded/e.total)*100; 72 console.log(sizeRate+"%"); 73 } 74 75 //読み込み後の表示 76 reader.onload=()=> 77 { 78 let typename:string=file[i].type; 79 let slash:number=typename.indexOf("/"); 80 typename=typename.substr(0,slash); 81 82 if(typename="image") 83 { 84 this.ImageRoad(<string>reader.result) 85 } 86 } 87 88 } 89 } 90 } 91 } 92 93 //表示物の整列初期化 94 public HTMLDesignInit() 95 { 96 97 } 98 99 public Run() 100 { 101 102 } 103 104 private ImageRoad(path:string) 105 { 106 let spriteWindow:Window|null = window.open("./subWindow/SpriteCutterWindow.html",undefined,'top=100,left=100,width=410,height=400'); 107 108 if(!spriteWindow){return;} 109 let convTextureToSprite:TextureSplitting=new TextureSplitting(path,spriteWindow); 110 } 111} 112 113//---------------------------------------------------------------------------------------------------------------------------- 114export default new GameEditorManager();
TypeScript
1 2 3/*TextureSplitting.ts*/ 4/*インポート*/ 5//---------------------------------------------------------------------------------------------------------------------------- 6import {Sprite} from "./GameUtility" 7//---------------------------------------------------------------------------------------------------------------------------- 8 9/*本体*/ 10//---------------------------------------------------------------------------------------------------------------------------- 11export class TextureSplitting 12{ 13 static onLoaded:boolean=false; 14 private dead:boolean; 15 16 private imageID:number; 17 private rectX:number; 18 private rectY:number; 19 20 private sizeX:number; 21 private sizeY:number; 22 23 private sizeXInput:HTMLInputElement|null; 24 private sizeYInput:HTMLInputElement|null; 25 private rectNumXInput:HTMLInputElement|null; 26 private rectNumYInput:HTMLInputElement|null; 27 private canvas:HTMLCanvasElement|null; 28 29 //コンストラクタ 30 constructor(private path:string,private subWindow:Window) 31 { 32 this.dead=false; 33 this.sizeXInput=null; 34 this.sizeYInput=null; 35 this.rectNumXInput=null; 36 this.rectNumYInput=null; 37 this.canvas=null; 38 39 this.imageID=-1; 40 this.rectX=1; 41 this.rectY=1; 42 this.sizeX=1; 43 this.sizeY=1; 44 45 /*ロード時に初期化*/ 46 this.subWindow.addEventListener("load",()=>{this.Init()});//ここが動かない 47 } 48 49 public Init():void 50 { 51 console.log("init"); 52 /*ウインドウの構成物があっているか確認する*/ 53 this.sizeXInput=<HTMLInputElement>this.subWindow.document.getElementById("x"); 54 if(!this.sizeXInput) 55 { 56 this.dead=true; 57 console.log("横幅を決めるInputエレメントがありません"); 58 return; 59 } 60 61 this.sizeYInput=<HTMLInputElement>this.subWindow.document.getElementById("y"); 62 if(!this.sizeYInput) 63 { 64 this.dead=true; 65 console.log("縦幅を決めるInputエレメントがありません"); 66 return; 67 } 68 69 this.rectNumXInput=<HTMLInputElement>this.subWindow.document.getElementById("boxNumX"); 70 if(!this.rectNumXInput) 71 { 72 this.dead=true; 73 console.log("ボックスの横の数を決めるエレメントがありません"); 74 return; 75 } 76 77 this.rectNumYInput=<HTMLInputElement>this.subWindow.document.getElementById("boxNumY"); 78 if(!this.rectNumYInput) 79 { 80 this.dead=true; 81 console.log("ボックスの縦の数を決めるエレメントがありません"); 82 return; 83 } 84 85 this.canvas=<HTMLCanvasElement>this.subWindow.document.getElementById("can"); 86 if(!this.canvas) 87 { 88 this.dead=true; 89 console.log("画像表示用のCANVASがありません"); 90 return; 91 } 92 93 /*画像作成*/ 94 let image:HTMLImageElement=new Image(); 95 image.src=this.path; 96 image.onload=()=> 97 { 98 if(!this.canvas){return;} 99 100 this.canvas.width=image.width+2; 101 this.canvas.height=image.height+2; 102 103 let con:CanvasRenderingContext2D=<CanvasRenderingContext2D>this.canvas.getContext("2d"); 104 con.fillStyle="black"; 105 con.fillRect(0,0,this.canvas.width,this.canvas.height); 106 107 con.drawImage(image,0,0,image.width,image.height,1,1,image.width,image.height); 108 109 this.imageID=Sprite.RegisterImage(image); 110 111 this.sizeX=image.width; 112 this.sizeY=image.height; 113 114 con.strokeStyle="#7cfc00" 115 con.strokeRect(0,0,image.width+1,image.height+1); 116 117 if(!this.sizeXInput||!this.sizeYInput){return;} 118 this.sizeXInput.value=this.sizeX.toString(); 119 this.sizeYInput.value=this.sizeY.toString(); 120 } 121 122 123 } 124} 125//----------------------------------------------------------------------------------------------------------------------------
HTML
HTML
1/*ゲームエディタ.HTML*/ 2<!DOCTYPE html> 3<html> 4 <head> 5 <meta charset="utf-8"> 6 <title>タイトル</title> 7 </head> 8 <body topmargin="0" bottommargin="0" leftmargin="0" rightmargin="0" marginheight="0" marginwidth="0"> 9 <script src="bundle.js"></script> 10 </body> 11</html>
HTML
1/*SpriteCutterWindow.html*/ 2<!DOCTYPE html> 3<html> 4<head> 5 <meta charset="utf-8"> 6 <title>SpriteCutter</title> 7</head> 8<body topmargin="0" bottommargin="0" leftmargin="0" rightmargin="0" marginheight="0" marginwidth="0"> 9 X:<input id="x" type="number" value="1" min="1" step="1"> 10 Y:<input id="y" type="number" value="1" min="1" step="1"> 11 BoxNumX:<input id="boxNumX" type="number" value="1",min="1"> 12 BoxNumY:<input id="boxNumY" type="number" value="1",min="1"><br> 13 <canvas id="can"></canvas> 14</body> 15 16<style> 17 input[type=number] 18 { 19 width:3em 20 } 21</style> 22</html>
試したこと
始めはonloadに代入してしまっていたのでaddEventListenerでの登録に切り替えました。
コンソールでのエラーチェック。特にエラーは出ていませんでした。
サブウインドウをそのままコンソールのログに出力してみたところ、代替の要素が以下の文字列で埋められていました。
Exception: DOMException: Blocked a frame with origin "null" from accessing a cross-origin frame. at o (<anonymous>:1:83)
補足情報(FW/ツールのバージョンなど)
開発環境
Google Chorm
package.json↓
{ "name": "pj01j", "version": "1.0.0", "main": "index.js", "scripts": { "build": "webpack --mode=development", "start": "webpack-dev-server --mode=development" }, "keywords": [], "author": "", "license": "ISC", "devDependencies": { "ts-loader": "^8.0.12", "typescript": "^4.1.3", "webpack": "^5.10.1", "webpack-cli": "^3.3.12", "webpack-dev-server": "^3.11.0" }, "dependencies": {}, "description": "" }
webpack.config.json(ネットに転がっていたのをコピペしてきました。)↓
const path = require('path'); module.exports = { // モジュールバンドルを行う起点となるファイルの指定 // 指定できる値としては、ファイル名の文字列や、それを並べた配列やオブジェクト // 下記はオブジェクトとして指定した例 entry: { bundle: './src/main.ts' }, output: { // モジュールバンドルを行った結果を出力する場所やファイル名の指定 // "__dirname"はこのファイルが存在するディレクトリを表すnode.jsで定義済みの定数 path: path.join(__dirname,'dist'), filename: '[name].js' // [name]はentryで記述した名前(この例ではbundle)が入る }, // モジュールとして扱いたいファイルの拡張子を指定する // 例えば「import Foo from './foo'」という記述に対して"foo.ts"という名前のファイルをモジュールとして探す // デフォルトは['.js', '.json'] resolve: { extensions:['.ts','.js'] }, devServer: { // webpack-dev-serverの公開フォルダ contentBase: path.join(__dirname,'dist') }, // モジュールに適用するルールの設定(ここではローダーの設定を行う事が多い) module: { rules: [ { // 拡張子が.tsで終わるファイルに対して、TypeScriptコンパイラを適用する test:/.ts$/,loader:'ts-loader' } ] } }
回答1件
あなたの回答
tips
プレビュー