├── .browserslistrc ├── .editorconfig ├── .eslintrc.json ├── .github └── workflows │ └── ci.yml ├── .gitignore ├── .npmignore ├── .nvmrc ├── .prettierignore ├── .prettierrc ├── LICENSE ├── README.md ├── angular.json ├── karma.conf.js ├── lib ├── index.ts ├── ng-package.json ├── package.json ├── public_api.ts ├── spec │ └── loader.service.spec.ts ├── src │ ├── aqm-panorama.component.ts │ ├── aqm.component.ts │ ├── aqm.config.ts │ ├── aqm.core.ts │ ├── aqm.module.ts │ └── loader.service.ts ├── test.ts └── tsconfig.lib.json ├── package.json ├── scripts └── build.js ├── src ├── app │ ├── app.component.ts │ ├── app.module.ts │ └── components │ │ ├── demo.component.html │ │ ├── demo.component.scss │ │ ├── demo.component.ts │ │ ├── gljs.component.html │ │ ├── gljs.component.ts │ │ ├── panorama.component.html │ │ ├── panorama.component.scss │ │ └── panorama.component.ts ├── assets │ └── fork.png ├── environments │ ├── environment.prod.ts │ └── environment.ts ├── index.html ├── main.ts └── polyfills.ts ├── tsconfig.app.json ├── tsconfig.json └── tsconfig.spec.json /.browserslistrc: -------------------------------------------------------------------------------- 1 | # This file is used by the build system to adjust CSS and JS output to support the specified browsers below. 2 | # For additional information regarding the format and rule options, please see: 3 | # https://github.com/browserslist/browserslist#queries 4 | 5 | # For the full list of supported browsers by the Angular framework, please see: 6 | # https://angular.io/guide/browser-support 7 | 8 | # You can see what browsers were selected by your queries by running: 9 | # npx browserslist 10 | 11 | last 1 Chrome version 12 | last 1 Firefox version 13 | last 2 Edge major versions 14 | last 2 Safari major versions 15 | last 2 iOS major versions 16 | Firefox ESR 17 | not IE 11 # Angular supports IE 11 only as an opt-in. To opt-in, remove the 'not' prefix on this line. 18 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | # Editor configuration, see https://editorconfig.org 2 | root = true 3 | 4 | [*] 5 | charset = utf-8 6 | indent_style = space 7 | indent_size = 2 8 | insert_final_newline = true 9 | trim_trailing_whitespace = true 10 | 11 | [*.ts] 12 | quote_type = single 13 | 14 | [*.md] 15 | max_line_length = off 16 | trim_trailing_whitespace = false 17 | -------------------------------------------------------------------------------- /.eslintrc.json: -------------------------------------------------------------------------------- 1 | { 2 | "root": true, 3 | "ignorePatterns": [ 4 | "projects/**/*" 5 | ], 6 | "overrides": [ 7 | { 8 | "files": [ 9 | "*.ts" 10 | ], 11 | "parserOptions": { 12 | "project": [ 13 | "tsconfig.json", 14 | "e2e/tsconfig.json" 15 | ], 16 | "createDefaultProgram": true 17 | }, 18 | "extends": [ 19 | "plugin:@angular-eslint/recommended", 20 | "plugin:@angular-eslint/template/process-inline-templates" 21 | ], 22 | "rules": { 23 | "@angular-eslint/directive-selector": [ 24 | "off", 25 | { 26 | "type": "attribute", 27 | "prefix": "app", 28 | "style": "camelCase" 29 | } 30 | ], 31 | "@angular-eslint/component-selector": [ 32 | "off", 33 | { 34 | "type": "element", 35 | "prefix": "app", 36 | "style": "kebab-case" 37 | } 38 | ], 39 | "@angular-eslint/no-host-metadata-property": [ 40 | "off" 41 | ] 42 | } 43 | }, 44 | { 45 | "files": [ 46 | "*.html" 47 | ], 48 | "extends": [ 49 | "plugin:@angular-eslint/template/recommended" 50 | ], 51 | "rules": {} 52 | } 53 | ] 54 | } 55 | -------------------------------------------------------------------------------- /.github/workflows/ci.yml: -------------------------------------------------------------------------------- 1 | name: Ci 2 | 3 | on: push 4 | 5 | jobs: 6 | build: 7 | runs-on: ubuntu-latest 8 | steps: 9 | - name: checkout 10 | uses: actions/checkout@master 11 | 12 | - name: install 13 | run: npm install 14 | 15 | - name: run 16 | run: | 17 | npm run build 18 | 19 | test: 20 | runs-on: ubuntu-latest 21 | steps: 22 | - name: checkout 23 | uses: actions/checkout@master 24 | 25 | - name: install 26 | run: npm install 27 | 28 | - name: run 29 | run: | 30 | npm run test 31 | cat ./coverage/lcov.info | ./node_modules/.bin/codecov 32 | env: 33 | CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }} 34 | 35 | lint: 36 | runs-on: ubuntu-latest 37 | steps: 38 | - name: checkout 39 | uses: actions/checkout@master 40 | 41 | - name: install 42 | run: npm install 43 | 44 | - name: run 45 | run: | 46 | npm run lint 47 | 48 | site: 49 | runs-on: ubuntu-latest 50 | steps: 51 | - name: checkout 52 | uses: actions/checkout@master 53 | 54 | - name: install 55 | run: npm install 56 | 57 | - name: build 58 | run: | 59 | node --max_old_space_size=5120 ./node_modules/@angular/cli/bin/ng build --prod --base-href /angular-qq-maps/ 60 | cp ./dist/index.html ./dist/404.html 61 | ls ./dist 62 | 63 | - name: deploy-to-gh-pages 64 | uses: peaceiris/actions-gh-pages@v3 65 | with: 66 | github_token: ${{ secrets.GITHUB_TOKEN }} 67 | publish_dir: ./dist 68 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # See http://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # compiled output 4 | /dist 5 | /tmp 6 | /out-tsc 7 | /publish 8 | /yarn.lock 9 | 10 | # dependencies 11 | /node_modules 12 | 13 | # IDEs and editors 14 | /.idea 15 | .project 16 | .classpath 17 | .c9/ 18 | *.launch 19 | .settings/ 20 | *.sublime-workspace 21 | 22 | # IDE - VSCode 23 | .vscode/* 24 | !.vscode/settings.json 25 | !.vscode/tasks.json 26 | !.vscode/launch.json 27 | !.vscode/extensions.json 28 | 29 | # misc 30 | /.sass-cache 31 | /connect.lock 32 | /coverage 33 | /libpeerconnection.log 34 | npm-debug.log 35 | yarn-error.log 36 | testem.log 37 | /typings 38 | 39 | # System Files 40 | .DS_Store 41 | Thumbs.db 42 | -------------------------------------------------------------------------------- /.npmignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | 5 | # Runtime data 6 | pids 7 | *.pid 8 | *.seed 9 | 10 | # Directory for instrumented libs generated by jscoverage/JSCover 11 | lib-cov 12 | 13 | # Coverage directory used by tools like istanbul 14 | coverage 15 | 16 | # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) 17 | .grunt 18 | 19 | # Compiled binary addons (http://nodejs.org/api/addons.html) 20 | build/Release 21 | 22 | # Dependency directory 23 | # Commenting this out is preferred by some people, see 24 | # https://www.npmjs.org/doc/misc/npm-faq.html#should-i-check-my-node_modules-folder-into-git- 25 | node_modules 26 | 27 | # Users Environment Variables 28 | .lock-wscript 29 | .tsdrc 30 | 31 | #IntelliJ configuration files 32 | .idea 33 | 34 | dist 35 | dev 36 | docs 37 | lib 38 | test 39 | tmp 40 | 41 | Thumbs.db 42 | .DS_Store 43 | 44 | *.ts 45 | !*.d.ts 46 | 47 | src/app/example* 48 | src/public 49 | typings 50 | *_spec.* 51 | CONTRIBUTING.md 52 | gulpfile.ts 53 | favicon.ico 54 | karma-shim.js 55 | karma.conf.js 56 | make.js 57 | protractor.conf.js 58 | test-main.js 59 | tsconfig.json 60 | tslint.json 61 | typedoc.json 62 | typings.json 63 | webpack.config.js 64 | *.yml 65 | .jshintrc 66 | .editorconfig 67 | -------------------------------------------------------------------------------- /.nvmrc: -------------------------------------------------------------------------------- 1 | 12.16.1 2 | -------------------------------------------------------------------------------- /.prettierignore: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cipchk/angular-qq-maps/31511c003e668d1aa339d4827aa1d292cefba4d5/.prettierignore -------------------------------------------------------------------------------- /.prettierrc: -------------------------------------------------------------------------------- 1 | { 2 | "printWidth": 140, 3 | "singleQuote": true, 4 | "trailingComma": "all" 5 | } 6 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018-present 卡色 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # angular-qq-maps 2 | 3 | [QQ Maps](https://lbs.qq.com/) Components for Angular 4 | 5 | [![NPM version](https://img.shields.io/npm/v/angular-qq-maps.svg)](https://www.npmjs.com/package/angular-qq-maps) 6 | ![Ci](https://github.com/cipchk/angular-qq-maps/workflows/Ci/badge.svg) 7 | 8 | ## Demo 9 | 10 | - [Live Demo](https://cipchk.github.io/angular-qq-maps/) 11 | - [Stackblitz](https://stackblitz.com/edit/angular-qq-maps) 12 | 13 | ### 1、安装 14 | 15 | ``` 16 | npm install angular-qq-maps --save 17 | ``` 18 | 19 | 把 `AqmModule` 模块导入到你项目中。 20 | 21 | ```typescript 22 | import { AqmModule } from 'angular-qq-maps'; 23 | 24 | @NgModule({ 25 | imports: [ 26 | BrowserModule, 27 | AqmModule.forRoot({ 28 | apiKey: '' // app key为必选项 29 | }) 30 | ], 31 | declarations: [AppComponent], 32 | bootstrap: [AppComponent] 33 | }) 34 | export class AppModule { } 35 | ``` 36 | 37 | ### 2、使用 38 | 39 | **地图组件** 40 | 41 | ```html 42 | 43 | ``` 44 | 45 | **街景组件** 46 | 47 | ```html 48 | 49 | ``` 50 | 51 | 默认自动异步加载 js 类库,所以只需要在 NgModule 提供 api key 就可以立即使用了。 `options` 等同腾讯地图 `new qq.maps.Map(mapContainer, options)`。 52 | 53 | ## 关于事件注意点(很重要,请认真阅读) 54 | 55 | 我精力有限,而如果真要以Angular的角度去开发腾讯地图工作量非常大,而且官网也并无提供一份良好的Typescript接口定义,所以放弃过度性封装。正因为如此,所以您在注册**事件**的时候还是要认真一点。 56 | 57 | 腾讯地图除绝大部分所需要的事件都是依赖于 `qq.maps.event` 对象的创建和删除动作,Angular是一种单页开发模式,对资源的**创建与销毁**是非常重要的。如果你在开发腾讯地图的时候突然发现被污染了,那说明你的并没有正确的销毁。 58 | 59 | 因此,我建议,当你需要注册一个地图的 `click` 事件时: 60 | 61 | ```typescript 62 | //添加监听事件 63 | qq.maps.event.addListener(this.map, 'click', (event: any) => { 64 | // doing 65 | this.zone.run(() => { 66 | // 对于需要Angular监听的变量而放在 zone 里面,可以确保页面渲染。 67 | this.status = `click ${+new Date}`; 68 | }); 69 | }); 70 | ``` 71 | 72 | 与之相对应,一定要在 `ngOnDestroy` 对事件的销毁: 73 | 74 | ```typescript 75 | ngOnDestroy(): void { 76 | ['click'].forEach(eventName => { 77 | qq.maps.event.clearListeners(this.map, eventName); 78 | }); 79 | } 80 | ``` 81 | 82 | 当然,这里还有一些关于**覆盖物**相关里面涉及的事件,也一并做相应的销毁处理。 83 | 84 | **很抱歉,如果你在使用 `angular-qq-maps` 的时候请认真阅读**。 85 | 86 | ## AqmConfig 87 | 88 | | 名称 | 类型 | 默认值 | 描述 | 89 | | ------- | ------------- | ----- | ----- | 90 | | `gl` | `boolean` | `false` | 表示使用 [JavaScript API GL](https://lbs.qq.com/webApi/javascriptGL/glGuide/glOverview) 版本 | 91 | | `apiKey` | `string` | - | APP KEY 必填项 | 92 | | `apiHostAndPath` | `string` | `map.qq.com/api/js` | - | 93 | | `apiCallback` | `string` | `angularQQMapsLoader` | API异步加载回调函数名 | 94 | | `apiVersion` | `string` | `2.exp` | API版本号 | 95 | | `apiLibraries` | `string[]` | - | 附加库 | 96 | | `apiProtocol` | `string` | `auto` | API 请求协议 | 97 | | `mapOptions` | `Object` | - | 默认地图配置项,等同于[MapOptions 对象规范](http://lbs.qq.com/javascript_v2/doc/mapoptions.html),当指定 `gl: true` 表示Gl版本的[MapOptions 对象规范](https://lbs.qq.com/javascript_gl/doc/mapoptions.html) | 98 | | `panoramaOptions` | `Object` | - | 默认街景配置项,等同于[PanoramaOptions 对象规范](http://lbs.qq.com/javascript_v2/doc/panoramaoptions.html) | 99 | 100 | ## Troubleshooting 101 | 102 | Please follow this guidelines when reporting bugs and feature requests: 103 | 104 | 1. Use [GitHub Issues](https://github.com/cipchk/angular-qq-maps/issues) board to report bugs and feature requests (not our email address) 105 | 2. Please **always** write steps to reproduce the error. That way we can focus on fixing the bug, not scratching our heads trying to reproduce it. 106 | 107 | Thanks for understanding! 108 | 109 | ### License 110 | 111 | The MIT License (see the [LICENSE](https://github.com/cipchk/angular-qq-maps/blob/master/LICENSE) file for the full text) 112 | -------------------------------------------------------------------------------- /angular.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "./node_modules/@angular/cli/lib/config/schema.json", 3 | "version": 1, 4 | "newProjectRoot": "projects", 5 | "projects": { 6 | "angular-qq-maps": { 7 | "projectType": "application", 8 | "schematics": { 9 | "@schematics/angular:component": { 10 | "style": "less" 11 | }, 12 | "@schematics/angular:application": { 13 | "strict": true 14 | } 15 | }, 16 | "root": "", 17 | "sourceRoot": "src", 18 | "prefix": "app", 19 | "architect": { 20 | "build": { 21 | "builder": "@angular-devkit/build-angular:browser", 22 | "options": { 23 | "outputPath": "dist", 24 | "index": "src/index.html", 25 | "main": "src/main.ts", 26 | "polyfills": "src/polyfills.ts", 27 | "tsConfig": "tsconfig.app.json", 28 | "assets": [ 29 | "src/favicon.ico", 30 | "src/assets" 31 | ], 32 | "inlineStyleLanguage": "less", 33 | "styles": [], 34 | "scripts": [] 35 | }, 36 | "configurations": { 37 | "production": { 38 | "budgets": [ 39 | { 40 | "type": "initial", 41 | "maximumWarning": "500kb", 42 | "maximumError": "1mb" 43 | }, 44 | { 45 | "type": "anyComponentStyle", 46 | "maximumWarning": "2kb", 47 | "maximumError": "4kb" 48 | } 49 | ], 50 | "fileReplacements": [ 51 | { 52 | "replace": "src/environments/environment.ts", 53 | "with": "src/environments/environment.prod.ts" 54 | } 55 | ], 56 | "outputHashing": "all" 57 | }, 58 | "development": { 59 | "buildOptimizer": false, 60 | "optimization": false, 61 | "vendorChunk": true, 62 | "extractLicenses": false, 63 | "sourceMap": true, 64 | "namedChunks": true 65 | } 66 | }, 67 | "defaultConfiguration": "production" 68 | }, 69 | "serve": { 70 | "builder": "@angular-devkit/build-angular:dev-server", 71 | "configurations": { 72 | "production": { 73 | "browserTarget": "angular-qq-maps:build:production" 74 | }, 75 | "development": { 76 | "browserTarget": "angular-qq-maps:build:development" 77 | } 78 | }, 79 | "defaultConfiguration": "development" 80 | }, 81 | "test": { 82 | "builder": "@angular-devkit/build-angular:karma", 83 | "options": { 84 | "main": "lib/test.ts", 85 | "polyfills": "src/polyfills.ts", 86 | "tsConfig": "tsconfig.spec.json", 87 | "karmaConfig": "karma.conf.js" 88 | } 89 | }, 90 | "lint": { 91 | "builder": "@angular-eslint/builder:lint", 92 | "options": { 93 | "lintFilePatterns": [ 94 | "src/**/*.ts", 95 | "src/**/*.html", 96 | "lib/**/*.ts", 97 | "lib/**/*.html" 98 | ] 99 | } 100 | } 101 | } 102 | } 103 | }, 104 | "defaultProject": "angular-qq-maps", 105 | "cli": { 106 | "defaultCollection": "@angular-eslint/schematics" 107 | } 108 | } 109 | -------------------------------------------------------------------------------- /karma.conf.js: -------------------------------------------------------------------------------- 1 | // Karma configuration file, see link for more information 2 | // https://karma-runner.github.io/1.0/config/configuration-file.html 3 | 4 | module.exports = function (config) { 5 | config.set({ 6 | basePath: '', 7 | frameworks: ['jasmine', '@angular-devkit/build-angular'], 8 | plugins: [ 9 | require('karma-jasmine'), 10 | require('karma-chrome-launcher'), 11 | require('karma-jasmine-html-reporter'), 12 | require('karma-coverage'), 13 | require('@angular-devkit/build-angular/plugins/karma') 14 | ], 15 | client: { 16 | jasmine: { 17 | // you can add configuration options for Jasmine here 18 | // the possible options are listed at https://jasmine.github.io/api/edge/Configuration.html 19 | // for example, you can disable the random execution with `random: false` 20 | // or set a specific seed with `seed: 4321` 21 | }, 22 | clearContext: false // leave Jasmine Spec Runner output visible in browser 23 | }, 24 | jasmineHtmlReporter: { 25 | suppressAll: true // removes the duplicated traces 26 | }, 27 | coverageReporter: { 28 | dir: require('path').join(__dirname, './coverage'), 29 | subdir: '.', 30 | reporters: [ 31 | { type: 'html' }, 32 | { type: 'text-summary' } 33 | ] 34 | }, 35 | reporters: ['progress', 'kjhtml'], 36 | port: 9876, 37 | colors: true, 38 | logLevel: config.LOG_INFO, 39 | autoWatch: true, 40 | browsers: ['Chrome'], 41 | singleRun: false, 42 | restartOnFileChange: true, 43 | customLaunchers: { 44 | ChromeHeadlessCI: { 45 | base: 'ChromeHeadless', 46 | flags: ['--no-sandbox'], 47 | }, 48 | } 49 | }); 50 | }; 51 | -------------------------------------------------------------------------------- /lib/index.ts: -------------------------------------------------------------------------------- 1 | export * from './public_api'; 2 | -------------------------------------------------------------------------------- /lib/ng-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "../node_modules/ng-packagr/ng-package.schema.json", 3 | "dest": "../publish", 4 | "deleteDestPath": true, 5 | "lib": { 6 | "entryFile": "public_api.ts" 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /lib/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "angular-qq-maps", 3 | "version": "12.0.0", 4 | "description": "Angular QQ Maps Components", 5 | "keywords": [ 6 | "angular-qq-maps", 7 | "ng2-qq-maps", 8 | "qq maps" 9 | ], 10 | "author": "cipchk ", 11 | "license": "MIT", 12 | "repository": { 13 | "type": "git", 14 | "url": "git+https://github.com/cipchk/angular-qq-maps.git" 15 | }, 16 | "bugs": { 17 | "url": "https://github.com/cipchk/angular-qq-maps/issues" 18 | }, 19 | "homepage": "https://cipchk.github.io/angular-qq-maps/" 20 | } 21 | -------------------------------------------------------------------------------- /lib/public_api.ts: -------------------------------------------------------------------------------- 1 | export * from './src/aqm.config'; 2 | export * from './src/aqm.component'; 3 | export * from './src/aqm-panorama.component'; 4 | export * from './src/aqm.module'; 5 | -------------------------------------------------------------------------------- /lib/spec/loader.service.spec.ts: -------------------------------------------------------------------------------- 1 | import { Component } from '@angular/core'; 2 | import { inject, TestBed, ComponentFixtureAutoDetect, ComponentFixture } from '@angular/core/testing'; 3 | 4 | import { LoaderService } from '../src/loader.service'; 5 | import { AqmModule } from '../src/aqm.module'; 6 | 7 | describe('Service: LoaderService', () => { 8 | let fixture: ComponentFixture; 9 | let el: HTMLElement; 10 | let htmlEl: HTMLElement; 11 | 12 | beforeEach(() => { 13 | TestBed.configureTestingModule({ 14 | declarations: [EmptyTestComponent], 15 | imports: [AqmModule.forRoot({ apiKey: '' })], 16 | providers: [LoaderService, { provide: ComponentFixtureAutoDetect, useValue: true }], 17 | }); 18 | 19 | fixture = TestBed.createComponent(EmptyTestComponent); 20 | el = fixture.nativeElement; 21 | fixture.detectChanges(); 22 | htmlEl = findParent(el, 'html'); 23 | }); 24 | 25 | it('should create the default script URL', inject([LoaderService], (loader: LoaderService) => { 26 | loader.load(); 27 | let script: HTMLScriptElement | null = null; 28 | const ls = htmlEl.querySelectorAll('script'); 29 | for (let i = 0; i < ls.length; i++) { 30 | const node = ls[i]; 31 | // tslint:disable-next-line:no-bitwise 32 | if (~node.src.indexOf('map.qq.com/api/js')) script = node; 33 | } 34 | 35 | expect(script).not.toBeNull(); 36 | expect(script!.type).toEqual('text/javascript'); 37 | expect(script!.async).toEqual(true); 38 | expect(script!.defer).toEqual(true); 39 | expect(script!.src).toBeDefined(); 40 | })); 41 | }); 42 | 43 | function findParent(el: any, selector: string): any { 44 | let retEl = null; 45 | while (el) { 46 | if (el.matches(selector)) { 47 | retEl = el; 48 | break; 49 | } 50 | el = el.parentElement; 51 | } 52 | return retEl; 53 | } 54 | 55 | @Component({ template: '' }) 56 | class EmptyTestComponent {} 57 | -------------------------------------------------------------------------------- /lib/src/aqm-panorama.component.ts: -------------------------------------------------------------------------------- 1 | import { 2 | Component, 3 | Input, 4 | ElementRef, 5 | EventEmitter, 6 | Output, 7 | NgZone, 8 | OnChanges, 9 | SimpleChanges, 10 | ViewEncapsulation, 11 | OnInit, 12 | } from '@angular/core'; 13 | import { LoaderService } from './loader.service'; 14 | import { AqmConfig } from './aqm.config'; 15 | 16 | declare const qq: any; 17 | 18 | @Component({ 19 | selector: 'aqm-panorama', 20 | template: ``, 21 | styles: [ 22 | ` 23 | aqm-panorama { 24 | display: block; 25 | width: 100%; 26 | height: 100%; 27 | } 28 | `, 29 | ], 30 | encapsulation: ViewEncapsulation.None, 31 | }) 32 | export class AqmPanoramaComponent implements OnInit, OnChanges { 33 | @Input() options: any = {}; 34 | @Output() ready = new EventEmitter(); 35 | 36 | private map: any = null; 37 | 38 | constructor( 39 | private el: ElementRef, 40 | private COG: AqmConfig, 41 | private loader: LoaderService, 42 | private zone: NgZone, 43 | ) {} 44 | 45 | ngOnInit(): void { 46 | this._initMap(); 47 | } 48 | 49 | ngOnChanges(changes: SimpleChanges): void { 50 | if ('options' in changes) { 51 | this._updateOptions(); 52 | } 53 | } 54 | 55 | private _initMap(): void { 56 | if (this.map) { 57 | return; 58 | } 59 | this.loader 60 | .load() 61 | .then(() => { 62 | this.zone.runOutsideAngular(() => { 63 | try { 64 | this.map = new qq.maps.Panorama( 65 | this.el.nativeElement, 66 | this.options, 67 | ); 68 | } catch (ex) { 69 | console.warn('街景初始化失败', ex); 70 | } 71 | }); 72 | this.ready.emit(this.map); 73 | }) 74 | .catch((error: Error) => { 75 | console.warn('js加载失败', error); 76 | }); 77 | } 78 | 79 | private _updateOptions(): void { 80 | this.options = { ...this.COG.panoramaOptions, ...this.options }; 81 | if (this.map) { 82 | this.map.setOptions(this.options); 83 | } 84 | } 85 | } 86 | -------------------------------------------------------------------------------- /lib/src/aqm.component.ts: -------------------------------------------------------------------------------- 1 | import { 2 | Component, 3 | Input, 4 | ElementRef, 5 | EventEmitter, 6 | Output, 7 | NgZone, 8 | OnChanges, 9 | SimpleChanges, 10 | ViewEncapsulation, 11 | OnInit, 12 | OnDestroy, 13 | } from '@angular/core'; 14 | import { LoaderService } from './loader.service'; 15 | import { AqmConfig } from './aqm.config'; 16 | import { isSSR } from './aqm.core'; 17 | 18 | declare const qq: any; 19 | declare const TMap: any; 20 | 21 | @Component({ 22 | selector: 'aqm-map', 23 | template: ``, 24 | styles: [ 25 | ` 26 | aqm-map { 27 | display: block; 28 | width: 100%; 29 | height: 100%; 30 | } 31 | `, 32 | ], 33 | exportAs: 'aqmMap', 34 | encapsulation: ViewEncapsulation.None, 35 | }) 36 | export class AqmComponent implements OnInit, OnChanges, OnDestroy { 37 | @Input() config!: AqmConfig; 38 | @Input() options: any = {}; 39 | @Output() ready = new EventEmitter(); 40 | 41 | private map: any = null; 42 | 43 | constructor(private el: ElementRef, private COG: AqmConfig, private loader: LoaderService, private zone: NgZone) {} 44 | 45 | ngOnInit(): void { 46 | if (isSSR) { 47 | return; 48 | } 49 | this._initMap(); 50 | } 51 | 52 | ngOnChanges(changes: SimpleChanges): void { 53 | if ('config' in changes) { 54 | this.loader.cog = this.config; 55 | } 56 | if ('options' in changes) { 57 | this._updateOptions(); 58 | } 59 | } 60 | 61 | private _initMap(): void { 62 | if (this.map) { 63 | return; 64 | } 65 | this.loader 66 | .load() 67 | .then(() => { 68 | this.zone.runOutsideAngular(() => { 69 | try { 70 | console.log(this.options); 71 | this.map = new (this.loader.cog.gl === true ? TMap : qq.maps).Map(this.el.nativeElement, this.options); 72 | } catch (ex) { 73 | console.warn('地图初始化失败', ex); 74 | } 75 | }); 76 | this.ready.emit(this.map); 77 | }) 78 | .catch((error: Error) => { 79 | console.warn('js加载失败', error); 80 | }); 81 | } 82 | 83 | private _updateOptions(): void { 84 | this.options = { ...this.COG.mapOptions, ...this.options }; 85 | if (this.map && this.map.setOptions) { 86 | this.map.setOptions(this.options); 87 | } 88 | } 89 | 90 | ngOnDestroy(): void { 91 | if (this.map && this.map.destroy) { 92 | this.map.destroy(); 93 | } 94 | } 95 | } 96 | -------------------------------------------------------------------------------- /lib/src/aqm.config.ts: -------------------------------------------------------------------------------- 1 | export class AqmConfig { 2 | /** 3 | * 表示使用 [JavaScript API GL](https://lbs.qq.com/webApi/javascriptGL/glGuide/glOverview) 版本 4 | */ 5 | gl?: boolean; 6 | 7 | /** 8 | * APP KEY 必填项 9 | */ 10 | apiKey?: string; 11 | 12 | /** 13 | * 默认:map.qq.com/api/js 14 | */ 15 | apiHostAndPath?: string; 16 | 17 | /** 18 | * API异步加载回调函数名 19 | */ 20 | apiCallback?: string; 21 | 22 | /** 23 | * API版本号,默认:2.exp 24 | */ 25 | apiVersion?: string; 26 | 27 | /** 28 | * 加载附加库 29 | */ 30 | apiLibraries?: string[]; 31 | 32 | /** 33 | * API 请求协议 34 | */ 35 | apiProtocol?: 'http' | 'https' | 'auto'; 36 | 37 | /** 38 | * 默认地图配置项,等同于[MapOptions 对象规范](http://lbs.qq.com/javascript_v2/doc/mapoptions.html),当指定 `gl: true` 表示Gl版本的[MapOptions 对象规范](https://lbs.qq.com/javascript_gl/doc/mapoptions.html) 39 | */ 40 | mapOptions?: any; 41 | 42 | /** 43 | * 默认街景配置项,等同于[PanoramaOptions 对象规范](http://lbs.qq.com/javascript_v2/doc/panoramaoptions.html) 44 | */ 45 | panoramaOptions?: any; 46 | } 47 | -------------------------------------------------------------------------------- /lib/src/aqm.core.ts: -------------------------------------------------------------------------------- 1 | export const isSSR = !(typeof document === 'object' && !!document); 2 | -------------------------------------------------------------------------------- /lib/src/aqm.module.ts: -------------------------------------------------------------------------------- 1 | import { CommonModule } from '@angular/common'; 2 | import { NgModule, ModuleWithProviders } from '@angular/core'; 3 | import { AqmComponent } from './aqm.component'; 4 | import { AqmPanoramaComponent } from './aqm-panorama.component'; 5 | import { AqmConfig } from './aqm.config'; 6 | import { LoaderService } from './loader.service'; 7 | 8 | @NgModule({ 9 | imports: [CommonModule], 10 | providers: [LoaderService], 11 | declarations: [AqmComponent, AqmPanoramaComponent], 12 | exports: [AqmComponent, AqmPanoramaComponent], 13 | }) 14 | export class AqmModule { 15 | static forRoot(config: AqmConfig): ModuleWithProviders { 16 | return { 17 | ngModule: AqmModule, 18 | providers: [{ provide: AqmConfig, useValue: config }], 19 | }; 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /lib/src/loader.service.ts: -------------------------------------------------------------------------------- 1 | import { Injectable } from '@angular/core'; 2 | import { AqmConfig } from './aqm.config'; 3 | 4 | declare const document: any; 5 | 6 | @Injectable() 7 | export class LoaderService { 8 | private _scriptLoadingPromise: Promise | null = null; 9 | private _cog!: AqmConfig; 10 | 11 | set cog(val: AqmConfig) { 12 | const _cog = (this._cog = { 13 | gl: false, 14 | apiProtocol: 'auto', 15 | apiVersion: '2.exp', 16 | apiCallback: 'angularQQMapsLoader', 17 | ...val, 18 | }); 19 | if (!_cog.apiHostAndPath) { 20 | this._scriptLoadingPromise = null; 21 | _cog.apiHostAndPath = _cog.gl ? 'map.qq.com/api/gljs' : 'map.qq.com/api/js'; 22 | } 23 | } 24 | get cog(): AqmConfig { 25 | return this._cog; 26 | } 27 | 28 | constructor(cog: AqmConfig) { 29 | this.cog = cog; 30 | } 31 | 32 | load(): Promise { 33 | if (this._scriptLoadingPromise) { 34 | return this._scriptLoadingPromise; 35 | } 36 | 37 | const script = document.createElement('script'); 38 | script.type = 'text/javascript'; 39 | script.async = true; 40 | script.defer = true; 41 | script.src = this._getSrc(); 42 | 43 | this._scriptLoadingPromise = new Promise((resolve: () => void, reject: (error: Event) => void) => { 44 | (window as any)[this._cog.apiCallback!] = () => { 45 | resolve(); 46 | }; 47 | 48 | script.onerror = (error: Event) => { 49 | reject(error); 50 | }; 51 | }); 52 | 53 | document.body.appendChild(script); 54 | return this._scriptLoadingPromise; 55 | } 56 | 57 | private _getSrc(): string { 58 | let protocol: string; 59 | switch (this._cog.apiProtocol) { 60 | case 'http': 61 | protocol = 'http:'; 62 | break; 63 | case 'https': 64 | protocol = 'https:'; 65 | break; 66 | default: 67 | protocol = ''; 68 | break; 69 | } 70 | const queryParams: { [key: string]: string | string[] | undefined } = { 71 | v: this._cog.apiVersion, 72 | key: this._cog.apiKey, 73 | libraries: this._cog.apiLibraries, 74 | callback: this._cog.apiCallback, 75 | }; 76 | const params: string = Object.keys(queryParams) 77 | .filter((k: string) => queryParams[k] != null) 78 | .filter((k: string) => { 79 | return !Array.isArray(queryParams[k]) || (Array.isArray(queryParams[k]) && queryParams[k]!.length > 0); 80 | }) 81 | .map((k: string) => { 82 | const i = queryParams[k]; 83 | if (Array.isArray(i)) { 84 | return { key: k, value: i.join(',') }; 85 | } 86 | return { key: k, value: i }; 87 | }) 88 | .map((entry: { key: string; value: string | undefined }) => { 89 | return `${entry.key}=${entry.value}`; 90 | }) 91 | .join('&'); 92 | return `${protocol}//${this._cog.apiHostAndPath}?${params}`; 93 | } 94 | } 95 | -------------------------------------------------------------------------------- /lib/test.ts: -------------------------------------------------------------------------------- 1 | // This file is required by karma.conf.js and loads recursively all the .spec and framework files 2 | 3 | import 'zone.js/testing'; 4 | import { getTestBed } from '@angular/core/testing'; 5 | import { BrowserDynamicTestingModule, platformBrowserDynamicTesting } from '@angular/platform-browser-dynamic/testing'; 6 | 7 | declare const require: { 8 | context( 9 | path: string, 10 | deep?: boolean, 11 | filter?: RegExp, 12 | ): { 13 | keys(): string[]; 14 | (id: string): T; 15 | }; 16 | }; 17 | 18 | // First, initialize the Angular testing environment. 19 | getTestBed().initTestEnvironment(BrowserDynamicTestingModule, platformBrowserDynamicTesting()); 20 | // Then we find all the tests. 21 | const context = require.context('./', true, /\.spec\.ts$/); 22 | // And load the modules. 23 | context.keys().map(context); 24 | -------------------------------------------------------------------------------- /lib/tsconfig.lib.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../tsconfig.json", 3 | "compilerOptions": { 4 | "alwaysStrict": true, 5 | "sourceMap": true, 6 | "inlineSources": true, 7 | "declaration": true, 8 | "strictFunctionTypes": true, 9 | "stripInternal": true 10 | }, 11 | "files": ["./src/aqm.module.ts"], 12 | "include": [ 13 | "**/*.ts" 14 | ], 15 | "angularCompilerOptions": { 16 | "enableIvy": true, 17 | "compilationMode": "partial" 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "angular-qq-maps", 3 | "version": "12.0.0", 4 | "description": "Angular QQ Maps Components", 5 | "keywords": [ 6 | "angular-qq-maps", 7 | "ng2-qq-maps", 8 | "qq maps" 9 | ], 10 | "author": "cipchk ", 11 | "license": "MIT", 12 | "repository": { 13 | "type": "git", 14 | "url": "git+https://github.com/cipchk/angular-qq-maps.git" 15 | }, 16 | "bugs": { 17 | "url": "https://github.com/cipchk/angular-qq-maps/issues" 18 | }, 19 | "homepage": "https://cipchk.github.io/angular-qq-maps/", 20 | "scripts": { 21 | "analyze": "ng b --stats-json --source-map", 22 | "lint": "ng l", 23 | "test": "ng t --no-progress --browsers=ChromeHeadlessCI --code-coverage --no-watch", 24 | "build": "node scripts/build.js", 25 | "release:next": "npm run build && cd publish && npm publish --access public --tag next", 26 | "release": "npm run build && cd publish && npm publish --access public" 27 | }, 28 | "dependencies": { 29 | "@angular/animations": "~12.0.2", 30 | "@angular/common": "~12.0.2", 31 | "@angular/compiler": "~12.0.2", 32 | "@angular/core": "~12.0.2", 33 | "@angular/forms": "~12.0.2", 34 | "@angular/platform-browser": "~12.0.2", 35 | "@angular/platform-browser-dynamic": "~12.0.2", 36 | "@angular/router": "~12.0.2", 37 | "rxjs": "~6.6.0", 38 | "tslib": "^2.1.0", 39 | "zone.js": "~0.11.4", 40 | "bootstrap": "^5.0.1", 41 | "ngx-highlight-js": "^12.0.0" 42 | }, 43 | "devDependencies": { 44 | "@angular-devkit/build-angular": "~12.0.2", 45 | "@angular/cli": "~12.0.2", 46 | "@angular/compiler-cli": "~12.0.2", 47 | "@types/jasmine": "~3.6.0", 48 | "@types/node": "^12.11.1", 49 | "jasmine-core": "~3.7.0", 50 | "karma": "~6.3.0", 51 | "karma-chrome-launcher": "~3.1.0", 52 | "karma-coverage": "~2.0.3", 53 | "karma-jasmine": "~4.0.0", 54 | "karma-jasmine-html-reporter": "^1.5.0", 55 | "typescript": "~4.2.3", 56 | "@angular-eslint/builder": "12.0.0", 57 | "@angular-eslint/eslint-plugin": "12.0.0", 58 | "@angular-eslint/eslint-plugin-template": "12.0.0", 59 | "@angular-eslint/schematics": "12.0.0", 60 | "@angular-eslint/template-parser": "12.0.0", 61 | "@typescript-eslint/eslint-plugin": "4.23.0", 62 | "@typescript-eslint/parser": "4.23.0", 63 | "codecov": "^3.8.1", 64 | "eslint": "^7.26.0", 65 | "ng-packagr": "^12.0.2" 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /scripts/build.js: -------------------------------------------------------------------------------- 1 | const path = require('path'); 2 | const fs = require('fs-extra'); 3 | const ngPackage = require('ng-packagr'); 4 | 5 | const root = path.resolve(__dirname, `..`); 6 | const libPackagePath = path.resolve(root, `./lib/package.json`); 7 | 8 | // Update version 9 | const rootPackageJson = require(path.resolve(root, `./package.json`)); 10 | const libPackageJson = require(libPackagePath); 11 | [ 12 | 'name', 13 | 'version', 14 | 'description', 15 | 'keywords', 16 | 'author', 17 | 'license', 18 | 'repository', 19 | 'bugs', 20 | 'homepage', 21 | ].forEach((key) => (libPackageJson[key] = rootPackageJson[key])); 22 | fs.writeJsonSync(libPackagePath, libPackageJson, { spaces: 2 }); 23 | 24 | ngPackage 25 | .ngPackagr() 26 | .forProject(path.resolve(root, `./lib/ng-package.json`)) 27 | .withTsConfig(path.resolve(root, './lib/tsconfig.lib.json')) 28 | .build() 29 | .then(() => 30 | fs.copyFileSync( 31 | path.resolve(root, `./README.md`), 32 | path.resolve(root, `./publish/README.md`), 33 | ), 34 | ) 35 | .catch((error) => { 36 | console.error(error); 37 | process.exit(1); 38 | }); 39 | -------------------------------------------------------------------------------- /src/app/app.component.ts: -------------------------------------------------------------------------------- 1 | import { Component, ViewEncapsulation } from '@angular/core'; 2 | 3 | @Component({ 4 | selector: 'app-root', 5 | template: ` 6 | 33 |

34 | QQ Maps Components for Angular,有关更多细节见README.md 39 |

40 | 41 | `, 42 | encapsulation: ViewEncapsulation.None, 43 | }) 44 | export class AppComponent {} 45 | -------------------------------------------------------------------------------- /src/app/app.module.ts: -------------------------------------------------------------------------------- 1 | import { NgModule } from '@angular/core'; 2 | import { RouterModule } from '@angular/router'; 3 | import { BrowserModule } from '@angular/platform-browser'; 4 | import { CommonModule } from '@angular/common'; 5 | import { HighlightJsModule } from 'ngx-highlight-js'; 6 | 7 | import { AqmModule } from 'angular-qq-maps'; 8 | 9 | import { AppComponent } from './app.component'; 10 | import { DemoComponent } from './components/demo.component'; 11 | import { DemoPanoramaComponent } from './components/panorama.component'; 12 | import { DemoGlJsComponent } from './components/gljs.component'; 13 | 14 | @NgModule({ 15 | imports: [ 16 | BrowserModule, 17 | RouterModule.forRoot( 18 | [ 19 | { path: '', component: DemoComponent }, 20 | { path: 'panorama', component: DemoPanoramaComponent }, 21 | { path: 'gljs', component: DemoGlJsComponent }, 22 | ], 23 | { useHash: true }, 24 | ), 25 | CommonModule, 26 | HighlightJsModule, 27 | 28 | AqmModule.forRoot({ 29 | apiKey: 'I3TBZ-QTN3J-MWPFI-FERMS-IBOCQ-LBBWY', 30 | }), 31 | ], 32 | declarations: [ 33 | AppComponent, 34 | DemoComponent, 35 | DemoPanoramaComponent, 36 | DemoGlJsComponent, 37 | ], 38 | providers: [], 39 | bootstrap: [AppComponent], 40 | }) 41 | export class AppDemoModule {} 42 | -------------------------------------------------------------------------------- /src/app/components/demo.component.html: -------------------------------------------------------------------------------- 1 |
2 |
示例
3 |
4 | 7 | 13 |

{{ status }}

14 |
操作
15 |
16 | 19 | 22 |
23 |
24 | 31 |
32 |
33 |
34 |
35 |
卫星地图
36 |
37 | 42 |
43 |
44 | -------------------------------------------------------------------------------- /src/app/components/demo.component.scss: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cipchk/angular-qq-maps/31511c003e668d1aa339d4827aa1d292cefba4d5/src/app/components/demo.component.scss -------------------------------------------------------------------------------- /src/app/components/demo.component.ts: -------------------------------------------------------------------------------- 1 | import { NgZone, OnDestroy, Component, ViewEncapsulation, ViewChild, ElementRef } from '@angular/core'; 2 | import { AqmComponent } from 'angular-qq-maps'; 3 | 4 | declare const qq: any; 5 | 6 | @Component({ 7 | selector: 'demo', 8 | templateUrl: './demo.component.html', 9 | styleUrls: ['./demo.component.scss'], 10 | encapsulation: ViewEncapsulation.None, 11 | }) 12 | export class DemoComponent implements OnDestroy { 13 | constructor(private el: ElementRef, private zone: NgZone) {} 14 | options: any = {}; 15 | status = ''; 16 | @ViewChild('map') mapComp!: AqmComponent; 17 | 18 | private map: any; 19 | 20 | // 卫星 21 | satelliteOptions: any; 22 | private mapSatellite: any; 23 | onReady(mapNative: any): void { 24 | mapNative.setOptions({ 25 | zoom: 12, 26 | center: new qq.maps.LatLng(39.916527, 116.397128), 27 | }); 28 | this.map = mapNative; 29 | this.status = '加载完成'; 30 | // 添加监听事件 31 | qq.maps.event.addListener(this.map, 'click', (event: any) => { 32 | // tslint:disable-next-line:no-unused-expression 33 | new qq.maps.Marker({ 34 | position: event.latLng, 35 | map: this.map, 36 | }); 37 | this.zone.run(() => { 38 | this.status = `click ${+new Date()}`; 39 | }); 40 | }); 41 | } 42 | 43 | panTo(): void { 44 | this.map.panTo(new qq.maps.LatLng(39.9, 116.4)); 45 | } 46 | 47 | zoom(): void { 48 | this.map.zoomTo((this.map.getZoom() + 1) % 17); 49 | } 50 | 51 | infoWindow(): void { 52 | const infoWin = new qq.maps.InfoWindow({ 53 | map: this.map, 54 | }); 55 | infoWin.open(); 56 | infoWin.setContent('Hello world'); 57 | infoWin.setPosition(this.map.getCenter()); 58 | } 59 | onReadySatellite(mapNative: any): void { 60 | mapNative.setOptions({ 61 | zoom: 14, 62 | center: new qq.maps.LatLng(39.916527, 116.397128), 63 | mapTypeId: qq.maps.MapTypeId.SATELLITE, 64 | }); 65 | this.mapSatellite = mapNative; 66 | } 67 | 68 | ngOnDestroy(): void { 69 | ['click'].forEach((eventName) => { 70 | qq.maps.event.clearListeners(this.map, eventName); 71 | }); 72 | } 73 | } 74 | -------------------------------------------------------------------------------- /src/app/components/gljs.component.html: -------------------------------------------------------------------------------- 1 |
2 |
示例(本示例可能会受一Angular项目内同时使用 GL 或传统的影响可能在切换过程中导致加载失败时,请直接刷新即可)
3 |
4 | 5 | 12 |
操作
13 |
14 | 15 | 16 | 17 |
18 |
19 |
20 | -------------------------------------------------------------------------------- /src/app/components/gljs.component.ts: -------------------------------------------------------------------------------- 1 | import { Component, ViewEncapsulation } from '@angular/core'; 2 | 3 | declare const TMap: any; 4 | 5 | @Component({ 6 | selector: 'demo-gljs', 7 | templateUrl: './gljs.component.html', 8 | encapsulation: ViewEncapsulation.None, 9 | }) 10 | export class DemoGlJsComponent { 11 | private map: any; 12 | options: any = {}; 13 | 14 | onReady(mapNative: any): void { 15 | this.map = mapNative; 16 | } 17 | 18 | change2D(): void { 19 | if (this.map) { 20 | this.map.setViewMode('2D'); 21 | } 22 | } 23 | 24 | change3D(): void { 25 | if (this.map) { 26 | this.map.setViewMode('3D'); 27 | this.map.setPitch(70); 28 | this.map.setZoom(17); 29 | } 30 | } 31 | 32 | updateStyle(): void { 33 | this.options = null; 34 | // TODO: 强制重新渲染组件 35 | setTimeout(() => { 36 | this.options = { 37 | center: new TMap.LatLng(39.916527, 116.397128), 38 | zoom: 11, 39 | mapStyleId: 'style2', 40 | }; 41 | }, 1000); 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /src/app/components/panorama.component.html: -------------------------------------------------------------------------------- 1 |
2 |
示例
3 |
4 | 8 | 13 |
14 |
15 | -------------------------------------------------------------------------------- /src/app/components/panorama.component.scss: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cipchk/angular-qq-maps/31511c003e668d1aa339d4827aa1d292cefba4d5/src/app/components/panorama.component.scss -------------------------------------------------------------------------------- /src/app/components/panorama.component.ts: -------------------------------------------------------------------------------- 1 | import { Component, ViewEncapsulation, ViewChild, ElementRef } from '@angular/core'; 2 | import { AqmPanoramaComponent } from 'angular-qq-maps'; 3 | 4 | declare const qq: any; 5 | 6 | @Component({ 7 | selector: 'panorama', 8 | templateUrl: './panorama.component.html', 9 | styleUrls: ['./panorama.component.scss'], 10 | encapsulation: ViewEncapsulation.None, 11 | }) 12 | export class DemoPanoramaComponent { 13 | options: any = { 14 | pano: '10011501120802180635300', 15 | pov: { 16 | heading: 1, 17 | pitch: 0, 18 | }, 19 | zoom: 1, 20 | }; 21 | @ViewChild('map') map!: AqmPanoramaComponent; 22 | 23 | constructor(private el: ElementRef) {} 24 | } 25 | -------------------------------------------------------------------------------- /src/assets/fork.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cipchk/angular-qq-maps/31511c003e668d1aa339d4827aa1d292cefba4d5/src/assets/fork.png -------------------------------------------------------------------------------- /src/environments/environment.prod.ts: -------------------------------------------------------------------------------- 1 | export const environment = { 2 | production: true 3 | }; 4 | -------------------------------------------------------------------------------- /src/environments/environment.ts: -------------------------------------------------------------------------------- 1 | // The file contents for the current environment will overwrite these during build. 2 | // The build system defaults to the dev environment which uses `environment.ts`, but if you do 3 | // `ng build --env=prod` then `environment.prod.ts` will be used instead. 4 | // The list of which env maps to which file can be found in `angular-cli.json`. 5 | 6 | export const environment = { 7 | production: false 8 | }; 9 | -------------------------------------------------------------------------------- /src/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | angular-qq-maps | QQ Maps Components for Angular 6 | 7 | 8 | 9 | 15 | 19 | 20 | 21 | 22 | 23 |
24 | Loading... 25 |
26 | 27 | 28 | Fork me on GitHub 33 | 34 | 35 | 36 | -------------------------------------------------------------------------------- /src/main.ts: -------------------------------------------------------------------------------- 1 | import { platformBrowserDynamic } from '@angular/platform-browser-dynamic'; 2 | import { enableProdMode } from '@angular/core'; 3 | import { environment } from './environments/environment'; 4 | import { AppDemoModule } from './app/app.module'; 5 | 6 | if (environment.production) { 7 | enableProdMode(); 8 | } 9 | 10 | platformBrowserDynamic() 11 | .bootstrapModule(AppDemoModule) 12 | .catch((err) => console.error(err)); 13 | -------------------------------------------------------------------------------- /src/polyfills.ts: -------------------------------------------------------------------------------- 1 | /** 2 | * This file includes polyfills needed by Angular and is loaded before the app. 3 | * You can add your own extra polyfills to this file. 4 | * 5 | * This file is divided into 2 sections: 6 | * 1. Browser polyfills. These are applied before loading ZoneJS and are sorted by browsers. 7 | * 2. Application imports. Files imported after ZoneJS that should be loaded before your main 8 | * file. 9 | * 10 | * The current setup is for so-called "evergreen" browsers; the last versions of browsers that 11 | * automatically update themselves. This includes Safari >= 10, Chrome >= 55 (including Opera), 12 | * Edge >= 13 on the desktop, and iOS 10 and Chrome on mobile. 13 | * 14 | * Learn more in https://angular.io/guide/browser-support 15 | */ 16 | 17 | /*************************************************************************************************** 18 | * BROWSER POLYFILLS 19 | */ 20 | 21 | /** IE10 and IE11 requires the following for NgClass support on SVG elements */ 22 | // import 'classlist.js'; // Run `npm install --save classlist.js`. 23 | 24 | /** 25 | * Web Animations `@angular/platform-browser/animations` 26 | * Only required if AnimationBuilder is used within the application and using IE/Edge or Safari. 27 | * Standard animation support in Angular DOES NOT require any polyfills (as of Angular 6.0). 28 | */ 29 | // import 'web-animations-js'; // Run `npm install --save web-animations-js`. 30 | 31 | /** 32 | * By default, zone.js will patch all possible macroTask and DomEvents 33 | * user can disable parts of macroTask/DomEvents patch by setting following flags 34 | * because those flags need to be set before `zone.js` being loaded, and webpack 35 | * will put import in the top of bundle, so user need to create a separate file 36 | * in this directory (for example: zone-flags.ts), and put the following flags 37 | * into that file, and then add the following code before importing zone.js. 38 | * import './zone-flags.ts'; 39 | * 40 | * The flags allowed in zone-flags.ts are listed here. 41 | * 42 | * The following flags will work for all browsers. 43 | * 44 | * (window as any).__Zone_disable_requestAnimationFrame = true; // disable patch requestAnimationFrame 45 | * (window as any).__Zone_disable_on_property = true; // disable patch onProperty such as onclick 46 | * (window as any).__zone_symbol__UNPATCHED_EVENTS = ['scroll', 'mousemove']; // disable patch specified eventNames 47 | * 48 | * in IE/Edge developer tools, the addEventListener will also be wrapped by zone.js 49 | * with the following flag, it will bypass `zone.js` patch for IE/Edge 50 | * 51 | * (window as any).__Zone_enable_cross_context_check = true; 52 | * 53 | */ 54 | 55 | /*************************************************************************************************** 56 | * Zone JS is required by default for Angular itself. 57 | */ 58 | import 'zone.js'; // Included with Angular CLI. 59 | 60 | /*************************************************************************************************** 61 | * APPLICATION IMPORTS 62 | */ 63 | -------------------------------------------------------------------------------- /tsconfig.app.json: -------------------------------------------------------------------------------- 1 | /* To learn more about this file see: https://angular.io/config/tsconfig. */ 2 | { 3 | "extends": "./tsconfig.json", 4 | "compilerOptions": { 5 | "outDir": "./out-tsc/app", 6 | "types": [] 7 | }, 8 | "files": ["src/main.ts", "src/polyfills.ts"], 9 | "include": ["src/**/*.d.ts"] 10 | } 11 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | /* To learn more about this file see: https://angular.io/config/tsconfig. */ 2 | { 3 | "compileOnSave": false, 4 | "compilerOptions": { 5 | "baseUrl": "./", 6 | "outDir": "./dist/out-tsc", 7 | "forceConsistentCasingInFileNames": true, 8 | "strict": true, 9 | "noImplicitReturns": true, 10 | "noFallthroughCasesInSwitch": true, 11 | "sourceMap": true, 12 | "declaration": false, 13 | "downlevelIteration": true, 14 | "experimentalDecorators": true, 15 | "moduleResolution": "node", 16 | "importHelpers": true, 17 | "target": "es2017", 18 | "module": "es2020", 19 | "lib": ["es2018", "dom"], 20 | "paths": { 21 | "angular-qq-maps": ["lib/index"] 22 | } 23 | }, 24 | "angularCompilerOptions": { 25 | "enableI18nLegacyMessageIdFormat": false, 26 | "strictInjectionParameters": true, 27 | "strictInputAccessModifiers": true, 28 | "strictTemplates": true 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /tsconfig.spec.json: -------------------------------------------------------------------------------- 1 | /* To learn more about this file see: https://angular.io/config/tsconfig. */ 2 | { 3 | "extends": "./tsconfig.json", 4 | "compilerOptions": { 5 | "outDir": "./out-tsc/spec", 6 | "types": ["jasmine"] 7 | }, 8 | "files": ["lib/test.ts", "src/polyfills.ts"], 9 | "include": ["lib/**/*.spec.ts", "lib/**/*.d.ts"] 10 | } 11 | --------------------------------------------------------------------------------