6NB2PU2F64XDSURKYMBECKEN7ZQ63RMDN2GL5CP74YA6HE4K3TTAC 3LZ4UD3N3VL3ZVTS25P3QKICCM4VXODR2OHTE5GPS2WGG3WRILYQC J47EV2H73JKATJDKBZZNSIGAPC7G5X5DCWZ7YDN55XUNPYPS54TQC FWV2VPFI3VIQXMY4LZ266AHP7PKBSKVMSJ6ERABTUFXCTFVEMFZQC 5LXKHEZNPK7RBJ33RTHN4Q3V5OUTM4WXZ477UOHTA34RNBPUN5DAC UPEYNW7CF54F2XHS3SZ7NDZTFAUGJL4OJ6FHLKC7M6XLXL3M2L4QC 7MCTB5G2W6IB7JQXGO2HCMRHBUYIOKXI4MBODKLAJIK66EMLC5ZQC PIULOOUAM6OIXXSEIAETIVEEEIQ45DEQXB6QHTDSNVQDH57TGTUAC P7KZ25R4CNS4PZITRWPBVXRFSLY5TKCOFO6U3SDKX45ITNVU773QC YLOKW6ERT2XEQG4T6GBPSBCQWVIHWAKBESCXJBKMQBSDXV3C2ACQC FERLNXU2QISSKOUBSPABB2ERHOWHQRI2GVKDJ352Y4B2FUXBRGRQC PI6D6Y5EHSXHSILBYHKRKXWXZ6H6JOR5ZTP44CXBW4LUUIREY7OQC E6LXIE7VBUGCR762DFTHYZISEWYFV5E3NM3MGLT5Z7YFQQ5GTYRQC QHVOZBISIQ3E3P5F6GGKWVDSXC4OA23HCIH2OMXEVGXKSF5W4APAC 5FNNIOUNDS5SG75A4ZR6VY7DS6WU2GNNCOSSHX34RFTRB7LJ3D2QC LX2ZVNAYX2FRCEIJ6XBCBILB3O7YT52AP56QDWCCGLATFCEB7KHQC C56DYYC72SFNR6BSKCOVDY2QW6XNP66EUGGKCBROTCFJVQDB4FUAC DB6B3MEDBTEEIS6KOSJH7L5JFXKDMATJARZ6AR7TF2HCCKTFRZJQC XTPX4PYLPGJAEK52LYOYHLVRCL7N5FFAEY4E3OL23LOWLYPLCILQC V3QTRVNR5EVDZ2O2WRK7ZCVKSGGYBSNILH44OWXKOJK2ME5JC7UQC KNH5OGCTL3YCOQQPA32M76SGWHGHAPQRIZ7S2CBC5DGIEV32SOYQC 3DZWNZUZGMHJH3JL3H7KN746C6XVNBRBFHBSVSB5AH7YYUFVYVDAC 5R7SS5AWSCPT4WWCS5WUBRFULLXATBZW4FFPBT6S5EYJVEWKL5NQC PI4VBCLQL4EGBUJ7B2FA3GH25B22CUIOMOZZ7GNPYCS5OSLIRKPAC LU257USNNJW57H5M5E46IB2E3IBFNYBXB6EPEM63BYC23NNVHCFQC RLLNOBJM5LB446HWBUNDLNMG35PTUFRBRRVNHMFTX7CMQC4JSXUQC UR5RFMWCD455OQZMTDQ2MSVJUPBNEUQHOBJ2UJBDWVHRJ4SOA5NAC TLRGOVFX6KIWQSWRPXS73WW4EHJQ5L5W5NYMO6UM2EF2H3EPAHHQC Y62XTAEHAC5MNJELNKACRLEVBUU2MKYKFPHB5M2S5X46B4EI2JJQC GBEGPEQZPTMSSEHTK5MKHFYCA5ZFGYCYURMQGWC4SJSWIPHNSPHAC F2MO5GK2AE5RLTNGFTPRGRGTJBNN5OTRXYNGDIY7QIPF5LXAAXCQC 632SZPUQC6KX3CDZLYWV22OSFIOG66CJ7PONRNTXYTFLQX3JFFXQC "exclude": ["node_modules", "dist", "test"],"compilerOptions": {/* Visit https://aka.ms/tsconfig.json to read more about this file */
"exclude": ["node_modules", "dist", "test"],"compilerOptions": {/* Visit https://aka.ms/tsconfig.json to read more about this file */
/* Projects */"incremental": true, /* Enable incremental compilation */// "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */// "tsBuildInfoFile": "./", /* Specify the folder for .tsbuildinfo incremental compilation files. */// "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects */// "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */// "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */
/* Projects */"incremental": true /* Enable incremental compilation */,// "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */// "tsBuildInfoFile": "./", /* Specify the folder for .tsbuildinfo incremental compilation files. */// "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects */// "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */// "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */
/* Language and Environment */"target": "es2020" /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */,"lib": ["es2020"] /* Specify a set of bundled library declaration files that describe the target runtime environment. */,"jsx": "react" /* Specify what JSX code is generated. */,// "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */// "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */// "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h' */// "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */// "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using `jsx: react-jsx*`.` */// "reactNamespace": "", /* Specify the object invoked for `createElement`. This only applies when targeting `react` JSX emit. */// "noLib": true, /* Disable including any library files, including the default lib.d.ts. */// "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */
/* Language and Environment */"target": "es2020" /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */,"lib": ["es2020"] /* Specify a set of bundled library declaration files that describe the target runtime environment. */,"jsx": "react" /* Specify what JSX code is generated. */,// "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */// "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */// "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h' */// "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */// "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using `jsx: react-jsx*`.` */// "reactNamespace": "", /* Specify the object invoked for `createElement`. This only applies when targeting `react` JSX emit. */// "noLib": true, /* Disable including any library files, including the default lib.d.ts. */// "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */
/* Modules */"module": "es2020" /* Specify what module code is generated. */,// "rootDir": "./", /* Specify the root folder within your source files. */"moduleResolution": "node" /* Specify how TypeScript looks up a file from a given module specifier. */,// "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */// "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */// "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */// "typeRoots": [], /* Specify multiple folders that act like `./node_modules/@types`. */"types": ["@cloudflare/workers-types","@types/jest",] /* Specify type package names to be included without being referenced in a source file. */,// "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */"resolveJsonModule": true /* Enable importing .json files */,// "noResolve": true, /* Disallow `import`s, `require`s or `<reference>`s from expanding the number of files TypeScript should add to a project. */
/* Modules */"module": "es2020" /* Specify what module code is generated. */,// "rootDir": "./", /* Specify the root folder within your source files. */"moduleResolution": "node" /* Specify how TypeScript looks up a file from a given module specifier. */,// "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */// "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */// "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */// "typeRoots": [], /* Specify multiple folders that act like `./node_modules/@types`. */"types": ["@cloudflare/workers-types","@types/jest"] /* Specify type package names to be included without being referenced in a source file. */,// "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */"resolveJsonModule": true /* Enable importing .json files */,// "noResolve": true, /* Disallow `import`s, `require`s or `<reference>`s from expanding the number of files TypeScript should add to a project. */
/* JavaScript Support */"allowJs": true /* Allow JavaScript files to be a part of your program. Use the `checkJS` option to get errors from these files. */,"checkJs": false /* Enable error reporting in type-checked JavaScript files. */,// "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from `node_modules`. Only applicable with `allowJs`. */
/* JavaScript Support */"allowJs": true /* Allow JavaScript files to be a part of your program. Use the `checkJS` option to get errors from these files. */,"checkJs": false /* Enable error reporting in type-checked JavaScript files. */,// "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from `node_modules`. Only applicable with `allowJs`. */
/* Emit */// "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */// "declarationMap": true, /* Create sourcemaps for d.ts files. */// "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */// "sourceMap": true, /* Create source map files for emitted JavaScript files. */// "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If `declaration` is true, also designates a file that bundles all .d.ts output. */// "outDir": "./", /* Specify an output folder for all emitted files. */// "removeComments": true, /* Disable emitting comments. */"noEmit": true /* Disable emitting files from a compilation. */,// "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */// "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types */// "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */// "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */// "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */// "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */// "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */// "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */// "newLine": "crlf", /* Set the newline character for emitting files. */// "stripInternal": true, /* Disable emitting declarations that have `@internal` in their JSDoc comments. */// "noEmitHelpers": true, /* Disable generating custom helper functions like `__extends` in compiled output. */// "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */// "preserveConstEnums": true, /* Disable erasing `const enum` declarations in generated code. */// "declarationDir": "./", /* Specify the output directory for generated declaration files. */// "preserveValueImports": true, /* Preserve unused imported values in the JavaScript output that would otherwise be removed. */
/* Emit */// "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */// "declarationMap": true, /* Create sourcemaps for d.ts files. */// "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */// "sourceMap": true, /* Create source map files for emitted JavaScript files. */// "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If `declaration` is true, also designates a file that bundles all .d.ts output. */// "outDir": "./", /* Specify an output folder for all emitted files. */// "removeComments": true, /* Disable emitting comments. */"noEmit": true /* Disable emitting files from a compilation. */,// "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */// "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types */// "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */// "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */// "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */// "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */// "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */// "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */// "newLine": "crlf", /* Set the newline character for emitting files. */// "stripInternal": true, /* Disable emitting declarations that have `@internal` in their JSDoc comments. */// "noEmitHelpers": true, /* Disable generating custom helper functions like `__extends` in compiled output. */// "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */// "preserveConstEnums": true, /* Disable erasing `const enum` declarations in generated code. */// "declarationDir": "./", /* Specify the output directory for generated declaration files. */// "preserveValueImports": true, /* Preserve unused imported values in the JavaScript output that would otherwise be removed. */
/* Interop Constraints */"isolatedModules": true /* Ensure that each file can be safely transpiled without relying on other imports. */,"allowSyntheticDefaultImports": true /* Allow 'import x from y' when a module doesn't have a default export. */,"esModuleInterop": true /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables `allowSyntheticDefaultImports` for type compatibility. */,// "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */"forceConsistentCasingInFileNames": true /* Ensure that casing is correct in imports. */,
/* Interop Constraints */"isolatedModules": true /* Ensure that each file can be safely transpiled without relying on other imports. */,"allowSyntheticDefaultImports": true /* Allow 'import x from y' when a module doesn't have a default export. */,"esModuleInterop": true /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables `allowSyntheticDefaultImports` for type compatibility. */,// "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */"forceConsistentCasingInFileNames": true /* Ensure that casing is correct in imports. */,
/* Type Checking */"strict": true /* Enable all strict type-checking options. */,// "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied `any` type.. */// "strictNullChecks": true, /* When type checking, take into account `null` and `undefined`. */// "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */// "strictBindCallApply": true, /* Check that the arguments for `bind`, `call`, and `apply` methods match the original function. */// "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */// "noImplicitThis": true, /* Enable error reporting when `this` is given the type `any`. */// "useUnknownInCatchVariables": true, /* Type catch clause variables as 'unknown' instead of 'any'. */// "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */// "noUnusedLocals": true, /* Enable error reporting when a local variables aren't read. */// "noUnusedParameters": true, /* Raise an error when a function parameter isn't read */// "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */// "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */// "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */// "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */// "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */// "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type */// "allowUnusedLabels": true, /* Disable error reporting for unused labels. */// "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */
/* Type Checking */"strict": true /* Enable all strict type-checking options. */,// "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied `any` type.. */// "strictNullChecks": true, /* When type checking, take into account `null` and `undefined`. */// "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */// "strictBindCallApply": true, /* Check that the arguments for `bind`, `call`, and `apply` methods match the original function. */// "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */// "noImplicitThis": true, /* Enable error reporting when `this` is given the type `any`. */// "useUnknownInCatchVariables": true, /* Type catch clause variables as 'unknown' instead of 'any'. */// "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */// "noUnusedLocals": true, /* Enable error reporting when a local variables aren't read. */// "noUnusedParameters": true, /* Raise an error when a function parameter isn't read */// "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */// "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */// "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */// "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */// "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */// "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type */// "allowUnusedLabels": true, /* Disable error reporting for unused labels. */// "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */
/* Completeness */// "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */"skipLibCheck": true /* Skip type checking all .d.ts files. */}
/* Completeness */// "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */"skipLibCheck": true /* Skip type checking all .d.ts files. */}
this.state.storage.put(`pi.${id}`,{name: json.CreateProjet.name,porteur: json.CreateProjet.porteur,tel: json.CreateProjet.tel,adresse: json.CreateProjet.adresse,simulation: json.CreateProjet.simulation,t: Date.now(),})console.log("saved", id)
this.state.storage.put(`pi.${id}`, {name: json.CreateProjet.name,porteur: json.CreateProjet.porteur,tel: json.CreateProjet.tel,adresse: json.CreateProjet.adresse,simulation: json.CreateProjet.simulation,t: Date.now(),})console.log('saved', id)
if ("SaveProjet" in json) {let x: undefined | Grain.GetProjetResp = await this.state.storage.get(`pi.${json.SaveProjet.id}`)
if ('SaveProjet' in json) {let x: undefined | Grain.GetProjetResp =await this.state.storage.get(`pi.${json.SaveProjet.id}`)
if ("GetProjet" in json) {let resp = <Grain.GetProjetResp> await this.state.storage.get(`pi.${json.GetProjet}`
if ('GetProjet' in json) {let resp = <Grain.GetProjetResp>(await this.state.storage.get(`pi.${json.GetProjet}`)
if ("DelProjet" in json) {let t: undefined | { t: string } = await this.state.storage.get(`pi.${json.DelProjet.id}`)if(t) {await this.state.storage.delete(`pi.${json.DelProjet.id}`)
if ('DelProjet' in json) {let t: undefined | { t: string } = await this.state.storage.get(`pi.${json.DelProjet.id}`)if (t) {await this.state.storage.delete(`pi.${json.DelProjet.id}`)
let keys: Map<string, { id: string, name: string, simulation: Grain.SimulationCommunaute, t: number }> = await this.state.storage.list(opts)
let keys: Map<string,{id: stringname: stringsimulation: Grain.SimulationCommunautet: number}> = await this.state.storage.list(opts)
"exclude": ["node_modules", "dist", "test"],"compilerOptions": {/* Visit https://aka.ms/tsconfig.json to read more about this file */
"exclude": ["node_modules", "dist", "test"],"compilerOptions": {/* Visit https://aka.ms/tsconfig.json to read more about this file */
/* Projects */"incremental": true, /* Enable incremental compilation */// "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */// "tsBuildInfoFile": "./", /* Specify the folder for .tsbuildinfo incremental compilation files. */// "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects */// "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */// "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */
/* Projects */"incremental": true /* Enable incremental compilation */,// "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */// "tsBuildInfoFile": "./", /* Specify the folder for .tsbuildinfo incremental compilation files. */// "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects */// "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */// "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */
/* Language and Environment */"target": "es2020" /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */,"lib": ["es2020"] /* Specify a set of bundled library declaration files that describe the target runtime environment. */,"jsx": "react" /* Specify what JSX code is generated. */,// "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */// "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */// "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h' */// "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */// "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using `jsx: react-jsx*`.` */// "reactNamespace": "", /* Specify the object invoked for `createElement`. This only applies when targeting `react` JSX emit. */// "noLib": true, /* Disable including any library files, including the default lib.d.ts. */// "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */
/* Language and Environment */"target": "es2020" /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */,"lib": ["es2020"] /* Specify a set of bundled library declaration files that describe the target runtime environment. */,"jsx": "react" /* Specify what JSX code is generated. */,// "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */// "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */// "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h' */// "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */// "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using `jsx: react-jsx*`.` */// "reactNamespace": "", /* Specify the object invoked for `createElement`. This only applies when targeting `react` JSX emit. */// "noLib": true, /* Disable including any library files, including the default lib.d.ts. */// "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */
/* Modules */"module": "es2020" /* Specify what module code is generated. */,// "rootDir": "./", /* Specify the root folder within your source files. */"moduleResolution": "node" /* Specify how TypeScript looks up a file from a given module specifier. */,// "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */// "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */// "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */// "typeRoots": [], /* Specify multiple folders that act like `./node_modules/@types`. */"types": ["@cloudflare/workers-types","@types/jest",] /* Specify type package names to be included without being referenced in a source file. */,// "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */"resolveJsonModule": true /* Enable importing .json files */,// "noResolve": true, /* Disallow `import`s, `require`s or `<reference>`s from expanding the number of files TypeScript should add to a project. */
/* Modules */"module": "es2020" /* Specify what module code is generated. */,// "rootDir": "./", /* Specify the root folder within your source files. */"moduleResolution": "node" /* Specify how TypeScript looks up a file from a given module specifier. */,// "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */// "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */// "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */// "typeRoots": [], /* Specify multiple folders that act like `./node_modules/@types`. */"types": ["@cloudflare/workers-types","@types/jest"] /* Specify type package names to be included without being referenced in a source file. */,// "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */"resolveJsonModule": true /* Enable importing .json files */,// "noResolve": true, /* Disallow `import`s, `require`s or `<reference>`s from expanding the number of files TypeScript should add to a project. */
/* JavaScript Support */"allowJs": true /* Allow JavaScript files to be a part of your program. Use the `checkJS` option to get errors from these files. */,"checkJs": false /* Enable error reporting in type-checked JavaScript files. */,// "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from `node_modules`. Only applicable with `allowJs`. */
/* JavaScript Support */"allowJs": true /* Allow JavaScript files to be a part of your program. Use the `checkJS` option to get errors from these files. */,"checkJs": false /* Enable error reporting in type-checked JavaScript files. */,// "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from `node_modules`. Only applicable with `allowJs`. */
/* Emit */// "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */// "declarationMap": true, /* Create sourcemaps for d.ts files. */// "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */// "sourceMap": true, /* Create source map files for emitted JavaScript files. */// "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If `declaration` is true, also designates a file that bundles all .d.ts output. */// "outDir": "./", /* Specify an output folder for all emitted files. */// "removeComments": true, /* Disable emitting comments. */"noEmit": true /* Disable emitting files from a compilation. */,// "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */// "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types */// "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */// "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */// "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */// "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */// "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */// "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */// "newLine": "crlf", /* Set the newline character for emitting files. */// "stripInternal": true, /* Disable emitting declarations that have `@internal` in their JSDoc comments. */// "noEmitHelpers": true, /* Disable generating custom helper functions like `__extends` in compiled output. */// "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */// "preserveConstEnums": true, /* Disable erasing `const enum` declarations in generated code. */// "declarationDir": "./", /* Specify the output directory for generated declaration files. */// "preserveValueImports": true, /* Preserve unused imported values in the JavaScript output that would otherwise be removed. */
/* Emit */// "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */// "declarationMap": true, /* Create sourcemaps for d.ts files. */// "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */// "sourceMap": true, /* Create source map files for emitted JavaScript files. */// "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If `declaration` is true, also designates a file that bundles all .d.ts output. */// "outDir": "./", /* Specify an output folder for all emitted files. */// "removeComments": true, /* Disable emitting comments. */"noEmit": true /* Disable emitting files from a compilation. */,// "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */// "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types */// "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */// "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */// "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */// "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */// "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */// "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */// "newLine": "crlf", /* Set the newline character for emitting files. */// "stripInternal": true, /* Disable emitting declarations that have `@internal` in their JSDoc comments. */// "noEmitHelpers": true, /* Disable generating custom helper functions like `__extends` in compiled output. */// "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */// "preserveConstEnums": true, /* Disable erasing `const enum` declarations in generated code. */// "declarationDir": "./", /* Specify the output directory for generated declaration files. */// "preserveValueImports": true, /* Preserve unused imported values in the JavaScript output that would otherwise be removed. */
/* Interop Constraints */"isolatedModules": true /* Ensure that each file can be safely transpiled without relying on other imports. */,"allowSyntheticDefaultImports": true /* Allow 'import x from y' when a module doesn't have a default export. */,"esModuleInterop": true /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables `allowSyntheticDefaultImports` for type compatibility. */,// "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */"forceConsistentCasingInFileNames": true /* Ensure that casing is correct in imports. */,
/* Interop Constraints */"isolatedModules": true /* Ensure that each file can be safely transpiled without relying on other imports. */,"allowSyntheticDefaultImports": true /* Allow 'import x from y' when a module doesn't have a default export. */,"esModuleInterop": true /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables `allowSyntheticDefaultImports` for type compatibility. */,// "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */"forceConsistentCasingInFileNames": true /* Ensure that casing is correct in imports. */,
/* Type Checking */"strict": true /* Enable all strict type-checking options. */,// "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied `any` type.. */// "strictNullChecks": true, /* When type checking, take into account `null` and `undefined`. */// "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */// "strictBindCallApply": true, /* Check that the arguments for `bind`, `call`, and `apply` methods match the original function. */// "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */// "noImplicitThis": true, /* Enable error reporting when `this` is given the type `any`. */// "useUnknownInCatchVariables": true, /* Type catch clause variables as 'unknown' instead of 'any'. */// "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */// "noUnusedLocals": true, /* Enable error reporting when a local variables aren't read. */// "noUnusedParameters": true, /* Raise an error when a function parameter isn't read */// "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */// "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */// "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */// "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */// "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */// "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type */// "allowUnusedLabels": true, /* Disable error reporting for unused labels. */// "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */
/* Type Checking */"strict": true /* Enable all strict type-checking options. */,// "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied `any` type.. */// "strictNullChecks": true, /* When type checking, take into account `null` and `undefined`. */// "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */// "strictBindCallApply": true, /* Check that the arguments for `bind`, `call`, and `apply` methods match the original function. */// "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */// "noImplicitThis": true, /* Enable error reporting when `this` is given the type `any`. */// "useUnknownInCatchVariables": true, /* Type catch clause variables as 'unknown' instead of 'any'. */// "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */// "noUnusedLocals": true, /* Enable error reporting when a local variables aren't read. */// "noUnusedParameters": true, /* Raise an error when a function parameter isn't read */// "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */// "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */// "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */// "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */// "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */// "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type */// "allowUnusedLabels": true, /* Disable error reporting for unused labels. */// "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */
/* Completeness */// "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */"skipLibCheck": true /* Skip type checking all .d.ts files. */}
/* Completeness */// "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */"skipLibCheck": true /* Skip type checking all .d.ts files. */}
console.log(coords);let u = `https://re.jrc.ec.europa.eu/api/seriescalc?lat=${coords.lat}&lon=${coords.lng}&startyear=2016&pvcalculation=1&peakpower=1&loss=${coords.loss || 14}&outputformat=json`
console.log(coords)let u = `https://re.jrc.ec.europa.eu/api/seriescalc?lat=${coords.lat}&lon=${coords.lng}&startyear=2016&pvcalculation=1&peakpower=1&loss=${coords.loss || 14}&outputformat=json`
import type { PlaywrightTestConfig } from '@playwright/test';const config: PlaywrightTestConfig = {webServer: {command: 'npm run build && npm run preview',port: 4173},testDir: 'tests'};export default config;
"allowJs": true,"checkJs": true,"esModuleInterop": true,"forceConsistentCasingInFileNames": true,"resolveJsonModule": true,"skipLibCheck": true,"sourceMap": true,"strict": true,
"allowJs": true,"checkJs": true,"esModuleInterop": true,"forceConsistentCasingInFileNames": true,"resolveJsonModule": true,"skipLibCheck": true,"sourceMap": true,"strict": true,
import adapter from '@sveltejs/adapter-cloudflare-workers';import preprocess from 'svelte-preprocess';import { vitePreprocess } from '@sveltejs/kit/vite';
import adapter from '@sveltejs/adapter-cloudflare-workers'import preprocess from 'svelte-preprocess'import { vitePreprocess } from '@sveltejs/kit/vite'
import { browser } from '$app/environment';import { onMount, tick } from 'svelte';import { assets as a } from '$app/paths'import type { Grain } from '../../../grain-types'export let lat: number = 45export let lng: number = 7export let puissance: numberexport let prmsFeature: boolean = falseexport let id: string = ""export let prms: Grain.Prm [] = []export let prodWeekly: number[] = []export let maxProd: number = 0export let assets = a as stringexport let server = "https://coturnix.fr"let consentement = false
import { browser } from '$app/environment'import { onMount, tick } from 'svelte'import { assets as a } from '$app/paths'import type { Grain } from '../../../grain-types'export let lat: number = 45export let lng: number = 7export let puissance: numberexport let prmsFeature: boolean = falseexport let id: string = ''export let prms: Grain.Prm[] = []export let prodWeekly: number[] = []export let maxProd: number = 0export let assets = a as stringexport let server = 'https://coturnix.fr'let consentement = false
let pvgis: null | {inputs: {location:{lat:number,lng:number}},outputs: { hourly: {time: string, "G(i)": number, P: number, T2m: number, H_sun: number, Int: number}[]}} = null
let pvgis: null | {inputs: { location: { lat: number; lng: number } }outputs: {hourly: {time: string'G(i)': numberP: numberT2m: numberH_sun: numberInt: number}[]}} = null
$: {initialised && updatePlot(puissance)}
$: {initialised && updatePlot(puissance)}
onMount(async () => {//@ts-ignorePlotly = await import('plotly.js-dist')await updatePlot(puissance)initialised = true})
onMount(async () => {//@ts-ignorePlotly = await import('plotly.js-dist')await updatePlot(puissance)initialised = true})
let darkMode = false;if(browser) {darkMode = window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches;window.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', event => {darkMode = !!event.matchesredraw()});}
let darkMode = falseif (browser) {darkMode =window.matchMedia &&window.matchMedia('(prefers-color-scheme: dark)').matcheswindow.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', (event) => {darkMode = !!event.matchesredraw()})}
let profils: Record<string, { profils: string[]}> = {"Résidentiel ≤6kVA":{"profils":[ "RES1-P1" ]},
let profils: Record<string, { profils: string[] }> = {'Résidentiel ≤6kVA': {profils: ['RES1-P1'],},
async function delProfil(i: number) {pr.splice(i, 1)pr = prawait updatePlot(puissance)}
async function delProfil(i: number) {pr.splice(i, 1)pr = prawait updatePlot(puissance)}
async function profile(name: string): Promise<{ coefs: number[], total: number }> {prm_loading = trueawait tick()let profiles = await Promise.all(profils[name].profils.map(async (x) => {let resp = await fetch(`${assets}/profiles/${x}.csv`,)return await resp.text()}))prm_loading = falseawait tick()
async function profile(name: string): Promise<{ coefs: number[]; total: number }> {prm_loading = trueawait tick()let profiles = await Promise.all(profils[name].profils.map(async (x) => {let resp = await fetch(`${assets}/profiles/${x}.csv`)return await resp.text()}))prm_loading = falseawait tick()
let annee = []let total = 0let file = 0;for(let p of profiles) {let l = 0;for(let line of p.split('\n')) {if(!line) {continue}const col = line.split(',')// const week = parseInt(col[0])// const dow = parseInt(col[1])const cs = parseFloat(col[2])const cj = parseFloat(col[3])for(let i = 0; i < 48; i++) {let ch = parseFloat(col[5+i])const c = cs * cj * chif(file == 0) {annee.push(c)} else {annee[l] += c}total += c}l += 1}file += 1}return { coefs: annee, total }}
let annee = []let total = 0let file = 0for (let p of profiles) {let l = 0for (let line of p.split('\n')) {if (!line) {continue}const col = line.split(',')// const week = parseInt(col[0])// const dow = parseInt(col[1])const cs = parseFloat(col[2])const cj = parseFloat(col[3])for (let i = 0; i < 48; i++) {let ch = parseFloat(col[5 + i])const c = cs * cj * chif (file == 0) {annee.push(c)} else {annee[l] += c}total += c}l += 1}file += 1}return { coefs: annee, total }}
async function refresh(event: SubmitEvent) {event.preventDefault()if(prms) {prm_loading = trueawait tick()const resp = await fetch(`${server}/api/grain/projet/${id || "nouveau"}/prms`, {method: "POST",body: JSON.stringify(prms)})if(resp.ok) {annee = await resp.json()}prm_loading = falseawait tick()} else {erreur = "La liste des PRMs est vide"}await updatePlot(puissance)}
async function refresh(event: SubmitEvent) {event.preventDefault()if (prms) {prm_loading = trueawait tick()const resp = await fetch(`${server}/api/grain/projet/${id || 'nouveau'}/prms`,{method: 'POST',body: JSON.stringify(prms),})if (resp.ok) {annee = await resp.json()}prm_loading = falseawait tick()} else {erreur = 'La liste des PRMs est vide'}await updatePlot(puissance)}
let auto = 0let totalProd = 0let totalConso = 0let soleil = {hourly: {x: <string[]>[],y: <number[]>[],},daily: {x: <string[]>[],y: <number[]>[],},weekly: {x: <string[]>[],y: <number[]>[],},x: <string[]>[],y: <number[]>[],type: 'bar',line: {color: "#ffbf00",width: 1,},marker: {color: "#ffbf00",width: 1,},name: "Production solaire",bucket: 1,}let somme = {hourly: {x: <string[]>[],y: <number[]>[],},daily: {x: <string[]>[],y: <number[]>[],},weekly: {x: <string[]>[],y: <number[]>[],},x: <string[]>[],y: <number[]>[],type: 'bar',line: {color: "#b81111",width: 1,},marker: {color: "#b81111",width: 1,},name: "Consommation totale",bucket: 1,}
let auto = 0let totalProd = 0let totalConso = 0let soleil = {hourly: {x: <string[]>[],y: <number[]>[],},daily: {x: <string[]>[],y: <number[]>[],},weekly: {x: <string[]>[],y: <number[]>[],},x: <string[]>[],y: <number[]>[],type: 'bar',line: {color: '#ffbf00',width: 1,},marker: {color: '#ffbf00',width: 1,},name: 'Production solaire',bucket: 1,}let somme = {hourly: {x: <string[]>[],y: <number[]>[],},daily: {x: <string[]>[],y: <number[]>[],},weekly: {x: <string[]>[],y: <number[]>[],},x: <string[]>[],y: <number[]>[],type: 'bar',line: {color: '#b81111',width: 1,},marker: {color: '#b81111',width: 1,},name: 'Consommation totale',bucket: 1,}
async function updatePv(puissance: number) {let d = new Date()let min_t = (new Date(d.getFullYear(), 0, 1)).getTime() / 1000let max_t = min_t + 364 * 24 * 3600if(!pvgis || pvgis.inputs.location.latitude != lat || pvgis.inputs.location.longitude != lng) {pvgis_loading = trueawait tick()let annuelle = await fetch(`${server}/pvgis`, {method: "POST",body: JSON.stringify({lat,lng,})})pvgis = await annuelle.json()pvgis_loading = falseawait tick()}soleil.hourly = {x: [], y: []};soleil.daily = {x: [], y: []};soleil.weekly = {x: [], y: []};maxProd = 0const start = new Date(min_t * 1000)const janvier = new Date(start.getFullYear(), 0, 1)for(let t = min_t; t < max_t; t += 3600) {let tt = new Date(t*1000);let tts = tt.toLocaleString()let tds = tt.toLocaleDateString()let pp = 0if(pvgis) {let len = pvgis.outputs.hourly.lengthlet n = ((t * 1000 - janvier.getTime()) / 3600000) % lenconst pvvar = 'P'pp = pvgis.outputs.hourly[Math.floor(n)][pvvar] * puissance / 1000soleil.hourly.x.push(tts)soleil.hourly.y.push(pp)if((t - min_t) % (24 * 3600) == 0) {if((t - min_t) % (24 * 7 * 3600) == 0) {if(soleil.weekly.y.length) {maxProd = Math.max(maxProd, soleil.weekly.y[soleil.weekly.y.length-1])}soleil.weekly.x.push(tds)soleil.weekly.y.push(pp)} else {soleil.weekly.y[soleil.weekly.y.length-1] += pp}soleil.daily.x.push(tds)soleil.daily.y.push(pp)} else {soleil.daily.y[soleil.daily.y.length-1] += ppsoleil.weekly.y[soleil.weekly.y.length-1] += pp}}}prodWeekly = soleil.weekly.y}
async function updatePv(puissance: number) {let d = new Date()let min_t = new Date(d.getFullYear(), 0, 1).getTime() / 1000let max_t = min_t + 364 * 24 * 3600if (!pvgis ||pvgis.inputs.location.latitude != lat ||pvgis.inputs.location.longitude != lng) {pvgis_loading = trueawait tick()let annuelle = await fetch(`${server}/pvgis`, {method: 'POST',body: JSON.stringify({lat,lng,}),})pvgis = await annuelle.json()pvgis_loading = falseawait tick()}soleil.hourly = { x: [], y: [] }soleil.daily = { x: [], y: [] }soleil.weekly = { x: [], y: [] }maxProd = 0const start = new Date(min_t * 1000)const janvier = new Date(start.getFullYear(), 0, 1)for (let t = min_t; t < max_t; t += 3600) {let tt = new Date(t * 1000)let tts = tt.toLocaleString()let tds = tt.toLocaleDateString()let pp = 0if (pvgis) {let len = pvgis.outputs.hourly.lengthlet n = ((t * 1000 - janvier.getTime()) / 3600000) % lenconst pvvar = 'P'pp =(pvgis.outputs.hourly[Math.floor(n)][pvvar] * puissance) /1000soleil.hourly.x.push(tts)soleil.hourly.y.push(pp)if ((t - min_t) % (24 * 3600) == 0) {if ((t - min_t) % (24 * 7 * 3600) == 0) {if (soleil.weekly.y.length) {maxProd = Math.max(maxProd,soleil.weekly.y[soleil.weekly.y.length - 1])}soleil.weekly.x.push(tds)soleil.weekly.y.push(pp)} else {soleil.weekly.y[soleil.weekly.y.length - 1] += pp}soleil.daily.x.push(tds)soleil.daily.y.push(pp)} else {soleil.daily.y[soleil.daily.y.length - 1] += ppsoleil.weekly.y[soleil.weekly.y.length - 1] += pp}}}prodWeekly = soleil.weekly.y}
let d = new Date()const min_t = (new Date(d.getFullYear(), 0, 1)).getTime() / 1000const max_t = min_t + 364 * 24 * 3600for(let [prm, r] of Object.entries(annee)) {let d: { t: number[], y: number[], i: number } = {t: [],y: [],i: 0,}let i = 0;for(let t = min_t; t < max_t; t += 1800) {d.t.push(t);d.y.push(r[i] / 1000);i += 1}annee_[prm] = d}
let d = new Date()const min_t = new Date(d.getFullYear(), 0, 1).getTime() / 1000const max_t = min_t + 364 * 24 * 3600for (let [prm, r] of Object.entries(annee)) {let d: { t: number[]; y: number[]; i: number } = {t: [],y: [],i: 0,}let i = 0for (let t = min_t; t < max_t; t += 1800) {d.t.push(t)d.y.push(r[i] / 1000)i += 1}annee_[prm] = d}
if (pr.length > 0) {for (let p of pr) {let d: { t: number[]; y: number[]; i: number } = {t: [],y: [],i: 0,}let i = 0for (let t = min_t; t <= max_t; t += 1800) {d.t.push(t)let pp = profs.get(p.type)if (!pp) {profs.set(p.type, await profile(p.type))}if (pp) {d.y.push((pp.coefs[i] * p.conso) / pp.total)}i += 1}annee_[p.type] = d}}
if(pr.length > 0) {for (let p of pr) {let d: { t: number[], y: number[], i: number } = {t: [],y: [],i: 0,}let i = 0for(let t = min_t; t <= max_t; t += 1800) {d.t.push(t);let pp = profs.get(p.type)if(!pp) {profs.set(p.type, await profile(p.type))}if(pp) {d.y.push(pp.coefs[i] * p.conso / pp.total)}i += 1}annee_[p.type] = d}}
auto = 0totalProd = 0totalConso = 0
somme.hourly = {x: [], y: []};somme.daily = {x: [], y: []};somme.weekly = {x: [], y: []};
const start = new Date(min_t * 1000)const janvier = new Date(start.getFullYear(), 0, 1)let i = 0for (let [_, r] of Object.entries(annee_)) {r.i = 0}for (let t = min_t; t < max_t; t += 3600) {let tt = new Date(t * 1000)let tds = tt.toLocaleDateString()let tts = tt.toLocaleString()let y = 0for (let [_, r] of Object.entries(annee_)) {// Les profils Enedis sont échantillonnés à la// demi-heure, il faut ajouter deux points consécutifswhile (r.i < r.t.length && r.t[r.i] < t + 3600) {if (!isNaN(r.y[r.i])) y += r.y[r.i]r.i += 1}}somme.hourly.x.push(tts)somme.hourly.y.push(y)if ((t - min_t) % (24 * 3600) == 0) {if ((t - min_t) % (24 * 7 * 3600) == 0) {somme.weekly.x.push(tds)somme.weekly.y.push(y)} else {somme.weekly.y[somme.weekly.y.length - 1] += y}somme.daily.x.push(tds)somme.daily.y.push(y)} else {somme.daily.y[somme.daily.y.length - 1] += ysomme.weekly.y[somme.weekly.y.length - 1] += y}totalConso += ytotalProd += soleil.hourly.y[i] * puissanceauto += Math.min(y, soleil.hourly.y[i] * puissance)i += 1}if (!Plotly)//@ts-ignorePlotly = await import('plotly.js-dist')
const start = new Date(min_t * 1000)const janvier = new Date(start.getFullYear(), 0, 1)let i = 0for(let [_, r] of Object.entries(annee_)) {r.i = 0}for(let t = min_t; t < max_t; t += 3600) {let tt = new Date(t*1000);let tds = tt.toLocaleDateString()let tts = tt.toLocaleString()let y = 0for(let [_, r] of Object.entries(annee_)) {// Les profils Enedis sont échantillonnés à la// demi-heure, il faut ajouter deux points consécutifswhile(r.i < r.t.length && r.t[r.i] < t + 3600) {if(!isNaN(r.y[r.i]))y += r.y[r.i]r.i += 1}}somme.hourly.x.push(tts)somme.hourly.y.push(y)if((t - min_t) % (24 * 3600) == 0) {if((t - min_t) % (24 * 7 * 3600) == 0) {somme.weekly.x.push(tds)somme.weekly.y.push(y)} else {somme.weekly.y[somme.weekly.y.length-1] += y}somme.daily.x.push(tds)somme.daily.y.push(y)} else {somme.daily.y[somme.daily.y.length-1] += ysomme.weekly.y[somme.weekly.y.length-1] += y}totalConso += ytotalProd += soleil.hourly.y[i]auto += Math.min(y, soleil.hourly.y[i] * puissance)i+= 1}if(!Plotly)//@ts-ignorePlotly = await import('plotly.js-dist')
await tick()redraw()}
await tick()redraw()}
function sample(s: {weekly: { x: (number | string)[]; y: number[] }daily: { x: (number | string)[]; y: number[] }hourly: { x: (number | string)[]; y: number[] }x: (number | string)[]y: number[]bucket: number},w?: number) {// ww: nombre d'échantillons bruts à afficherlet ww = w || s.hourly.x.lengthlet bbox = (<SVGGraphicsElement | undefined>(document.getElementsByClassName('bglayer')[0]))?.getBBox()let width = (bbox?.width || 10) / 3if (ww <= width) {s.x = s.hourly.xs.y = s.hourly.ys.bucket = 1} else if (ww / 24 <= width) {s.x = s.daily.xs.y = s.daily.ys.bucket = 24} else {s.x = s.weekly.xs.y = s.weekly.ys.bucket = 24 * 7}}
function sample(s: { weekly: { x: (number|string)[], y: number[] },daily: { x: (number|string)[], y: number[] },hourly: { x: (number|string)[], y: number[] },x: (number|string)[],y: number[], bucket: number },w?: number,) {// ww: nombre d'échantillons bruts à afficherlet ww = w || s.hourly.x.lengthlet bbox = (<SVGGraphicsElement | undefined>(document.getElementsByClassName("bglayer")[0]))?.getBBox()let width = (bbox?.width || 10)/3if(ww <= width) {s.x = s.hourly.xs.y = s.hourly.ys.bucket = 1} else if (ww / 24 <= width) {s.x = s.daily.xs.y = s.daily.ys.bucket = 24} else {s.x = s.weekly.xs.y = s.weekly.ys.bucket = 24 * 7}}
let has_plot = falselet layout = {}function relayout(event: any) {if (event.bucket) {return}let w = event['xaxis.range[1]'] - Math.max(0, event['xaxis.range[0]'])let layout_ = JSON.parse(JSON.stringify(layout))if (isNaN(w)) {sample(soleil)sample(somme)layout_.xaxis.autorange = truelayout_.yaxis.autorange = trueevent.bucket = soleil.bucketplotStyle = 'min-height:450px'if (has_plot) {Plotly!.update('plot', [soleil, somme], layout_)} else {Plotly!.newPlot('plot', [soleil, somme], layout_, {responsive: true,})//@ts-ignoredocument.getElementById('plot')?.on('plotly_relayout', relayout)has_plot = true}} else {let sb = soleil.bucketif (event.bucket) {w *= event.bucket} else {w *= soleil.bucket}sample(soleil, w)sample(somme, w)let sb_ = soleil.bucketevent['xaxis.range[0]'] *= sb / sb_event['xaxis.range[1]'] *= sb / sb_event.bucket = soleil.bucketlayout_.xaxis.range = [event['xaxis.range[0]'],event['xaxis.range[1]'],]let unite: stringif (soleil.bucket == 24) {unite = 'kWh/jour'} else if (soleil.bucket == 24 * 7) {unite = 'kWh/semaine'} else {unite = 'kWh'}layout_.yaxis.title.text = unitelayout_.yaxis.autorange = truelayout_.yaxis.fixedrange = falseplotStyle = 'min-height:450px'if (has_plot) {Plotly!.update('plot', [soleil, somme], layout_)} else {Plotly!.newPlot('plot', [soleil, somme], layout_, {responsive: true,})//@ts-ignoredocument.getElementById('plot')?.on('plotly_relayout', relayout)has_plot = true}}}
let has_plot = falselet layout = {}function relayout(event: any) {if(event.bucket) {return}let w = event["xaxis.range[1]"] - Math.max(0, event["xaxis.range[0]"])let layout_ = JSON.parse(JSON.stringify(layout))if(isNaN(w)) {sample(soleil)sample(somme)layout_.xaxis.autorange = truelayout_.yaxis.autorange = trueevent.bucket = soleil.bucketplotStyle = "min-height:450px"if(has_plot) {Plotly!.update('plot', [soleil, somme], layout_)} else {Plotly!.newPlot('plot', [soleil, somme], layout_, { responsive: true })//@ts-ignoredocument.getElementById('plot')?.on('plotly_relayout', relayout)has_plot = true}} else {let sb = soleil.bucketif(event.bucket) {w *= event.bucket} else {w *= soleil.bucket}sample(soleil, w)sample(somme, w)let sb_ = soleil.bucketevent["xaxis.range[0]"] *= sb / sb_event["xaxis.range[1]"] *= sb / sb_event.bucket = soleil.bucketlayout_.xaxis.range = [event["xaxis.range[0]"],event["xaxis.range[1]"]]let unite: string;if(soleil.bucket == 24) {unite = 'kWh/jour'} else if (soleil.bucket == 24 * 7) {unite = 'kWh/semaine'} else {unite = 'kWh'}layout_.yaxis.title.text = unitelayout_.yaxis.autorange = truelayout_.yaxis.fixedrange = falseplotStyle = "min-height:450px"if(has_plot) {Plotly!.update('plot', [soleil, somme], layout_)} else {Plotly!.newPlot('plot', [soleil, somme], layout_, { responsive: true })//@ts-ignoredocument.getElementById('plot')?.on('plotly_relayout', relayout)has_plot = true}}};
function redraw() {sample(soleil)sample(somme)let unite: stringif (soleil.bucket == 24) {unite = 'kWh/jour'} else if (soleil.bucket == 24 * 7) {unite = 'kWh/semaine'} else {unite = 'kWh'}layout = {title: 'Autoconsommation',autosize: true,automargin: true,plot_bgcolor: '#fff0',paper_bgcolor: '#fff0',font: {color: darkMode ? '#fff' : '#000',},xaxis: {gridcolor: darkMode ? '#444' : '#bbb',ticklabeloverflow: 'allow',ticklabelstep: 4,tickangle: 45,},yaxis: {title: { text: unite },gridcolor: darkMode ? '#444' : '#bbb',color: darkMode ? '#fff' : '#000',},showlegend: true,legend: {xanchor: 'center',x: 0.5,y: -0.4,orientation: 'h',},}plotStyle = 'min-height:450px'if (has_plot) {Plotly!.update('plot', [soleil, somme], layout)//@ts-ignoredocument.getElementById('plot')?.on('plotly_relayout', relayout)} else {Plotly!.newPlot('plot', [soleil, somme], layout, {responsive: true,})//@ts-ignoredocument.getElementById('plot')?.on('plotly_relayout', relayout)has_plot = true}
function redraw() {sample(soleil)sample(somme)let unite: string;if(soleil.bucket == 24) {unite = 'kWh/jour'} else if (soleil.bucket == 24 * 7) {unite = 'kWh/semaine'} else {unite = 'kWh'}layout = {title: "Autoconsommation",autosize: true,automargin: true,plot_bgcolor: "#fff0",paper_bgcolor: "#fff0",font: {color: darkMode ? '#fff': '#000'},xaxis: {gridcolor: darkMode ? '#444': '#bbb',ticklabeloverflow: 'allow',ticklabelstep: 4,tickangle: 45,},yaxis: {title: { text: unite },gridcolor: darkMode ? '#444': '#bbb',color: darkMode ? '#fff': '#000',},showlegend: true,legend: {xanchor: 'center',x: 0.5,y: -0.4,orientation: 'h'},}plotStyle = "min-height:450px"if(has_plot) {Plotly!.update('plot', [soleil, somme], layout)//@ts-ignoredocument.getElementById('plot')?.on('plotly_relayout', relayout)} else {Plotly!.newPlot('plot', [soleil, somme], layout, { responsive: true })//@ts-ignoredocument.getElementById('plot')?.on('plotly_relayout', relayout)has_plot = true}
var dataProd = [{values: [Math.round(auto), Math.round(totalProd - auto)],labels: ['Autoconsommé', 'Surplus'],marker: { colors: ['#ffbf00dd', '#b81111dd'] },type: 'pie',sort: false,hole: 0.5,},]
var dataProd = [{values: [Math.round(auto), Math.round(totalProd - auto)],labels: ['Autoconsommé', 'Surplus'],marker: { colors: ["#ffbf00dd", "#b81111dd"] },type: 'pie',sort: false,hole: .5,}];
var dataConso = [{values: [Math.round(auto), Math.round(totalConso - auto)],labels: ['Autoproduit', 'Alloproduit'],marker: { colors: ['#ffbf00dd', '#b81111dd'] },type: 'pie',sort: false,hole: 0.5,},]
var dataConso = [{values: [Math.round(auto), Math.round(totalConso - auto)],labels: ['Autoproduit', 'Alloproduit'],marker: { colors: ["#ffbf00dd", "#b81111dd"] },type: 'pie',sort: false,hole: .5,}];
plotStyle = 'min-height:450px'Plotly.react('autoProd',dataProd,{title: 'Autoconsommation',font: {color: darkMode ? '#fff' : '#000',},plot_bgcolor: '#fff0',paper_bgcolor: '#fff0',autosize: true,legend: {orientation: 'h',},},{ responsive: true })Plotly.react('autoConso',dataConso,{title: 'Autoproduction',font: {color: darkMode ? '#fff' : '#000',},plot_bgcolor: '#fff0',paper_bgcolor: '#fff0',autosize: true,legend: {orientation: 'h',},},{ responsive: true })}</script>
plotStyle = "min-height:450px"Plotly.react('autoProd', dataProd, {title: "Autoconsommation",font: {color: darkMode ? '#fff': '#000'},plot_bgcolor: "#fff0",paper_bgcolor: "#fff0",autosize: true,legend: {orientation: "h",}}, { responsive: true });Plotly.react('autoConso', dataConso, {title: "Autoproduction",font: {color: darkMode ? '#fff': '#000'},plot_bgcolor: "#fff0",paper_bgcolor: "#fff0",autosize: true,legend: {orientation: "h",}}, { responsive: true });}</script><form method="POST" action="/api/grain" id="pdl" on:submit={refresh}></form>
<form method="POST" action="/api/grain" id="pdl" on:submit={refresh} />
<button type="button" class="btn-close" style="padding:20px;margin:-16px -16px -16px auto" on:click={() => erreur=""} aria-label="Close"></button>
<buttontype="button"class="btn-close"style="padding:20px;margin:-16px -16px -16px auto"on:click={() => (erreur = '')}aria-label="Close" />
<input type="number" class="form-control" placeholder="Consommation Annuelle (kWh)" min="0" step="500" bind:value={pr.conso} on:change={(_ev) => updatePlot(puissance)}/>
<inputtype="number"class="form-control"placeholder="Consommation Annuelle (kWh)"min="0"step="500"bind:value={pr.conso}on:change={(_ev) => updatePlot(puissance)} />
<table class="table"><thead><tr><th>PRM<button type="button" class="btn btn-link align-baseline p-0 ms-2" data-bs-toggle="popover" data-bs-trigger="hover focus" data-bs-content="Un PRM, aussi appelé PDL, est l'identifiant d'un compteur électrique. On peut le trouver sur les factures d'électricité, ou en appuyant sur le bouton + du compteur Linky."><i class="bi bi-question-circle"></i></button></th><th>Prénom</th><th>Nom</th><th></th></tr></thead><tbody>{#each prms as prm, i}<tr><td><input class="form-control" bind:value={prm.prm} type="number" /></td><td><input class="form-control" bind:value={prm.nom}/></td><td><input class="form-control" bind:value={prm.prenom}/></td><td style="width:1%;white-space:nowrap;text-align:center"><button class="btn btn-link" on:click={(ev) => delPrm(ev, i)}><i class="bi bi-x-circle text-primary"/></button></td></tr>{/each}</tbody></table><div class="my-3 form-check"><input class="form-check-input" type="checkbox" id="consentement" bind:checked={consentement}><label class="form-check-label" for="consentement">Ces abonnés consentent à ce que j'accède à leurs données</label></div>
<table class="table"><thead><tr><th>PRM<buttontype="button"class="btn btn-link align-baseline p-0 ms-2"data-bs-toggle="popover"data-bs-trigger="hover focus"data-bs-content="Un PRM, aussi appelé PDL, est l'identifiant d'un compteur électrique. On peut le trouver sur les factures d'électricité, ou en appuyant sur le bouton + du compteur Linky."><i class="bi bi-question-circle" /></button></th><th>Prénom</th><th>Nom</th><th /></tr></thead><tbody>{#each prms as prm, i}<tr><td><inputclass="form-control"bind:value={prm.prm}type="number" /></td><td><inputclass="form-control"bind:value={prm.nom} /></td><td><inputclass="form-control"bind:value={prm.prenom} /></td><tdstyle="width:1%;white-space:nowrap;text-align:center"><buttonclass="btn btn-link"on:click={(ev) => delPrm(ev, i)}><iclass="bi bi-x-circle text-primary" /></button></td></tr>{/each}</tbody></table><div class="my-3 form-check"><inputclass="form-check-input"type="checkbox"id="consentement"bind:checked={consentement} /><label class="form-check-label" for="consentement">Ces abonnés consentent à ce que j'accède à leurs données</label></div>
<button disabled={!consentement} class="mx-2 btn btn-primary" form="pdl">Mettre à jour</button><div class="mx-2 spinner-border text-primary" class:d-none={!prm_loading}></div>
<buttondisabled={!consentement}class="mx-2 btn btn-primary"form="pdl">Mettre à jour</button><divclass="mx-2 spinner-border text-primary"class:d-none={!prm_loading} />
<div class="col-12 col-sm-6 p-0" style={plotStyle} id="autoConso"></div><div class="col-12 col-sm-6 p-0" style={plotStyle} id="autoProd"></div>
<div class="col-12 col-sm-6 p-0" style={plotStyle} id="autoConso" /><div class="col-12 col-sm-6 p-0" style={plotStyle} id="autoProd" />
//@ts-nocheckimport { line, curveLinear, Delaunay, range, scaleLinear, scaleUtc } from 'd3';// import data from './line-data';
//@ts-nocheckimport {line,curveLinear,Delaunay,range,scaleLinear,scaleUtc,} from 'd3'// import data from './line-data';
const marginTop = 100; // the top margin, in pixelsconst marginRight = 0; // the right margin, in pixelsconst marginBottom = 30; // the bottom margin, in pixelsconst marginLeft = 100; // the left margin, in pixelsconst inset = 0; // inset the default range, in pixelsconst width = 600; // the outer width of the chart, in pixelsconst height = 400; // the outer height of the chart, in pixelsconst xLabel = ''; // a label for the y-axisconst yLabel = 'Consommation (Wh)'; // a label for the y-axisconst xFormat = ''; // a format specifier string for the y-axisconst yFormat = 'Wh'; // a format specifier string for the y-axisconst horizontalGrid = true; // show horizontal grid linesconst verticalGrid = true; // show vertical grid linesconst colors = ["#b81111", "#ffbf00"]; // fill color for dots && number of colors in fill array MUST match number of subsets in dataconst showDots = false; // whether dots should be displayedconst dotsFilled = true; // whether dots should be filled or outlinedconst r = 0; // (fixed) radius of dots, in pixelsconst strokeWidth = 1; // stroke width of line, in pixelsconst strokeOpacity = [0.8, 0.2, 0.8, 0.8]; // stroke opacity of lineconst tooltipBackground = 'white'; // background color of tooltipconst tooltipTextColor = 'black'; // text color of tooltipconst strokeLinecap = 'round'; // stroke line cap of the lineconst strokeLinejoin = 'round'; // stroke line join of the lineconst xScalefactor = width / 150; //y-axis number of valuesconst yScalefactor = height / 40; //y-axis number of valuesconst curve = curveLinear; // method of interpolation between pointsconst xType = scaleUtc; // type of x-scaleconst insetTop = 50; // inset from topconst insetRight = inset; // inset from rightconst insetBottom = inset; // inset fro bottomconst insetLeft = inset; // inset from leftconst xRange = [marginLeft + insetLeft, width - marginRight - insetRight]; // [left, right]const yType = scaleLinear; // type of y-scaleconst yRange = [height - marginBottom - insetBottom, marginTop + insetTop]; // [bottom, top]
const marginTop = 100 // the top margin, in pixelsconst marginRight = 0 // the right margin, in pixelsconst marginBottom = 30 // the bottom margin, in pixelsconst marginLeft = 100 // the left margin, in pixelsconst inset = 0 // inset the default range, in pixelsconst width = 600 // the outer width of the chart, in pixelsconst height = 400 // the outer height of the chart, in pixelsconst xLabel = '' // a label for the y-axisconst yLabel = 'Consommation (Wh)' // a label for the y-axisconst xFormat = '' // a format specifier string for the y-axisconst yFormat = 'Wh' // a format specifier string for the y-axisconst horizontalGrid = true // show horizontal grid linesconst verticalGrid = true // show vertical grid linesconst colors = ['#b81111', '#ffbf00'] // fill color for dots && number of colors in fill array MUST match number of subsets in dataconst showDots = false // whether dots should be displayedconst dotsFilled = true // whether dots should be filled or outlinedconst r = 0 // (fixed) radius of dots, in pixelsconst strokeWidth = 1 // stroke width of line, in pixelsconst strokeOpacity = [0.8, 0.2, 0.8, 0.8] // stroke opacity of lineconst tooltipBackground = 'white' // background color of tooltipconst tooltipTextColor = 'black' // text color of tooltipconst strokeLinecap = 'round' // stroke line cap of the lineconst strokeLinejoin = 'round' // stroke line join of the lineconst xScalefactor = width / 150 //y-axis number of valuesconst yScalefactor = height / 40 //y-axis number of valuesconst curve = curveLinear // method of interpolation between pointsconst xType = scaleUtc // type of x-scaleconst insetTop = 50 // inset from topconst insetRight = inset // inset from rightconst insetBottom = inset // inset fro bottomconst insetLeft = inset // inset from leftconst xRange = [marginLeft + insetLeft, width - marginRight - insetRight] // [left, right]const yType = scaleLinear // type of y-scaleconst yRange = [height - marginBottom - insetBottom, marginTop + insetTop] // [bottom, top]
// For a single set of dataconsole.log(data)if (!('data' in data[0])) {x = Object.keys(data[0])[0];y = Object.keys(data[0])[1];xVals = data.map((el: Record<string, any>) => el[x]);yVals = data.map((el: Record<string, any>) => el[y]);colorVals = data.map((_) => 0);points = data.map((el) => ({x: el[x],y: el[y],color: 0}));}// For data with subsets (NOTE: expects 'id' and 'data' keys)else {x = Object.keys(data[0]?.data[0])[0];y = Object.keys(data[0]?.data[0])[1];data.forEach((subset, i) => {subset.data.forEach((coordinate) => {xVals.push(coordinate[x]);yVals.push(coordinate[y]);colorVals.push(i);points.push({x: coordinate[x],y: coordinate[y],color: i});});subsets.push(subset.id);});}
// For a single set of dataconsole.log(data)if (!('data' in data[0])) {x = Object.keys(data[0])[0]y = Object.keys(data[0])[1]xVals = data.map((el: Record<string, any>) => el[x])yVals = data.map((el: Record<string, any>) => el[y])colorVals = data.map((_) => 0)points = data.map((el) => ({x: el[x],y: el[y],color: 0,}))}// For data with subsets (NOTE: expects 'id' and 'data' keys)else {x = Object.keys(data[0]?.data[0])[0]y = Object.keys(data[0]?.data[0])[1]data.forEach((subset, i) => {subset.data.forEach((coordinate) => {xVals.push(coordinate[x])yVals.push(coordinate[y])colorVals.push(i)points.push({x: coordinate[x],y: coordinate[y],color: i,})})subsets.push(subset.id)})}
const I = range(xVals.length);const gaps = (_d, i) => !isNaN(xVals[i]) && !isNaN(yVals[i]);const cleanData = points.map(gaps);
const I = range(xVals.length)const gaps = (_d, i) => !isNaN(xVals[i]) && !isNaN(yVals[i])const cleanData = points.map(gaps)
const xDomain = [xVals[0], xVals[xVals.length - 1]];const yDomain = [0, Math.max(...yVals)];const xScale = xType(xDomain, xRange);const yScale = yType(yDomain, yRange);const niceY = scaleLinear().domain([0, Math.max(...yVals)]).nice();
const xDomain = [xVals[0], xVals[xVals.length - 1]]const yDomain = [0, Math.max(...yVals)]const xScale = xType(xDomain, xRange)const yScale = yType(yDomain, yRange)const niceY = scaleLinear().domain([0, Math.max(...yVals)]).nice()
$: {lines = [];colors.forEach((_color, j) => {const filteredI = I.filter((_el, i) => colorVals[i] === j);lines.push(chartLine(filteredI));});}
$: {lines = []colors.forEach((_color, j) => {const filteredI = I.filter((_el, i) => colorVals[i] === j)lines.push(chartLine(filteredI))})}
const pointsScaled = points.map((el) => [xScale(el.x), yScale(el.y), el.color]);const delaunayGrid = Delaunay.from(pointsScaled);const voronoiGrid = delaunayGrid.voronoi([0, 0, width, height]);
const pointsScaled = points.map((el) => [xScale(el.x),yScale(el.y),el.color,])const delaunayGrid = Delaunay.from(pointsScaled)const voronoiGrid = delaunayGrid.voronoi([0, 0, width, height])
const xTicks = xScale.ticks(xScalefactor);const xTicksFormatted = xTicks.map((el) => (new Date(el*1000).toLocaleDateString()));const yTicks = niceY.ticks(yScalefactor);
const xTicks = xScale.ticks(xScalefactor)const xTicksFormatted = xTicks.map((el) =>new Date(el * 1000).toLocaleDateString())const yTicks = niceY.ticks(yScalefactor)
<svg {width} {height} viewBox="0 0 {width} {height}"cursor='crosshair'on:mouseout="{() => dotInfo = null}"on:blur="{() => dotInfo = null}">
<svg{width}{height}viewBox="0 0 {width} {height}"cursor="crosshair"on:mouseout={() => (dotInfo = null)}on:blur={() => (dotInfo = null)}>
<path class="line" fill='none' stroke-opacity={points[dotInfo[1]].color === i ? '1' : '0.1'} stroke={colors[i]} d={subsetLine} stroke-width={strokeWidth} stroke-linecap={strokeLinecap} stroke-linejoin={strokeLinejoin}/><circle cx={xScale(points[dotInfo[1]].x)} cy={yScale(points[dotInfo[1]].y)} r={r} stroke={colors[points[dotInfo[1]].color]} fill={dotsFilled} />
<pathclass="line"fill="none"stroke-opacity={points[dotInfo[1]].color === i? '1': '0.1'}stroke={colors[i]}d={subsetLine}stroke-width={strokeWidth}stroke-linecap={strokeLinecap}stroke-linejoin={strokeLinejoin} /><circlecx={xScale(points[dotInfo[1]].x)}cy={yScale(points[dotInfo[1]].y)}{r}stroke={colors[points[dotInfo[1]].color]}fill={dotsFilled} />
<path class="line" fill='none' stroke={colors[i]} d={subsetLine}stroke-opacity={strokeOpacity[i]} stroke-width={strokeWidth} stroke-linecap={strokeLinecap} stroke-linejoin={strokeLinejoin} />
<pathclass="line"fill="none"stroke={colors[i]}d={subsetLine}stroke-opacity={strokeOpacity[i]}stroke-width={strokeWidth}stroke-linecap={strokeLinecap}stroke-linejoin={strokeLinejoin} />
<g class="y-axis" transform="translate({marginLeft}, 0)" pointer-events='none'><path class="domain" stroke="black" d="M{insetLeft}, {marginTop} V{height - marginBottom + 6}"/>
<gclass="y-axis"transform="translate({marginLeft}, 0)"pointer-events="none"><pathclass="domain"stroke="black"d="M{insetLeft}, {marginTop} V{height - marginBottom + 6}" />
<g class="x-axis" transform="translate(0,{height - marginBottom - insetBottom})" pointer-events='none'><path class="domain" stroke="black" d="M{marginLeft},0.5 H{width - marginRight}"/>
<gclass="x-axis"transform="translate(0,{height - marginBottom - insetBottom})"pointer-events="none"><pathclass="domain"stroke="black"d="M{marginLeft},0.5 H{width - marginRight}" />
<div class="tooltip" style='position:absolute; left:{dotInfo[2].pageX + 12}px; top:{dotInfo[2].pageY + 12}px; pointer-events:none; background-color:{tooltipBackground}; color:{tooltipTextColor}'>
<divclass="tooltip"style="position:absolute; left:{dotInfo[2].pageX +12}px; top:{dotInfo[2].pageY +12}px; pointer-events:none; background-color:{tooltipBackground}; color:{tooltipTextColor}">
.chart-container {justify-content: center;align-items: center;margin-top: 50px;margin-left: 80px;}svg {max-width: 100%;height: auto;height: "intrinsic";margin: auto;}path {fill: "green"}.y-axis {font-size: "10px";font-family: sans-serif;text-anchor: "end";}.x-axis {font-size: "10px";font-family: sans-serif;text-anchor: "end";}.tick text { font-size: 80%; fill: white !important }.tick {opacity: 1;}.tick-start {stroke: black;stroke-opacity: 1;}.tick-grid {stroke: black;stroke-opacity: 0.2;font-size: "11px";color: black;}.tick text {fill: black;}
.chart-container {justify-content: center;align-items: center;margin-top: 50px;margin-left: 8 0px;}svg {max-width: 100%;height: auto;height: 'intrinsic';margin: auto;}path {fill: 'green';}.y-axis {font-size: '10px';font-family: sans-serif;text-anchor: 'end';}.x-axis {font-size: '10px';font-family: sans-serif;text-anchor: 'end';}.tick text {font-size: 80%;fill: white !important;}.tick {opacity: 1;}.tick-start {stroke: black;stroke-opacity: 1;}.tick-grid {stroke: black;stroke-opacity: 0.2;font-size: '11px';color: black;}.tick text {fill: black;}
@media (prefers-color-scheme: dark) {.y-axis text { fill: white; }.x-axis text { fill: white; }.tick-start {stroke: white;}.tick-grid {stroke: white;}.tick text {fill: white;}.domain { stroke: white }}
@media (prefers-color-scheme: dark) {.y-axis text {fill: white;}.x-axis text {fill: white;}.tick-start {stroke: white;}.tick-grid {stroke: white;}.tick text {fill: white;}.domain {stroke: white;}}
.tooltip{border-radius: 5px;padding: 5px;box-shadow: rgba(0, 0, 0, 0.4) 0px 2px 4px, rgba(0, 0, 0, 0.3) 0px 7px 13px -3px, rgba(0, 0, 0, 0.2) 0px -3px 0px inset;opacity: 1;}
.tooltip {border-radius: 5px;padding: 5px;box-shadow: rgba(0, 0, 0, 0.4) 0px 2px 4px,rgba(0, 0, 0, 0.3) 0px 7px 13px -3px,rgba(0, 0, 0, 0.2) 0px -3px 0px inset;opacity: 1;}
import Banque from '../../Banque.svelte'import Simulation from './Simulation.svelte'import { page } from '$app/stores';import { assets as a } from '$app/paths';import { enhance, applyAction } from '$app/forms';import { onMount } from 'svelte';import type { SubmitFunction } from '@sveltejs/kit';import type { Grain } from '../../../helpers'import * as H from '../../../helpers'import type { Modal, Offcanvas } from 'bootstrap'import { email } from '../../../stores'export let prmsFeature: boolean = falseexport let assets: string = aexport let server = "https://coturnix.fr"type Prm = { prm: number | null, nom: string, prenom: string }
import Banque from '../../Banque.svelte'import Simulation from './Simulation.svelte'import { page } from '$app/stores'import { assets as a } from '$app/paths'import { enhance, applyAction } from '$app/forms'import { onMount } from 'svelte'import type { SubmitFunction } from '@sveltejs/kit'import type { Grain } from '../../../helpers'import * as H from '../../../helpers'import type { Modal, Offcanvas } from 'bootstrap'import { email } from '../../../stores'export let prmsFeature: boolean = falseexport let assets: string = aexport let server = 'https://coturnix.fr'type Prm = { prm: number | null; nom: string; prenom: string }
export let data: {nom: string,porteur: string,adresse: string,tel: string,id: string,img?: string,simulation: Grain.SimulationCommunaute,guest?: boolean,prms: Prm[],email?: string,}
export let data: {nom: stringporteur: stringadresse: stringtel: stringid: stringimg?: stringsimulation: Grain.SimulationCommunauteguest?: booleanprms: Prm[]email?: string}
onMount(async () => {email.set(data.email || null)email.subscribe((value) => {if (value) data.email = value})let modal = document.getElementById('grainSaveModal')console.log('mount modal', modal)if (modal) {document.body.appendChild(modal)}if (!window.bootstrap) {console.log('no window bootstrap, load')window.bootstrap = await import('bootstrap')}menuElt = document.getElementById('menuoff')if (!menuElt) {return}menu = new window.bootstrap.Offcanvas(menuElt)const popoverTriggerList = document.querySelectorAll('[data-bs-toggle="popover"]')for (let t of popoverTriggerList) {new window.bootstrap.Popover(t)}})
onMount(async () => {email.set(data.email || null)email.subscribe((value) => { if(value) data.email = value })let modal = document.getElementById('grainSaveModal')console.log("mount modal", modal)if(modal) {document.body.appendChild(modal);}if(!window.bootstrap) {console.log("no window bootstrap, load");window.bootstrap = await import('bootstrap')}menuElt = document.getElementById('menuoff')if(!menuElt) {return}menu = new window.bootstrap.Offcanvas(menuElt)const popoverTriggerList = document.querySelectorAll('[data-bs-toggle="popover"]')for(let t of popoverTriggerList) {new window.bootstrap.Popover(t)}})
let saveModal_: null | Modal = nulllet menu: null | Offcanvas = nulllet menuElt: null | HTMLElement = null
let saveModal_: null | Modal = null;let menu: null | Offcanvas = null;let menuElt: null | HTMLElement = null
async function saveModal(_e: Event) {console.log('saveModal', _e)if (!saveModal_) {console.log('no saveModal')saveModal_ = new window.bootstrap.Modal('#grainSaveModal', {focus: false,keyboard: true,})}
async function saveModal(_e: Event) {console.log("saveModal", _e)if(!saveModal_) {console.log("no saveModal")saveModal_ = new window.bootstrap.Modal('#grainSaveModal', {focus: false,keyboard: true,})}
showSaveModalAfterMenuHide()menu?.hide()}
showSaveModalAfterMenuHide()menu?.hide()}
function showSaveModalAfterMenuHide() {// menuElt?.removeEventListener('hidden.bs.offcanvas', showSaveModalAfterMenuHide)let c = document.getElementsByClassName('offcanvas-backdrop')for (const elt of c) {elt.parentElement?.removeChild(elt)}saveModal_?.show()}
function showSaveModalAfterMenuHide() {// menuElt?.removeEventListener('hidden.bs.offcanvas', showSaveModalAfterMenuHide)let c = document.getElementsByClassName("offcanvas-backdrop")for(const elt of c) {elt.parentElement?.removeChild(elt)}saveModal_?.show()}
let save: SubmitFunction = async ({ formData }) => {console.log('save called')formData.set('data', JSON.stringify(p))formData.set('prms', JSON.stringify(data.prms))saveModal_?.hide()return async ({ result }) => {console.log(JSON.stringify(result))await applyAction(result)}}
let save: SubmitFunction = async ({ formData }) => {console.log("save called")formData.set('data', JSON.stringify(p))formData.set('prms', JSON.stringify(data.prms))saveModal_?.hide()return async ({ result }) => {console.log(JSON.stringify(result))await applyAction(result);};}
let expert = $page.url.hash == '#expert'
let expert = $page.url.hash == "#expert"
$: compteActive = $page.url.hash == '#compte' ? 'active' : ''$: banqueActive = $page.url.hash == '#banque' ? 'active' : ''$: expertActive = expert && $page.url.hash == '#expert' ? 'active' : ''$: simuActive =(true || !data.guest) && $page.url.hash == '#simu' ? 'active' : ''$: syntheseActive =!compteActive && !banqueActive && !simuActive && !expertActive? 'active': ''
$: compteActive = ($page.url.hash == "#compte") ? "active": ""$: banqueActive = ($page.url.hash == "#banque") ? "active": ""$: expertActive = (expert && $page.url.hash == "#expert") ? "active": ""$: simuActive = ((true || !data.guest) && $page.url.hash == "#simu") ? "active": ""$: syntheseActive = (!compteActive && !banqueActive && !simuActive && !expertActive) ? "active": ""
$: compteShow = compteActive ? 'show' : ''$: banqueShow = banqueActive ? 'show' : ''$: simuShow = simuActive ? 'show' : ''$: syntheseShow = syntheseActive ? 'show' : ''$: expertShow = expertActive ? 'show' : ''
let an = new Date().getFullYear()
function tarifSurplus_(puissance: number): number {let resultat = p.tarifCRE.prix[0]for (let i = 0; i < p.tarifCRE.limites.length; i++) {if (puissance < p.tarifCRE.limites[i]) {return resultat} else {resultat = p.tarifCRE.prix[i]}}return resultat}
function tarifSurplus_(puissance: number): number {let resultat = p.tarifCRE.prix[0];for(let i = 0; i < p.tarifCRE.limites.length; i++) {if(puissance < p.tarifCRE.limites[i]) {return resultat} else {resultat = p.tarifCRE.prix[i]}}return resultat}
$: investissement = p.puissance? p.puissance * 1000 * p.ratio + p.enedis: 0
function onSurfaceChange(ev: Event) {surface = (ev.target as HTMLInputElement).valuep.puissance = surface / surface_kwc}
function onPuissanceChange(ev: Event) {p.puissance = (ev.target as HTMLInputElement).valuesurface = p.puissance * surface_kwc}
$: tarifLocal = (i: number) => H.tarifLocal(p, i)$: tarifAllo = (i: number) => p.coutElec * Math.pow(1+p.inflationElec/100, i)
$: chiffreAffaires = (i: number) =>(i == 0 ? primeInvestissement : 0) +productionAnnuelle(i) *(autoconso * tarifLocal(i) +(1 - autoconso) * tarifSurplus(i) +(p.autoprod * tarifAllo(i)) / 100)
$: chiffreAffaires = (i: number) =>((i == 0) ? primeInvestissement : 0) + productionAnnuelle(i) * (autoconso * tarifLocal(i) + (1 - autoconso) * tarifSurplus(i) + p.autoprod * tarifAllo(i)/100)
$: exploitation = (i: number) =>p.puissance * p.maintenance * Math.pow(1 + p.inflation / 100, i)
$: resultatFiscal = (i: number) => ebe(i) - amortissement(i) - provisionOnduleurs(i) - interetsDetteSenior(i) - interetsDSRA(i)
$: {resultatNetData[0] = {id: '',data: new Array(N).fill(0).map((_, i) => {return { x: an + i, y: resultatNet(i) }}),}}
let resultatNetData: { id: string, data: {x:number,y:number}[]}[] = [{id:"",data:[]}]$: {resultatNetData[0] = { id: "", data: new Array(N).fill(0).map((_, i) => { return { x: an + i, y: resultatNet(i) }}) }}// Synthèse$: consoMoyenneFoyer = (i: number) => H.consoMoyenneFoyer(p, i)$: coutElec = () => {let cout = 0for(let i = 0; i < N; i++) {cout += p.coutElec * Math.pow(1 + p.inflationElec / 100, i) * consoMoyenneFoyer(i)}return cout}$: coutElecAuto = () => {let cout = 0for(let i = 0; i < N; i++) {cout += tarifLocal(i) * consoMoyenneFoyer(i) * p.autoprod / 100+ p.coutElec * Math.pow(1 + p.inflationElec / 100, i) * consoMoyenneFoyer(i) * (100 - p.autoprod) / 100}return cout}
$: coutElecAuto = () => {let cout = 0for (let i = 0; i < N; i++) {cout +=(tarifLocal(i) * consoMoyenneFoyer(i) * p.autoprod) / 100 +(p.coutElec *Math.pow(1 + p.inflationElec / 100, i) *consoMoyenneFoyer(i) *(100 - p.autoprod)) /100}return cout}
function format(x : number){let f = 0let s = ''if (Math.abs(x) <= 1000){s = ' €'f = x} else if (Math.abs(x) < 1000000) {s = ' k€'f = x/1000} else if(Math.abs(x) < 1000000000) {s = ' M€'f = x/1000000} else {s = ' mds€'f = x/1000000000}return fmt(2).format(f) + s}function rentabiliteTaux(resultat: number): string {return fmt(2).format(investissement ?((resultat*100/investissement)-100): 0) + "%"}let maxa = -1/0let mina = 1/0let margin = 1function traceArray(f: (_: number) => number, n:number){let c = ''let ai = 0maxa = -1/0mina = 1/0for (let i = 0; i < n; i ++ ){ai += f(i)maxa = Math.max(maxa, ai)mina = Math.min(mina, ai)c += ` ${c ? 'L':'M'} ${i.toFixed(arr)}, ${(-ai.toFixed(arr))}`}margin = Math.max(1, (maxa - mina) / 20)return c}$: roiDate = () => {let sum = 0let lastNeg = 0for (let i = 0; i < N; i += 1 ){sum += resultatNet(i)if(sum < 0)lastNeg = i}lastNeg += 1if (lastNeg < N) {if(lastNeg <= 1 && sum >= 0) {return `Tout de suite`} else if (lastNeg == 1) {return `1 an`} else {return `${lastNeg} ans`}} else {return "À la saint Glinglin"}}
function format(x: number) {let f = 0let s = ''if (Math.abs(x) <= 1000) {s = ' €'f = x} else if (Math.abs(x) < 1000000) {s = ' k€'f = x / 1000} else if (Math.abs(x) < 1000000000) {s = ' M€'f = x / 1000000} else {s = ' mds€'f = x / 1000000000}return fmt(2).format(f) + s}
$: rembPret = (n:number) => {let totalRembAnnuel_n = remboursementAnnuel.slice(0, n).reduce((a, b) => a + b, 0)let totalInteret_n = sum(interetsDetteSenior, n)let totalRembAnnuel =remboursementAnnuel.reduce((a, b) => a + b, 0)let totalInteret = sum(interetsDetteSenior, n)return fmt(2).format((totalRembAnnuel + totalInteret) ?((totalRembAnnuel_n + totalInteret_n) * 100 / (totalRembAnnuel + totalInteret)): 0)}
let maxa = -1 / 0let mina = 1 / 0let margin = 1function traceArray(f: (_: number) => number, n: number) {let c = ''let ai = 0maxa = -1 / 0mina = 1 / 0for (let i = 0; i < n; i++) {ai += f(i)maxa = Math.max(maxa, ai)mina = Math.min(mina, ai)c += ` ${c ? 'L' : 'M'} ${i.toFixed(arr)}, ${-ai.toFixed(arr)}`}margin = Math.max(1, (maxa - mina) / 20)return c}
$: economieFoyerMois = fmt(2).format(coutElec_ ? ((coutElec_ - coutElecAuto_) / (coutElec_/(N*12))):0)
$: roiDate = () => {let sum = 0let lastNeg = 0for (let i = 0; i < N; i += 1) {sum += resultatNet(i)if (sum < 0) lastNeg = i}lastNeg += 1if (lastNeg < N) {if (lastNeg <= 1 && sum >= 0) {return `Tout de suite`} else if (lastNeg == 1) {return `1 an`} else {return `${lastNeg} ans`}} else {return 'À la saint Glinglin'}}
$: rembPret = (n: number) => {let totalRembAnnuel_n = remboursementAnnuel.slice(0, n).reduce((a, b) => a + b, 0)let totalInteret_n = sum(interetsDetteSenior, n)let totalRembAnnuel = remboursementAnnuel.reduce((a, b) => a + b, 0)let totalInteret = sum(interetsDetteSenior, n)return fmt(2).format(totalRembAnnuel + totalInteret? ((totalRembAnnuel_n + totalInteret_n) * 100) /(totalRembAnnuel + totalInteret): 0)}
<button class="navbar-toggler" type="button" data-bs-toggle="offcanvas" data-bs-target="#menuoff" aria-label="Toggle navigation"><span class="navbar-toggler-icon"></span>
<buttonclass="navbar-toggler"type="button"data-bs-toggle="offcanvas"data-bs-target="#menuoff"aria-label="Toggle navigation"><span class="navbar-toggler-icon" />
<input class="form-check-input" type="checkbox" role="switch" id="expert" bind:checked={expert}><label class="form-check-label" for="expert">Niveau expert</label>
<inputclass="form-check-input"type="checkbox"role="switch"id="expert"bind:checked={expert} /><label class="form-check-label" for="expert">Niveau expert</label>
<label class="form-label" for="puissance">Puissance totale (kWc)</label><input class="form-control form-control-sm" type="number" id="puissance" min="1" value={p.puissance} on:change={onPuissanceChange} />
<label class="form-label" for="puissance">Puissance totale (kWc)</label><inputclass="form-control form-control-sm"type="number"id="puissance"min="1"value={p.puissance}on:change={onPuissanceChange} />
<label class="form-label" for="puissance">Surface totale (m²)</label><input class="form-control form-control-sm" type="number" id="surface" min="1" value={surface} on:change={onSurfaceChange} />
<label class="form-label" for="puissance">Surface totale (m²)</label><inputclass="form-control form-control-sm"type="number"id="surface"min="1"value={surface}on:change={onSurfaceChange} />
<label class="form-label" for="autoconso">Taux d'autoconsommation (%)<button type="button" class="btn btn-link align-baseline p-0 ms-2" data-bs-toggle="popover" data-bs-trigger="hover focus" data-bs-content="Pourcentage de la production consommée localement, à valider plus finement dans l'onglet Simulation. C'est la valeur que l'application Coturnix optimise."><i class="bi bi-question-circle"></i></button>
<label class="form-label" for="autoconso">Taux d'autoconsommation (%)<buttontype="button"class="btn btn-link align-baseline p-0 ms-2"data-bs-toggle="popover"data-bs-trigger="hover focus"data-bs-content="Pourcentage de la production consommée localement, à valider plus finement dans l'onglet Simulation. C'est la valeur que l'application Coturnix optimise."><i class="bi bi-question-circle" /></button>
<label class="form-label" for="autoprod">Taux d'autoproduction (%)<button type="button" class="btn btn-link align-baseline p-0 ms-2" data-bs-toggle="popover" data-bs-trigger="hover focus" data-bs-content="Pourcentage des consommations venant de sources locales, à valider plus finement dans l'onglet Simulation."><i class="bi bi-question-circle"></i></button></label>
<label class="form-label" for="autoprod">Taux d'autoproduction (%)<buttontype="button"class="btn btn-link align-baseline p-0 ms-2"data-bs-toggle="popover"data-bs-trigger="hover focus"data-bs-content="Pourcentage des consommations venant de sources locales, à valider plus finement dans l'onglet Simulation."><i class="bi bi-question-circle" /></button></label>
<label class="form-label" for="prix">Prix d'achat alloproduit (€/kWh)<button type="button" class="btn btn-link align-baseline p-0 ms-2" data-bs-toggle="popover" data-bs-trigger="hover focus" data-bs-content="Ce prix dépend du contrat de fourniture d'électricité du producteur."><i class="bi bi-question-circle"></i></button></label><input class="form-control form-control-sm" type="number" step="0.01" min="0" id="coutElec" bind:value={p.coutElec}/>
<label class="form-label" for="prix">Prix d'achat alloproduit (€/kWh)<buttontype="button"class="btn btn-link align-baseline p-0 ms-2"data-bs-toggle="popover"data-bs-trigger="hover focus"data-bs-content="Ce prix dépend du contrat de fourniture d'électricité du producteur."><i class="bi bi-question-circle" /></button></label><inputclass="form-control form-control-sm"type="number"step="0.01"min="0"id="coutElec"bind:value={p.coutElec} />
<label class="form-label" for="prix">Prix de vente local (€/kWh)<button type="button" class="btn btn-link align-baseline p-0 ms-2" data-bs-toggle="popover" data-bs-trigger="hover focus" data-bs-content="Dans Coturnix, chaque producteur choisit son prix, et Coturnix propose le moins cher au consommateur."><i class="bi bi-question-circle"></i></button></label><input class="form-control form-control-sm" type="number" step="0.01" min="0" id="prix" bind:value={p.prix}/>
<label class="form-label" for="prix">Prix de vente local (€/kWh)<buttontype="button"class="btn btn-link align-baseline p-0 ms-2"data-bs-toggle="popover"data-bs-trigger="hover focus"data-bs-content="Dans Coturnix, chaque producteur choisit son prix, et Coturnix propose le moins cher au consommateur."><i class="bi bi-question-circle" /></button></label><inputclass="form-control form-control-sm"type="number"step="0.01"min="0"id="prix"bind:value={p.prix} />
<label class="form-label" for="inflationElec">Inflation nationale de l'électricité (%)</label><input class="form-control form-control-sm" type="number" bind:value={p.inflationElec} min="0" id="inflationElec" />
<label class="form-label" for="inflationElec">Inflation nationale de l'électricité (%)</label><inputclass="form-control form-control-sm"type="number"bind:value={p.inflationElec}min="0"id="inflationElec" />
<label class="form-label" for="echeances">Durée d'analyse (an)</label><input class="form-control form-control-sm" type="number" id="echeances" min="0" bind:value={N}/>
<label class="form-label" for="echeances">Durée d'analyse (an)</label><inputclass="form-control form-control-sm"type="number"id="echeances"min="0"bind:value={N} />
<label class="form-label" for="apport">Apport initial (€)</label><input class="form-control form-control-sm" type="number" id="apport" min="0" step="1000" bind:value={p.apport}/>
<label class="form-label" for="apport">Apport initial (€)</label><inputclass="form-control form-control-sm"type="number"id="apport"min="0"step="1000"bind:value={p.apport} />
<label class="form-label" for="interet">Taux d'intérêt(%)</label><input class="form-control form-control-sm" type="number" step="0.1" id="interet" min="0" bind:value={p.interet}/>
<label class="form-label" for="interet">Taux d'intérêt(%)</label><inputclass="form-control form-control-sm"type="number"step="0.1"id="interet"min="0"bind:value={p.interet} />
<label class="form-label" for="echeances">Nombre d'échéances (en mois)</label><input class="form-control form-control-sm" type="number" id="echeances" min="0" bind:value={p.echeances}/>
<label class="form-label" for="echeances">Nombre d'échéances (en mois)</label><inputclass="form-control form-control-sm"type="number"id="echeances"min="0"bind:value={p.echeances} />
<form id="delForm" method="POST" action="?/del"></form><button class="my-2 me-2 btn btn-primary" on:click={saveModal}>Sauvegarder</button><button class="my-2 btn btn-outline-primary" form="delForm">Supprimer</button>
<form id="delForm" method="POST" action="?/del" /><buttonclass="my-2 me-2 btn btn-primary"on:click={saveModal}>Sauvegarder</button><buttonclass="my-2 btn btn-outline-primary"form="delForm">Supprimer</button>
<a href="#synthese" class="nav-link {syntheseActive}" id="synthese-tab" type="button" role="tab" aria-controls="synthese-tab-pane" aria-selected="true">Synthèse</a>
<ahref="#synthese"class="nav-link {syntheseActive}"id="synthese-tab"type="button"role="tab"aria-controls="synthese-tab-pane"aria-selected="true">Synthèse</a>
<a href="#compte" class="nav-link {compteActive}" id="profile-tab" type="button" role="tab" aria-controls="compte-tab-pane" aria-selected="false">Détails financiers</a>
<ahref="#compte"class="nav-link {compteActive}"id="profile-tab"type="button"role="tab"aria-controls="compte-tab-pane"aria-selected="false">Détails financiers</a>
<a href="#banque" class="nav-link {banqueActive}" id="banque-tab" type="button" role="tab" aria-controls="banque-tab-pane" aria-selected="false">Emprunt</a>
<ahref="#banque"class="nav-link {banqueActive}"id="banque-tab"type="button"role="tab"aria-controls="banque-tab-pane"aria-selected="false">Emprunt</a>
<a href="#expert" class="nav-link {expertActive}" id="expert-tab" type="button" role="tab" aria-controls="expert-tab-pane" aria-selected="false">Mode expert</a>
<ahref="#expert"class="nav-link {expertActive}"id="expert-tab"type="button"role="tab"aria-controls="expert-tab-pane"aria-selected="false">Mode expert</a>
<a href="#simu" class="nav-link {simuActive}" id="prm-tab" type="button" role="tab" aria-controls="prm-tab-pane" aria-selected="false">Simulation</a>
<ahref="#simu"class="nav-link {simuActive}"id="prm-tab"type="button"role="tab"aria-controls="prm-tab-pane"aria-selected="false">Simulation</a>
<div class="tab-pane fade {syntheseActive} {syntheseShow} p-3" id="synthese-tab-pane" role="tabpanel" aria-labelledby="synthese-tab" tabindex="0"><h3 class="my-3 text-body fs-1 fw-bold ">En un regard, <span class="text-primary">tout</span> votre projet.</h3>
<divclass="tab-pane fade {syntheseActive} {syntheseShow} p-3"id="synthese-tab-pane"role="tabpanel"aria-labelledby="synthese-tab"tabindex="0"><h3 class="my-3 text-body fs-1 fw-bold">En un regard, <span class="text-primary">tout</span> votreprojet.</h3>
<svg viewBox="{Math.floor(-N*0.05)} {Math.floor(-maxa - margin)} {Math.ceil(N*1.1)} {Math.ceil(maxa-mina + 2 * margin)}" xmlns="http://www.w3.org/2000/svg" width="250px" height="100px" preserveAspectRatio="none"><path d={traceArray(resultatNet,N)} fill="transparent" stroke-width="2" vector-effect="non-scaling-stroke" stroke="#b71515" />
<svgviewBox="{Math.floor(-N * 0.05)} {Math.floor(-maxa - margin)} {Math.ceil(N * 1.1)} {Math.ceil(maxa - mina + 2 * margin)}"xmlns="http://www.w3.org/2000/svg"width="250px"height="100px"preserveAspectRatio="none"><pathd={traceArray(resultatNet, N)}fill="transparent"stroke-width="2"vector-effect="non-scaling-stroke"stroke="#b71515" />
<div class="d-flex flex-column justify-content-between text-center ms-3"><div style="width:250px" class="py-3 my-auto"><div class="spinner-border ms-3 loading" class:d-none={!pvgis_loading}></div><svg class:d-none={pvgis_loading || !maxProd} viewBox="-10 0 270 {maxProd}" preserveAspectRatio="none" xmlns="http://www.w3.org/2000/svg" width="250px" height="100px">
<divclass="d-flex flex-column justify-content-between text-center ms-3"><divstyle="width:250px"class="py-3 my-auto"><divclass="spinner-border ms-3 loading"class:d-none={!pvgis_loading} /><svgclass:d-none={pvgis_loading ||!maxProd}viewBox="-10 0 270 {maxProd}"preserveAspectRatio="none"xmlns="http://www.w3.org/2000/svg"width="250px"height="100px">
<svg class="donnee" class:d-none={pvgis_loading || maxProd} xmlns="http://www.w3.org/2000/svg" width="32" height="32" fill="currentColor" viewBox="0 0 16 16"><path d="M6 .278a.768.768 0 0 1 .08.858 7.208 7.208 0 0 0-.878 3.46c0 4.021 3.278 7.277 7.318 7.277.527 0 1.04-.055 1.533-.16a.787.787 0 0 1 .81.316.733.733 0 0 1-.031.893A8.349 8.349 0 0 1 8.344 16C3.734 16 0 12.286 0 7.71 0 4.266 2.114 1.312 5.124.06A.752.752 0 0 1 6 .278"/>
<svgclass="donnee"class:d-none={pvgis_loading ||maxProd}xmlns="http://www.w3.org/2000/svg"width="32"height="32"fill="currentColor"viewBox="0 0 16 16"><pathd="M6 .278a.768.768 0 0 1 .08.858 7.208 7.208 0 0 0-.878 3.46c0 4.021 3.278 7.277 7.318 7.277.527 0 1.04-.055 1.533-.16a.787.787 0 0 1 .81.316.733.733 0 0 1-.031.893A8.349 8.349 0 0 1 8.344 16C3.734 16 0 12.286 0 7.71 0 4.266 2.114 1.312 5.124.06A.752.752 0 0 1 6 .278" />
<div class="donnee">{N ? format(sum(resultatNet,N)/N) : "0€"}</div><div>Bénéfice annuel moyen </div>
<div class="donnee">{N? format(sum(resultatNet, N) / N): '0€'}</div><div>Bénéfice annuel moyen</div>
<div class="flex-column justify-content-between text-center"><div class="donnee">{rentabiliteTaux(sum(resultatNet,10))}</div>
<divclass="flex-column justify-content-between text-center"><div class="donnee">{rentabiliteTaux(sum(resultatNet, 10))}</div>
<div class="tab-pane fade {compteActive} {compteShow} p-3" id="compte-tab-pane" role="tabpanel" aria-labelledby="compte-tab" tabindex="0"><h3 class="my-3 fs-1 fw-bold"><span class="text-primary">Projetez-vous</span> dans votre projet.</h3>
<divclass="tab-pane fade {compteActive} {compteShow} p-3"id="compte-tab-pane"role="tabpanel"aria-labelledby="compte-tab"tabindex="0"><h3 class="my-3 fs-1 fw-bold"><span class="text-primary">Projetez-vous</span> dans votreprojet.</h3>
<div class="d-flex flex-column my-3"><div class="tcellt">{an + i}</div><div class="tcellt">{resultatNet(i).toFixed(arr)}</div></div>
<div class="d-flex flex-column my-3"><div class="tcellt">{an + i}</div><div class="tcellt">{resultatNet(i).toFixed(arr)}</div></div>
<div class="titreligne tcellt">Autoproduction (€)</div><div class="titreligne tcellt">Vente locale (€)</div><div class="titreligne tcellt">Vente de surplus (€)</div>
<div class="titreligne tcellt">Autoproduction (€)</div><div class="titreligne tcellt">Vente locale (€)</div><div class="titreligne tcellt">Vente de surplus (€)</div>
<div class="d-flex flex-column my-4"><div class="tcellt">{an + i}</div><div class="tcellt">{(productionAnnuelle(i) * (p.autoprod * tarifAllo(i) / 100)).toFixed(0)}</div><div class="tcellt">{(productionAnnuelle(i) * (autoconso * tarifLocal(i))).toFixed(0)}</div><div class="tcellt">{(productionAnnuelle(i) * ((1 - autoconso) * tarifSurplus(i))).toFixed(0)}</div><div class="tcellt"> </div><div class="tcellt">{chiffreAffaires(i).toFixed(arr)}</div></div>
<div class="d-flex flex-column my-4"><div class="tcellt">{an + i}</div><div class="tcellt">{(productionAnnuelle(i) *((p.autoprod * tarifAllo(i)) / 100)).toFixed(0)}</div><div class="tcellt">{(productionAnnuelle(i) *(autoconso * tarifLocal(i))).toFixed(0)}</div><div class="tcellt">{(productionAnnuelle(i) *((1 - autoconso) * tarifSurplus(i))).toFixed(0)}</div><div class="tcellt"> </div><div class="tcellt">{chiffreAffaires(i).toFixed(arr)}</div></div>
<div class="d-flex flex-column my-4"><div class="tcellt">{an + i}</div><div class="tcellt">{exploitation(i).toFixed(arr)}</div><div class="tcellt">{turpe(i).toFixed(arr)}</div><div class="tcellt">{assurance(i).toFixed(arr)}</div><div class="tcellt">{divers(i).toFixed(arr)}</div><div class="tcellt">{charges(i).toFixed(arr)}</div></div>
<div class="d-flex flex-column my-4"><div class="tcellt">{an + i}</div><div class="tcellt">{exploitation(i).toFixed(arr)}</div><div class="tcellt">{turpe(i).toFixed(arr)}</div><div class="tcellt">{assurance(i).toFixed(arr)}</div><div class="tcellt">{divers(i).toFixed(arr)}</div><div class="tcellt">{charges(i).toFixed(arr)}</div></div>
<div class="titreligne tcellt">Taxe foncière</div><div class="titreligne tcellt">Cotisation foncière des entreprises</div><div class="titreligne tcellt">Excédent brut d'exploitation</div>
<div class="titreligne tcellt">Taxe foncière</div><div class="titreligne tcellt">Cotisation foncière des entreprises</div><div class="titreligne tcellt">Excédent brut d'exploitation</div>
<div class="d-flex flex-column my-4"><div class="tcellt">{an + i}</div><div class="tcellt">{valeurAjoutee(i).toFixed(arr)}</div><div class="tcellt">{accise(i).toFixed(arr)}</div><div class="tcellt">{ifer(i).toFixed(arr)}</div><div class="tcellt">{taxeFonciere(i).toFixed(arr)}</div><div class="tcellt">{cfe(i).toFixed(arr)}</div><div class="tcellt">{ebe(i).toFixed(arr)}</div></div>
<div class="d-flex flex-column my-4"><div class="tcellt">{an + i}</div><div class="tcellt">{valeurAjoutee(i).toFixed(arr)}</div><div class="tcellt">{accise(i).toFixed(arr)}</div><div class="tcellt">{ifer(i).toFixed(arr)}</div><div class="tcellt">{taxeFonciere(i).toFixed(arr)}</div><div class="tcellt">{cfe(i).toFixed(arr)}</div><div class="tcellt">{ebe(i).toFixed(arr)}</div></div>
<div class="titreligne tcellt">Amortissement</div><div class="titreligne tcellt">Intérêts dette senior</div><div class="titreligne tcellt">Intérêts DSRA</div><div class="titreligne tcellt">Résultat fiscal</div><div class="titreligne tcellt">Impôt sur les sociétés</div><div class="titreligne tcellt">Résultat net</div>
<div class="titreligne tcellt">Amortissement</div><div class="titreligne tcellt">Intérêts dette senior</div><div class="titreligne tcellt">Intérêts DSRA</div><div class="titreligne tcellt">Résultat fiscal</div><div class="titreligne tcellt">Impôt sur les sociétés</div><div class="titreligne tcellt">Résultat net</div>
<div class="d-flex flex-column my-4"><div class="tcellt">{an + i}</div><div class="tcellt">{provisionOnduleurs(i).toFixed(arr)}</div><div class="tcellt">{amortissement(i).toFixed(arr)}</div><div class="tcellt">{interetsDetteSenior(i).toFixed(arr)}</div><div class="tcellt">{interetsDSRA(i).toFixed(arr)}</div><div class="tcellt">{resultatFiscal(i).toFixed(arr)}</div><div class="tcellt">{is(i).toFixed(arr)}</div><div class="tcellt">{resultatNet(i).toFixed(arr)}</div></div>
<div class="d-flex flex-column my-4"><div class="tcellt">{an + i}</div><div class="tcellt">{provisionOnduleurs(i).toFixed(arr)}</div><div class="tcellt">{amortissement(i).toFixed(arr)}</div><div class="tcellt">{interetsDetteSenior(i).toFixed(arr)}</div><div class="tcellt">{interetsDSRA(i).toFixed(arr)}</div><div class="tcellt">{resultatFiscal(i).toFixed(arr)}</div><div class="tcellt">{is(i).toFixed(arr)}</div><div class="tcellt">{resultatNet(i).toFixed(arr)}</div></div>
{#if investissement > apport }<h5 class="my-3">Couverture de la dette</h5><div class="d-flex flex-wrap"><div class="d-flex flex-column my-3"><div class="titreligne tcellt">Année</div><div class="titreligne tcellt">DSCR</div>
{#if investissement > apport}<h5 class="my-3">Couverture de la dette</h5><div class="d-flex flex-wrap"><div class="d-flex flex-column my-3"><div class="titreligne tcellt">Année</div><div class="titreligne tcellt">DSCR</div></div>{#each Array(Math.ceil(N)) as _, i}<div class="d-flex flex-column my-3"><div class="tcellt">{an + i}</div><div class="tcellt">{fmt(2).format(dscr(i))}</div></div>{/each}
{#each Array(Math.ceil(N)) as _, i}<div class="d-flex flex-column my-3"><div class="tcellt">{an + i}</div><div class="tcellt">{fmt(2).format(dscr(i))}</div></div>{/each}</div>
<div class="tab-pane fade {banqueActive} {banqueShow} p-3" id="banque-tab-pane" role="tabpanel" aria-labelledby="banque-tab" tabindex="0"><h3 class="my-3 fs-1 fw-bold ">Tous <span class="text-primary">les recoins</span> de votre emprunt.</h3><Banque dette = {dette} taux={p.interet / 100} duree={p.echeances} bind:interetsAnnuels={interetsAnnuels} bind:remboursementAnnuel={remboursementAnnuel} />
<divclass="tab-pane fade {banqueActive} {banqueShow} p-3"id="banque-tab-pane"role="tabpanel"aria-labelledby="banque-tab"tabindex="0"><h3 class="my-3 fs-1 fw-bold">Tous <span class="text-primary">les recoins</span> de votreemprunt.</h3><Banque{dette}taux={p.interet / 100}duree={p.echeances}bind:interetsAnnuelsbind:remboursementAnnuel />
<div class="tab-pane fade {expertActive} {expertShow} py-3" id="expert-tab-pane" role="tabpanel" aria-labelledby="expert-tab" tabindex="0">
<divclass="tab-pane fade {expertActive} {expertShow} py-3"id="expert-tab-pane"role="tabpanel"aria-labelledby="expert-tab"tabindex="0">
<label class="form-label" for="enedis">Coût de raccordement Enedis</label><input class="form-control form-control-sm" type="number" id="enedis" min="0" bind:value={p.enedis}/>
<label class="form-label" for="enedis">Coût de raccordement Enedis</label><inputclass="form-control form-control-sm"type="number"id="enedis"min="0"bind:value={p.enedis} />
<label class="form-label" for="productible">Productible annuel (kWh/kWc)</label><input class="form-control form-control-sm" type="number" id="productible" min="0" bind:value={p.productible}/>
<label class="form-label" for="productible">Productible annuel (kWh/kWc)</label><inputclass="form-control form-control-sm"type="number"id="productible"min="0"bind:value={p.productible} />
<label class="form-label" for="ratio">Ratio installation (€/W)</label><input class="form-control form-control-sm" type="number" id="ratio" min="0" bind:value={p.ratio}/>
<label class="form-label" for="ratio">Ratio installation (€/W)</label><inputclass="form-control form-control-sm"type="number"id="ratio"min="0"bind:value={p.ratio} />
<label class="form-label" for="degradation">Taux de dégradation PV(%)</label><input class="form-control form-control-sm" type="number" id="degradation" min="0" bind:value={p.degradation}/>
<label class="form-label" for="degradation">Taux de dégradation PV(%)</label><inputclass="form-control form-control-sm"type="number"id="degradation"min="0"bind:value={p.degradation} />
<label class="form-label" for="inflation">Inflation tarif local</label><input class="form-control form-control-sm" type="number" id="inflation" min="0" bind:value={p.inflation}/>
<label class="form-label" for="inflation">Inflation tarif local</label><inputclass="form-control form-control-sm"type="number"id="inflation"min="0"bind:value={p.inflation} />
<div class="tab-pane fade {simuActive} {simuShow} show p-3" id="simu-tab-pane" role="tabpanel" aria-labelledby="simu-tab" tabindex="0">
<divclass="tab-pane fade {simuActive} {simuShow} show p-3"id="simu-tab-pane"role="tabpanel"aria-labelledby="simu-tab"tabindex="0">
<Simulation id={data.id} server={server} assets={assets} prmsFeature={prmsFeature} bind:prms={data.prms} puissance={p.puissance} bind:prodWeekly={prodWeekly} bind:maxProd={maxProd} bind:pvgis_loading={pvgis_loading} />
<Simulationid={data.id}{server}{assets}{prmsFeature}bind:prms={data.prms}puissance={p.puissance}bind:prodWeeklybind:maxProdbind:pvgis_loading />
<h5 class="modal-title pb-3" id="saveModalLabel">Sauvegarder</h5><form method="POST" id="saveForm" action="?/save" use:enhance={save}>
<h5 class="modal-title pb-3" id="saveModalLabel">Sauvegarder</h5><formmethod="POST"id="saveForm"action="?/save"use:enhance={save}>
<label class="form-label" for="nom">Nom du projet</label><input class="form-control" type="text" id="nom" name="nom" bind:value={data.nom} required/>
<label class="form-label" for="nom">Nom du projet</label><inputclass="form-control"type="text"id="nom"name="nom"bind:value={data.nom}required />
<label class="form-label" for="porteur">Prénom et nom du porteur du projet</label><input class="form-control" type="text" id="porteur" name="porteur" bind:value={data.porteur}/>
<label class="form-label" for="porteur">Prénom et nom du porteur du projet</label><inputclass="form-control"type="text"id="porteur"name="porteur"bind:value={data.porteur} />
<label class="form-label" for="adresse">Adresse</label><input class="form-control" type="text" id="adresse" name="adresse" bind:value={data.adresse}/>
<label class="form-label" for="adresse">Adresse</label><inputclass="form-control"type="text"id="adresse"name="adresse"bind:value={data.adresse} />
<label class="form-label" for="tel">Téléphone</label><input class="form-control" type="text" id="tel" name="tel" bind:value={data.tel}/>
<label class="form-label" for="tel">Téléphone</label><inputclass="form-control"type="text"id="tel"name="tel"bind:value={data.tel} />
<button form="saveForm" class="btn btn-primary">Sauvegarder</button><button type="button" class="btn btn-outline-primary" data-bs-dismiss="modal">Annuler</button>
<button form="saveForm" class="btn btn-primary">Sauvegarder</button><buttontype="button"class="btn btn-outline-primary"data-bs-dismiss="modal">Annuler</button>
@media (prefers-color-scheme: light) {nav {background-color: #fff !important;}}
@media (prefers-color-scheme: light) {nav {background-color: #fff !important;}}
input.prix::-webkit-outer-spin-button,input.prix::-webkit-inner-spin-button {/* display: none; <- Crashes Chrome on hover */-webkit-appearance: none;margin: 0; /* <-- Apparently some margin are still there even though it's hidden */}
input.prix::-webkit-outer-spin-button,input.prix::-webkit-inner-spin-button {/* display: none; <- Crashes Chrome on hover */-webkit-appearance: none;margin: 0; /* <-- Apparently some margin are still there even though it's hidden */}
import { error } from '@sveltejs/kit';import type { PageServerLoad, Actions } from './$types';import { userForm, Grain, save, del } from '../../../helpers';
import { error } from '@sveltejs/kit'import type { PageServerLoad, Actions } from './$types'import { userForm, Grain, save, del } from '../../../helpers'
return <Grain.GetProjetResp & { guest?: boolean }> {nom: "",id: "",porteur: "",tel: "",adresse: "",simulation: { ... sim },
return <Grain.GetProjetResp & { guest?: boolean }>{nom: '',id: '',porteur: '',tel: '',adresse: '',simulation: { ...sim },
<p><span class="text-primary align-top"><span class="g">G</span><span class="ra">RA</span>IN</span> est l'outil de simulation photovoltaïque développé par <span class="text-primary align-top"><span class="g">CO</span><span class="ra">TURN</span>IX</span> en 2023. Il est accessible en version gratuite pour tous et en version payante pour les fournisseurs d'installation pour traiter un grand nombre de simulation.</p>
<p><span class="text-primary align-top"><span class="g">G</span><span class="ra">RA</span>IN</span>est l'outil de simulation photovoltaïque développé par<span class="text-primary align-top"><span class="g">CO</span><span class="ra">TURN</span>IX</span> en2023. Il est accessible en version gratuite pour tous et en version payantepour les fournisseurs d'installation pour traiter un grand nombre desimulation.</p>
<p><span class="text-primary align-top"><span class="g">CO</span><span class="ra">TURN</span>IX</span> a été fondée en 2017.</p>
<p><span class="text-primary align-top"><span class="g">CO</span><span class="ra">TURN</span>IX</span> aété fondée en 2017.</p>
<p>Elle offre des services de traitement et analyse de données au service de la performance énergétique.</p><p>Son nom vient du nom latin de la caille des blés. Cet oiseau migrateur est reconnu pour son incroyable capacité à optimiser naturellement chaque dépense d'énergie lors de ses longs vols et chaque intrant au sol pour se charger de la quantité de nourriture exacte dont elle a besoin jusqu'à sa prochaine pause. </p><p> <span class="text-primary align-top"><span class="g"> CO</span><span class="ra">TURN</span>IX</span> a regroupé dans son équipe des spécialistes de l’énergie, des mathématiques, de l’informatique et de la sociologie, ingénieurs et chercheurs, pour concevoir des technologies à la pointe du marché.</p>
<p>Elle offre des services de traitement et analyse de données auservice de la performance énergétique.</p><p>Son nom vient du nom latin de la caille des blés. Cet oiseaumigrateur est reconnu pour son incroyable capacité à optimisernaturellement chaque dépense d'énergie lors de ses longs vols etchaque intrant au sol pour se charger de la quantité de nourritureexacte dont elle a besoin jusqu'à sa prochaine pause.</p><p><span class="text-primary align-top"><span class="g"> CO</span><span class="ra">TURN</span>IX</span>a regroupé dans son équipe des spécialistes de l’énergie, des mathématiques,de l’informatique et de la sociologie, ingénieurs et chercheurs, pourconcevoir des technologies à la pointe du marché.</p>
console.log("load")const token = cookies.get('token')console.log("token", token)if(!token || !platform) {return null}try {console.log("verify token")const id = await verifyToken(platform.env, token)console.log("id", id)if (!id) {throw error(403, 'Forbidden');}const id_ = platform.env.USER.idFromString(id.id)const identite = await userForm(platform.env, id_, {Identite: {}})return { email: identite.email }} catch(e) {console.log("error", e)return null
console.log('load')const token = cookies.get('token')console.log('token', token)if (!token || !platform) {return null}try {console.log('verify token')const id = await verifyToken(platform.env, token)console.log('id', id)if (!id) {throw error(403, 'Forbidden')}const id_ = platform.env.USER.idFromString(id.id)const identite = await userForm(platform.env, id_, {Identite: {},})return { email: identite.email }} catch (e) {console.log('error', e)return null}
export let donnees: {projets: number,puissance: number,economies: number,};let fmt = (n: number) => Intl.NumberFormat('fr-FR', { maximumFractionDigits: n });
export let donnees: {projets: numberpuissance: numbereconomies: number}let fmt = (n: number) =>Intl.NumberFormat('fr-FR', { maximumFractionDigits: n })
function format(x : number){let f = 0let s = ''if (Math.abs(x) <= 1000){s = ' kWc'f = x} else if(Math.abs(x) <= 1000000) {s = ' MWc€'f = x/1000} else {s = ' GWc'f = x/1000000}return fmt(2).format(f) + s}
function format(x: number) {let f = 0let s = ''if (Math.abs(x) <= 1000) {s = ' kWc'f = x} else if (Math.abs(x) <= 1000000) {s = ' MWc€'f = x / 1000} else {s = ' GWc'f = x / 1000000}return fmt(2).format(f) + s}</script>
<div class="pb-3 mb-3 border-bottom border-4 border-primary fs-1 fw-bold bg-cc">{donnees.projets}</div><div>Simulations </div>
<divclass="pb-3 mb-3 border-bottom border-4 border-primary fs-1 fw-bold bg-cc">{donnees.projets}</div><div>Simulations</div>
<div class="flex-column justify-content-between text-center mx-3"><div class="pb-3 mb-3 border-bottom border-4 border-primary fs-1 fw-bold bg-cc fs-1 fw-bold">{format(donnees.puissance)}</div><div>Simulés </div>
<divclass="flex-column justify-content-between text-center mx-3"><divclass="pb-3 mb-3 border-bottom border-4 border-primary fs-1 fw-bold bg-cc fs-1 fw-bold">{format(donnees.puissance)}</div><div>Simulés</div>
<div class="pb-3 mb-3 border-bottom border-4 border-primary fs-1 fw-bold bg-cc fs-1 fw-bold">+{Math.round(donnees.economies / 1000)}k€</div>
<divclass="pb-3 mb-3 border-bottom border-4 border-primary fs-1 fw-bold bg-cc fs-1 fw-bold">+{Math.round(donnees.economies / 1000)}k€</div>
const marginTop = 30; // the top margin, in pixelsconst marginRight = 30; // the right margin, in pixelsconst marginBottom = 30; // the bottom margin, in pixelsconst marginLeft = 100; // the left margin, in pixelsconst inset = 0; // inset the default range, in pixelsconst width = 600; // the outer width of the chart, in pixelsconst height = 400; // the outer height of the chart, in pixelsconst xLabel = ''; // a label for the y-axisconst yLabel = 'Résultat net'; // a label for the y-axisconst xFormat = ''; // a format specifier string for the y-axisconst yFormat = '€'; // a format specifier string for the y-axisconst horizontalGrid = true; // show horizontal grid linesconst verticalGrid = true; // show vertical grid linesconst colors = ["#b81111", "#ffbf00"]; // fill color for dots && number of colors in fill array MUST match number of subsets in dataconst showDots = false; // whether dots should be displayedconst dotsFilled = true; // whether dots should be filled or outlinedconst r = 0; // (fixed) radius of dots, in pixelsconst strokeWidth = 1; // stroke width of line, in pixelsconst strokeOpacity = [1]; // stroke opacity of lineconst tooltipBackground = 'white'; // background color of tooltipconst tooltipTextColor = 'black'; // text color of tooltipconst strokeLinecap = 'round'; // stroke line cap of the lineconst strokeLinejoin = 'round'; // stroke line join of the lineconst xScalefactor = width / 180; //y-axis number of valuesconst yScalefactor = height / 40; //y-axis number of valuesconst curve = curveLinear; // method of interpolation between pointsconst xType = scaleLinear; // type of x-scaleconst insetTop = 50; // inset from topconst insetRight = inset; // inset from rightconst insetBottom = inset; // inset fro bottomconst insetLeft = inset; // inset from leftconst xRange = [marginLeft + insetLeft, width - marginRight - insetRight]; // [left, right]const yType = scaleLinear; // type of y-scaleconst yRange = [height - marginBottom - insetBottom, marginTop + insetTop]; // [bottom, top]
const marginTop = 30 // the top margin, in pixelsconst marginRight = 30 // the right margin, in pixelsconst marginBottom = 30 // the bottom margin, in pixelsconst marginLeft = 100 // the left margin, in pixelsconst inset = 0 // inset the default range, in pixelsconst width = 600 // the outer width of the chart, in pixelsconst height = 400 // the outer height of the chart, in pixelsconst xLabel = '' // a label for the y-axisconst yLabel = 'Résultat net' // a label for the y-axisconst xFormat = '' // a format specifier string for the y-axisconst yFormat = '€' // a format specifier string for the y-axisconst horizontalGrid = true // show horizontal grid linesconst verticalGrid = true // show vertical grid linesconst colors = ['#b81111', '#ffbf00'] // fill color for dots && number of colors in fill array MUST match number of subsets in dataconst showDots = false // whether dots should be displayedconst dotsFilled = true // whether dots should be filled or outlinedconst r = 0 // (fixed) radius of dots, in pixelsconst strokeWidth = 1 // stroke width of line, in pixelsconst strokeOpacity = [1] // stroke opacity of lineconst tooltipBackground = 'white' // background color of tooltipconst tooltipTextColor = 'black' // text color of tooltipconst strokeLinecap = 'round' // stroke line cap of the lineconst strokeLinejoin = 'round' // stroke line join of the lineconst xScalefactor = width / 180 //y-axis number of valuesconst yScalefactor = height / 40 //y-axis number of valuesconst curve = curveLinear // method of interpolation between pointsconst xType = scaleLinear // type of x-scaleconst insetTop = 50 // inset from topconst insetRight = inset // inset from rightconst insetBottom = inset // inset fro bottomconst insetLeft = inset // inset from leftconst xRange = [marginLeft + insetLeft, width - marginRight - insetRight] // [left, right]const yType = scaleLinear // type of y-scaleconst yRange = [height - marginBottom - insetBottom, marginTop + insetTop] // [bottom, top]
let I, xScale, gaps, cleanData, xDomain, yDomain, yScale, niceY, chartLine, pointsScaled, delaunayGrid, voronoiGrid, xTicks, xTicksFormatted, yTicks
let I,xScale,gaps,cleanData,xDomain,yDomain,yScale,niceY,chartLine,pointsScaled,delaunayGrid,voronoiGrid,xTicks,xTicksFormatted,yTicks
$: {// For a single set of dataxVals = []yVals = []if (!('data' in data[0])) {x = Object.keys(data[0])[0];y = Object.keys(data[0])[1];xVals = data.map((el: Record<string, any>) => el[x]);yVals = data.map((el: Record<string, any>) => el[y]);colorVals = data.map((_) => 0);points = data.map((el) => ({x: el[x],y: el[y],color: 0}));}// For data with subsets (NOTE: expects 'id' and 'data' keys)else {x = Object.keys(data[0]?.data[0])[0];y = Object.keys(data[0]?.data[0])[1];data.forEach((subset, i) => {subset.data.forEach((coordinate) => {xVals.push(coordinate[x]);yVals.push(coordinate[y]);colorVals.push(i);points.push({x: coordinate[x],y: coordinate[y],color: i});});subsets.push(subset.id);});}
$: {// For a single set of dataxVals = []yVals = []if (!('data' in data[0])) {x = Object.keys(data[0])[0]y = Object.keys(data[0])[1]xVals = data.map((el: Record<string, any>) => el[x])yVals = data.map((el: Record<string, any>) => el[y])colorVals = data.map((_) => 0)points = data.map((el) => ({x: el[x],y: el[y],color: 0,}))}// For data with subsets (NOTE: expects 'id' and 'data' keys)else {x = Object.keys(data[0]?.data[0])[0]y = Object.keys(data[0]?.data[0])[1]data.forEach((subset, i) => {subset.data.forEach((coordinate) => {xVals.push(coordinate[x])yVals.push(coordinate[y])colorVals.push(i)points.push({x: coordinate[x],y: coordinate[y],color: i,})})subsets.push(subset.id)})}
xDomain = [xVals[0], xVals[xVals.length - 1]];yDomain = [Math.min(...yVals), Math.max(...yVals)];xScale = xType(xDomain, xRange);yScale = yType(yDomain, yRange);niceY = scaleLinear().domain([Math.min(...yVals), Math.max(...yVals)]).nice();
xDomain = [xVals[0], xVals[xVals.length - 1]]yDomain = [Math.min(...yVals), Math.max(...yVals)]xScale = xType(xDomain, xRange)yScale = yType(yDomain, yRange)niceY = scaleLinear().domain([Math.min(...yVals), Math.max(...yVals)]).nice()
lines = [];colors.forEach((_color, j) => {const filteredI = I.filter((_el, i) => colorVals[i] === j);lines.push(chartLine(filteredI));});console.log("lines", lines)
lines = []colors.forEach((_color, j) => {const filteredI = I.filter((_el, i) => colorVals[i] === j)lines.push(chartLine(filteredI))})console.log('lines', lines)
pointsScaled = points.map((el) => [xScale(el.x), yScale(el.y), el.color]);delaunayGrid = Delaunay.from(pointsScaled);voronoiGrid = delaunayGrid.voronoi([0, 0, width, height]);
pointsScaled = points.map((el) => [xScale(el.x),yScale(el.y),el.color,])delaunayGrid = Delaunay.from(pointsScaled)voronoiGrid = delaunayGrid.voronoi([0, 0, width, height])
<svg {width} {height} viewBox="0 0 {width} {height}"cursor='crosshair'on:mouseout="{() => dotInfo = null}"on:blur="{() => dotInfo = null}">
<svg{width}{height}viewBox="0 0 {width} {height}"cursor="crosshair"on:mouseout={() => (dotInfo = null)}on:blur={() => (dotInfo = null)}>
<path class="line" fill='none' stroke-opacity={points[dotInfo[1]].color === i ? '1' : '0.1'} stroke={colors[i]} d={subsetLine} stroke-width={strokeWidth} stroke-linecap={strokeLinecap} stroke-linejoin={strokeLinejoin}/><circle cx={xScale(points[dotInfo[1]].x)} cy={yScale(points[dotInfo[1]].y)} r={r} stroke={colors[points[dotInfo[1]].color]} fill={dotsFilled} />
<pathclass="line"fill="none"stroke-opacity={points[dotInfo[1]].color === i? '1': '0.1'}stroke={colors[i]}d={subsetLine}stroke-width={strokeWidth}stroke-linecap={strokeLinecap}stroke-linejoin={strokeLinejoin} /><circlecx={xScale(points[dotInfo[1]].x)}cy={yScale(points[dotInfo[1]].y)}{r}stroke={colors[points[dotInfo[1]].color]}fill={dotsFilled} />
<path class="line" fill='none' stroke={colors[i]} d={subsetLine}stroke-opacity={strokeOpacity[i]} stroke-width={strokeWidth} stroke-linecap={strokeLinecap} stroke-linejoin={strokeLinejoin} />
<pathclass="line"fill="none"stroke={colors[i]}d={subsetLine}stroke-opacity={strokeOpacity[i]}stroke-width={strokeWidth}stroke-linecap={strokeLinecap}stroke-linejoin={strokeLinejoin} />
<g class="y-axis" transform="translate({marginLeft}, 0)" pointer-events='none'><path class="domain" stroke="black" d="M{insetLeft}, {marginTop} V{height - marginBottom + 6}"/>
<gclass="y-axis"transform="translate({marginLeft}, 0)"pointer-events="none"><pathclass="domain"stroke="black"d="M{insetLeft}, {marginTop} V{height - marginBottom + 6}" />
<g class="x-axis" transform="translate(0,{height - marginBottom - insetBottom})" pointer-events='none'><path class="domain" stroke="black" d="M{marginLeft},0.5 H{width - marginRight}"/>
<gclass="x-axis"transform="translate(0,{height - marginBottom - insetBottom})"pointer-events="none"><pathclass="domain"stroke="black"d="M{marginLeft},0.5 H{width - marginRight}" />
<div class="tooltip" style='position:absolute; left:{dotInfo[2].pageX + 12}px; top:{dotInfo[2].pageY + 12}px; pointer-events:none; background-color:{tooltipBackground}; color:{tooltipTextColor}'>
<divclass="tooltip"style="position:absolute; left:{dotInfo[2].pageX +12}px; top:{dotInfo[2].pageY +12}px; pointer-events:none; background-color:{tooltipBackground}; color:{tooltipTextColor}">
.chart-container {justify-content: center;align-items: center;margin-top: 50px;margin-left: 80px;}svg {max-width: 100%;height: auto;height: "intrinsic";margin: auto;}path {fill: "green"}.y-axis {font-size: "10px";font-family: sans-serif;text-anchor: "end";}.x-axis {font-size: "10px";font-family: sans-serif;text-anchor: "end";}.tick text { font-size: 80%; fill: white !important }.tick {opacity: 1;}.tick-start {stroke: black;stroke-opacity: 1;}.tick-grid {stroke: black;stroke-opacity: 0.2;font-size: "11px";color: black;}.tick text {fill: black;}.y-axis .tick text {text-anchor: end !important;}
.chart-container {justify-content: center;align-items: center;margin-top: 50px;margin-left: 8 0px;}svg {max-width: 100%;height: auto;height: 'intrinsic';margin: auto;}path {fill: 'green';}.y-axis {font-size: '10px';font-family: sans-serif;text-anchor: 'end';}.x-axis {font-size: '10px';font-family: sans-serif;text-anchor: 'end';}.tick text {font-size: 80%;fill: white !important;}.tick {opacity: 1;}.tick-start {stroke: black;stroke-opacity: 1;}.tick-grid {stroke: black;stroke-opacity: 0.2;font-size: '11px';color: black;}.tick text {fill: black;}
@media (prefers-color-scheme: dark) {.y-axis text { fill: white; }.x-axis text { fill: white; }.tick-start {stroke: white;}.tick-grid {stroke: white;}.tick text {fill: white;}.domain { stroke: white }}
.y-axis .tick text {text-anchor: end !important;}
.tooltip{border-radius: 5px;padding: 5px;box-shadow: rgba(0, 0, 0, 0.4) 0px 2px 4px, rgba(0, 0, 0, 0.3) 0px 7px 13px -3px, rgba(0, 0, 0, 0.2) 0px -3px 0px inset;opacity: 1;}
.tooltip {border-radius: 5px;padding: 5px;box-shadow: rgba(0, 0, 0, 0.4) 0px 2px 4px,rgba(0, 0, 0, 0.3) 0px 7px 13px -3px,rgba(0, 0, 0, 0.2) 0px -3px 0px inset;opacity: 1;}
export let remboursement = new Array(duree + 1)export let remboursementAnnuel = new Array(dureeAns_)export let crd = new Array(duree + 1)export let crdAnnuel = new Array(dureeAns_)export let interets = new Array(duree + 1)export let interetsAnnuels = new Array(dureeAns_)
export let remboursement = new Array(duree + 1)export let remboursementAnnuel = new Array(dureeAns_)export let crd = new Array(duree + 1)export let crdAnnuel = new Array(dureeAns_)export let interets = new Array(duree + 1)export let interetsAnnuels = new Array(dureeAns_)
remboursement = new Array(duree + 1)crd = new Array(duree + 1)interets = new Array(duree + 1)remboursementAnnuel = new Array(dureeAns_)crdAnnuel = new Array(dureeAns_)interetsAnnuels = new Array(dureeAns_)
remboursement = new Array(duree + 1)crd = new Array(duree + 1)interets = new Array(duree + 1)remboursementAnnuel = new Array(dureeAns_)crdAnnuel = new Array(dureeAns_)interetsAnnuels = new Array(dureeAns_)
crd[0] = detteremboursement[0] = 0interets[0] = 0crdAnnuel[0] = detteremboursementAnnuel[0] = 0interetsAnnuels[0] = 0for(let i = 1; i <= duree; i++) {if(i <= periodeRemboursementCapital) {remboursement[i] = 0} else if (i < nombreEcheancesPeriodeTronquee) {remboursement[i] = ppmt(taux * prorataPeriodique,i - periodeRemboursementCapital,totalPeriodes,-dette,)} else if (i == nombreEcheances) {remboursement[i] = crd[i-1]} else {remboursement[i] = 0}crd[i] = crd[i-1] - remboursement[i]interets[i] = crd[i-1] * taux * prorataPeriodiqueif((i % nombrePeriodesParAn) == 0) {crdAnnuel[i/nombrePeriodesParAn] = crd[i]remboursementAnnuel[i/nombrePeriodesParAn] = 0interetsAnnuels[i/nombrePeriodesParAn] = 0}remboursementAnnuel[Math.floor(i/nombrePeriodesParAn)] += remboursement[i]interetsAnnuels[Math.floor(i/nombrePeriodesParAn)] += interets[i]}}
crd[0] = detteremboursement[0] = 0interets[0] = 0crdAnnuel[0] = detteremboursementAnnuel[0] = 0interetsAnnuels[0] = 0for (let i = 1; i <= duree; i++) {if (i <= periodeRemboursementCapital) {remboursement[i] = 0} else if (i < nombreEcheancesPeriodeTronquee) {remboursement[i] = ppmt(taux * prorataPeriodique,i - periodeRemboursementCapital,totalPeriodes,-dette)} else if (i == nombreEcheances) {remboursement[i] = crd[i - 1]} else {remboursement[i] = 0}crd[i] = crd[i - 1] - remboursement[i]interets[i] = crd[i - 1] * taux * prorataPeriodiqueif (i % nombrePeriodesParAn == 0) {crdAnnuel[i / nombrePeriodesParAn] = crd[i]remboursementAnnuel[i / nombrePeriodesParAn] = 0interetsAnnuels[i / nombrePeriodesParAn] = 0}remboursementAnnuel[Math.floor(i / nombrePeriodesParAn)] +=remboursement[i]interetsAnnuels[Math.floor(i / nombrePeriodesParAn)] += interets[i]}}
table {font-size: 90%;}th{font-size:1rem;font-weight:bold;}td{padding: 5px 5px;padding: 5px 7px 5px 10px;text-align:end;border:none;}
table {font-size: 90%;}th {font-size: 1rem;font-weight: bold;}td {padding: 5px 5px;padding: 5px 7px 5px 10px;text-align: end;border: none;}
import { base as b, assets as a } from '$app/paths'import type { PageData } from './$types';import { onMount } from 'svelte';import '../app.scss';import { email } from '../stores'import Donnees from './Donnees.svelte'export let data: PageData;export let base = bexport let assets: string = aonMount(() => {email.set(data.email || null)})
import { base as b, assets as a } from '$app/paths'import type { PageData } from './$types'import { onMount } from 'svelte'import '../app.scss'import { email } from '../stores'import Donnees from './Donnees.svelte'export let data: PageDataexport let base = bexport let assets: string = aonMount(() => {email.set(data.email || null)})
<h1 class="text-uppercase lh-1" style="font-size:4rem;width:50%">No GRAIN,<br/>No gain.</h1><h2 class="sub">L'outil <span class="text-primary">gratuit</span> de faisabilité d'autoconsommation.</h2><a class="mt-3 btn btn-primary" href="{base}/projet/nouveau">Lancer ma simulation</a>
<h1 class="text-uppercase lh-1" style="font-size:4rem;width:50%">No GRAIN,<br />No gain.</h1><h2 class="sub">L'outil <span class="text-primary">gratuit</span> de faisabilitéd'autoconsommation.</h2><a class="mt-3 btn btn-primary" href="{base}/projet/nouveau">Lancer ma simulation</a>
<Donnees donnees = {data.donnees}/><h1 class="my-5 lh-1 text-center">Simulez <span class="text-primary fw-bold">gratuitement</span> vos <span class="text-primary fw-bold">revenus</span> photovoltaïques.</h1>
<Donnees donnees={data.donnees} /><h1 class="my-5 lh-1 text-center">Simulez <span class="text-primary fw-bold">gratuitement</span> vos<span class="text-primary fw-bold">revenus</span> photovoltaïques.</h1>
<h2> <span class="text-primary fw-bold">Faisabilité </span>et <span class="text-primary fw-bold">optimisation</span> </h2><p> <span class="text-primary fs-5 align-bottom"><span class="logoCol1"> G</span><span class="logoCol2">RA</span>IN</span> vous donne l'ensemble des informations économique de votre projet d'auto-consommation et d'auto-consommation collective pour <span class="text-primary fw-bold">prévoir</span>, <span class="text-primary fw-bold">choisir</span>, <span class="text-primary fw-bold">optimiser</span> votre installation photovoltaïque et son utilisation.<br/>Partagez une énergie <span class="text-primary fw-bold">moins cher</span>, <span class="text-primary fw-bold">local</span> et <span class="text-primary fw-bold">de saison</span>.
<h2><span class="text-primary fw-bold">Faisabilité </span>et<span class="text-primary fw-bold">optimisation</span></h2><p><span class="text-primary fs-5 align-bottom"><span class="logoCol1"> G</span><span class="logoCol2">RA</span>IN</span>vous donne l'ensemble des informations économique de votre projetd'auto-consommation et d'auto-consommation collective pour<span class="text-primary fw-bold">prévoir</span>,<span class="text-primary fw-bold">choisir</span>,<span class="text-primary fw-bold">optimiser</span>votre installation photovoltaïque et son utilisation.<br />Partagez une énergie<span class="text-primary fw-bold">moins cher</span>,<span class="text-primary fw-bold">local</span>et <span class="text-primary fw-bold">de saison</span>.
<h2>Reprenez <span class="text-primary fw-bold">les rennes</span>.</h2><p>Avec toutes les informations, simulez le futur de votre production d'énergie et reprennez le pouvoir sur votre énergie.<br/> <span class="text-primary fw-bold"> Simplement*</span>, <span class="text-primary fw-bold">rapidement</span> et <span class="text-primary fw-bold">gratuitement</span>.<br/> Créez votre futur !
<h2>Reprenez <span class="text-primary fw-bold">les rennes</span>.</h2><p>Avec toutes les informations, simulez le futur de votreproduction d'énergie et reprennez le pouvoir sur votre énergie.<br /><span class="text-primary fw-bold"> Simplement*</span>,<span class="text-primary fw-bold">rapidement</span>et <span class="text-primary fw-bold">gratuitement</span>.<br />Créez votre futur !
<h2>Et <span class="text-primary fw-bold">ensuite</span> ? </h2><p>Ensuite, passez sur <span class="text-primary fs-6 align-bottom"><span class="logoCol1"> CO</span><span class="logoCol2">TURN</span>IX</span> pour partager l'énergie de vos panneaux photovoltaïque avec vos voisins.<span class="text-primary fs-6 align-bottom"><span class="logoCol1"> CO</span><span class="logoCol2">TURN</span>IX</span> gère aussi les flux financiers entre les participants.<br/>Oui, <span class="text-primary fw-bold">on fait tout ça.</span>.
<h2>Et <span class="text-primary fw-bold">ensuite</span> ?</h2><p>Ensuite, passez sur <span class="text-primary fs-6 align-bottom"><span class="logoCol1"> CO</span><span class="logoCol2">TURN</span>IX</span>pour partager l'énergie de vos panneaux photovoltaïque avec vos voisins.<span class="text-primary fs-6 align-bottom"><span class="logoCol1"> CO</span><span class="logoCol2">TURN</span>IX</span>gère aussi les flux financiers entre les participants.<br />Oui,<span class="text-primary fw-bold">on fait tout ça.</span>.
.sub {font-size: 1.4rem;font-weight: bold;margin: 20px 0;}.img{height:calc(max(400px, 100vh - 120px));background-size: calc(min(75vw, (180/70)*50vh)) calc(min(50vh, (70/180)*75vw));width: 100%;background-position:bottom 0px right 0px;background-repeat:no-repeat;}
.sub {font-size: 1.4rem;font-weight: bold;margin: 20px 0;}.img {height: calc(max(1200px, 100vh - 120px));background-size: calc(min(75vw, (180/70) * 50vh))calc(min(50vh, (70/180) * 75vw));width: 100%;background-position: bottom 0px right 0px;background-repeat: no-repeat;}
@media not (prefers-color-scheme: dark) {.card {background-color:color-mix(in srgb, var(--bs-body-bg), transparent 30%)}}
@media not (prefers-color-scheme: dark) {.card {background-color: color-mix(in srgb,var(--bs-body-bg),transparent 30%);}}
<a class="nav-link " href="{base}"><span class="text-primary fs-1 align-middle"><span class="logoCol1"> G</span><span class="logoCol2">RA</span>IN</span><img src="{assets}/grain.svg" alt="Coturnix" style="width:30px;height:30px"/>
<a class="nav-link" href={base}><span class="text-primary fs-1 align-middle"><span class="logoCol1"> G</span><span class="logoCol2">RA</span>IN</span><imgsrc="{assets}/grain.svg"alt="Coturnix"style="width:30px;height:30px" />
main {font-family: 'Lato', sans-serif;flex: 1;display: flex;flex-direction: column;width: 100%;margin: 0 auto;box-sizing: border-box;}footer {display: flex;justify-content: center;align-items: center;padding: 8px;background-color: $primary;}
main {font-family: 'Lato', sans-serif;flex: 1;display: flex;flex-direction: column;width: 100%;margin: 0 auto;box-sizing: border-box;}footer {display: flex;justify-content: center;align-items: center;padding: 8px;background-color: $primary;}
export async function userForm(env: EnvUser, id: DurableObjectId, body: Grain.CreateProjet): Promise<Grain.CreateProjetResp>export async function userForm(env: EnvUser, id: DurableObjectId, body: Grain.SaveProjet): Promise<null>export async function userForm(env: EnvUser, id: DurableObjectId, body: Grain.ListProjets): Promise<Grain.ListProjetsResp>export async function userForm(env: EnvUser, id: DurableObjectId, body: Grain.DelProjet): Promise<null>export async function userForm(env: EnvUser, id: DurableObjectId, body: Grain.GetProjet): Promise<Grain.GetProjetResp>export async function userForm(env: EnvUser, id: DurableObjectId, body: Grain.Cmd): Promise<any> {let headers = new Headers();headers.set("Content-Type", "application/json");let stub = env.USER.get(id);let x = await (await stub.fetch("https://y.coturnix.fr",{method: "POST",
export async function userForm(env: EnvUser,id: DurableObjectId,body: Grain.CreateProjet): Promise<Grain.CreateProjetResp>export async function userForm(env: EnvUser,id: DurableObjectId,body: Grain.SaveProjet): Promise<null>export async function userForm(env: EnvUser,id: DurableObjectId,body: Grain.ListProjets): Promise<Grain.ListProjetsResp>export async function userForm(env: EnvUser,id: DurableObjectId,body: Grain.DelProjet): Promise<null>export async function userForm(env: EnvUser,id: DurableObjectId,body: Grain.GetProjet): Promise<Grain.GetProjetResp>export async function userForm(env: EnvUser,id: DurableObjectId,body: Grain.Cmd): Promise<any> {let headers = new Headers()headers.set('Content-Type', 'application/json')let stub = env.USER.get(id)let x = await (await stub.fetch('https://y.coturnix.fr', {method: 'POST',
cout += tarifLocal(p, i) * consoMoyenneFoyer(p, i) * p.autoprod / 100+ p.coutElec * Math.pow(1 + p.inflationElec / 100, i) * consoMoyenneFoyer(p, i) * (100 - p.autoprod) / 100
cout +=(tarifLocal(p, i) * consoMoyenneFoyer(p, i) * p.autoprod) / 100 +(p.coutElec *Math.pow(1 + p.inflationElec / 100, i) *consoMoyenneFoyer(p, i) *(100 - p.autoprod)) /100
export function productionAnnuelle(p: Grain.SimulationCommunaute, i: number){return p.productible * p.puissance * Math.pow(1-(p.degradation)/100, i)
export function productionAnnuelle(p: Grain.SimulationCommunaute, i: number) {return p.productible * p.puissance * Math.pow(1 - p.degradation / 100, i)
puissance: number,economies?: number,autoconso: number,autoprod: number,fraisDivers: number,prix: number,apport: number,interet: number,echeances: number,consoMoyenneFoyer: number,productible: number,degradation: number,inflation: number,ratio: number,enedis: number,
puissance: numbereconomies?: numberautoconso: numberautoprod: numberfraisDivers: numberprix: numberapport: numberinteret: numberecheances: numberconsoMoyenneFoyer: numberproductible: numberdegradation: numberinflation: numberratio: numberenedis: number
limites: number[],prix: number[],inflation: number,},coutElec: number,inflationElec: number,maintenance: number,turpe: number,turpeInjection: number,provisionOnduleurs: number,assurance: number,divers: number,ratioDcAc: number,dureeAmortissement: number,tauxIS: number,tauxDSRA: number,
limites: number[]prix: number[]inflation: number}coutElec: numberinflationElec: numbermaintenance: numberturpe: numberturpeInjection: numberprovisionOnduleurs: numberassurance: numberdivers: numberratioDcAc: numberdureeAmortissement: numbertauxIS: numbertauxDSRA: number
name?: string,porteur?: string,tel?: string,adresse?: string,simulation?: SimulationCommunaute,prms: Prm[],
name?: stringporteur?: stringtel?: stringadresse?: stringsimulation?: SimulationCommunauteprms: Prm[]
id: string,name?: string,porteur?: string,tel?: string,adresse?: string,simulation?: SimulationCommunaute,prms: Prm[],
id: stringname?: stringporteur?: stringtel?: stringadresse?: stringsimulation?: SimulationCommunauteprms: Prm[]
<meta name="viewport" content="width=device-width, initial-scale=1"><link rel="stylesheet" href="%sveltekit.assets%/bootstrap-icons.css"><link rel="preconnect" href="https://fonts.googleapis.com"><link rel="preconnect" href="https://fonts.gstatic.com" crossorigin><link href="https://fonts.googleapis.com/css2?family=Lato:wght@650&family=Roboto:wght@700&display=swap" rel="stylesheet"><link href="/favicon.png" rel="icon">
<meta name="viewport" content="width=device-width, initial-scale=1" /><link rel="stylesheet" href="%sveltekit.assets%/bootstrap-icons.css" /><link rel="preconnect" href="https://fonts.googleapis.com" /><link rel="preconnect" href="https://fonts.gstatic.com" crossorigin /><linkhref="https://fonts.googleapis.com/css2?family=Lato:wght@650&family=Roboto:wght@700&display=swap"rel="stylesheet" /><link href="/favicon.png" rel="icon" />
staticnode_modulessrc/simulation_communaute.js.svelte-kit