Sencha Touch and Leaflet.js API - sencha-touch

I would like to use Leaflet.js API with Sencha Touch 2.3.1 and leaflet.js gives this error:
Uncaught Error: Map container not found.
These links are included in index.html
<link rel="stylesheet" href="http://cdn.leafletjs.com/leaflet-0.7.2/leaflet.css" />
<script src="http://cdn.leafletjs.com/leaflet-0.7.2/leaflet.js"></script>
Here is my mainview code:
Ext.define('App.view.Main', {
extend: 'Ext.Container',
xtype: 'main',
requires: [
'App.view.MapView',
],
config: {
layout: 'card',
items: [
{
itemId: 'mapview',
xtype: 'mapview',
id : 'map'
}
]
}
});
This is the 'App.view.MapView' code:
Ext.define("App.view.MapView", {
extend: 'Ext.Container',
requires: ['Ext.device.Geolocation'],
xtype: 'mapview',
initialize: function(){
var map = L.map('map').setView([47.36865, 8.539183], 13);
var layer = L.tileLayer('http://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png').addTo(map);
map.on('click', function() {
console.log('Click-Event on map / Time: ' + Date.now());
});
},
});
What am I doing wrong? Please help.

Leaflet is searching for a DOM element, map, that isn't there (yet...).
This problem occurs when L.map('map') is called before the DOM has finished loading.

Guessing the js was executed before the DOM was ready. Try wrapping your code in a function and setting window.onload equal to your function.

Ok, seems I found a solution. I changed this line:
var map = L.map('map').setView([47.36865, 8.539183], 13);
to
var map = L.map(this.element.dom).setView([47.36865, 8.539183], 13);

Related

Nuxt: Page crashing on page reload

Anyone know why a sub page crashes when user reloads the page? It is fine when you navigate to the page using nuxt-link from another page (using route params), but when the user reloads/refreshes the page, it will crash.
Here is my sandbox where you can test it out: Codesandbox
Code from nuxt link:
<nuxt-link :to="{name: 'photos-id-title', params: { id: photo.id, title: photo.title }}">
Code from photo details page:
<template>
<section>
<!-- <template v-if="photo"> -->
<img
:id="photo.filename"
:src="photo.url"
class="img-fluid thumbnail rounded"
:alt="photo.title"
/>
<h1 class="h3">{{ photo.title }}</h1>
</section>
</template>
<script>
import { Annotorious } from '#recogito/annotorious'
export default {
data() {
return {
photo: {},
anno: {},
title: this.$route.params.title
}
},
async mounted() {
await this.getPhotoDoc()
this.anno = await new Annotorious({ image: this.photo.filename })
},
methods: {
async getPhotoDoc() {
const docRef = await this.$fireStore
.collection('photos')
.doc(this.$route.params.id)
.get()
try {
if (docRef.exists) {
// data() returns all data about the doc
console.log('got the doc: ', docRef.data())
this.photo = docRef.data()
} else {
console.log('no docs exist')
}
} catch (error) {
console.log('Error getting document:', error)
}
}
},
head() {
return {
title: this.photo.title,
meta: [
{
hid: 'description',
name: 'description',
content: this.photo.description
}
]
}
}
}
</script>
User journey: Click PHOTOS from navbar, select any photo on the page. You shall see a "photo detail" page. Loads fine. Try to refresh the page -- it will crash.
Note: I also have this scaffolded in a regular/plain vue app using Vue-cli and have NO issues. Only seems to be a problem with Nuxt. Must be SSR related?
Thanks for any help...
If you think this is SSR related and the Annotorious plugin might cause the problem try this:
nuxt.config.js add the plugin with mode client
plugins: [
{ src: '~/plugins/client-only.js', mode: 'client' }, // only on client side
]
You can find more information in the nuxtjs docs here

Chart can't be populated from data component [vue-highcharts wrapper]

I'm starting with the Higcharts wrapper for vue. Currently I'm migrating the code of a stockchart that I was using outside vue without problems into the wrapper. Everything is going well except that I can't populate the chart from component data or computed variables. Only from hard-written array or from component props.
This is the code:
<template>
<highcharts
class="stock"
v-bind:constructor-type="'stockChart'"
v-bind:options="config"
v-bind:deepCopyOnUpdate="false"
></highcharts>
</template>
<script>
export default {
name: "stockChart",
props: {
options: {
type: Object,
required: true
}
},
data: function() {
return {
config: {
series: [{
name: this.options.title,
//data: [[1,3],[2,7],[3,9],[4,2],[5,0],[10,13]] //THIS WORKS!
//data: this.options.plotData //THIS ALSO WORKS!!
data: this.plotData //THIS DOESN'T...
}],
(...)
},
plotData: [[1,3],[2,7],[3,9],[4,2],[5,0],[10,13]]
}
},
computed: {
// THIS ALSO ISN'T WORKING... THAT IS HOW I WANT IT TO WORK
/*plotData: function(){
return this.options.xData.map((e,i) => [e, this.options.yData[i]]);
}*/
}
}
</script>
<style scoped>
.stock {
width: 70%;
margin: 0 auto
}
</style>
I don't understand anything. The three methods should be equivalent. Why I can load data from props but not from data or computed? I can't find any good documentation about the vue wrapper to understand why is this happening.
Thanks for your help,
H25E
The answer is very simple. The reason is that the Vue defines all component data only after returning a whole data object, so you should not use this keyword to refer other component data within data definition. In order to make it work correctly, you should keep the plotData within component's data, but move the config into the computed properties. Take a look on the code below:
props: {
options: {
type: Object,
required: true
}
},
data: function() {
return {
plotData: [[1,3],[2,7],[3,9],[4,2],[5,0],[10,13]]
}
},
computed: {
config: function() {
return {
series: [{
name: this.options.title,
data: this.plotData
}]
}
},
}

Stripe is not defined in Nuxt

I want to add stripe elements to my nuxt js page However, I got an error
Stripe is not defined
I have inserted the <script src="https://js.stripe.com/v3/"></script> on my nuxt.config.js
Here's the code
head: {
title: process.env.npm_package_name || "",
script: [{ src: "https://js.stripe.com/v3/" }],
link: [
{ rel: "icon", type: "image/x-icon", href: "/favicon.ico" },
]
},
My payment page
<template>
<div>
<div ref="card"></div>
<button v-on:click="purchase">Purchase</button>
</div>
</template>
<script>
let stripe = Stripe("Key"),
elements = stripe.elements(),
card = undefined;
export default {
mounted: function() {
card = elements.create("card");
card.mount(this.$refs.card);
},
methods: {
async purchase() {
let result = await stripe.createToken(card);
}
}
};
</script>
I followed this tutorial and still can't fix it
https://alligator.io/vuejs/stripe-elements-vue-integration/
You are including stripe for into scripts, so it will be loaded in browser. But nuxt is SSR. And the code in your script section will be also executed on server. And on server there no stripe, so it wont work. You need to execute all your code that create Stripe in mounted hook, which is only executed on client

App expands to full screen in Confluence

I'm trying to add a Rally app to Confluence via the SDK. I'm successful, however, the app expands to fill the whole page covering Confluence headers. How do I restrict the app from expanding full screen? I've added a class that limits the height and width of app, but it still expands to full screen covering the Confluence header.
Here's my code:
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Hierarchical Grid Example</title>
<script type="text/javascript"
src="https://rally1.rallydev.com/apps/2.0rc3/sdk.js">
</script>
<script type="text/javascript">
Ext.override('Rally.sdk.Bootstrapper', {
_launchAppInViewport: function (className, settings, timeboxScope) {
this._wireIoHeaderHandlers();
this.app = this._createApp(className, settings, timeboxScope);
this.app.render('rallyDiv');
}
});
Rally.onReady(function() {
Ext.define('Rally.example.HierarchicalGrid', {
extend: 'Rally.app.App',
componentCls: 'app',
items: [
{ xtype: 'container', itemId: 'rallyDiv'}
],
autoCreateViewPort:false,
launch: function() {
Ext.create('Rally.data.wsapi.TreeStoreBuilder').build({
context: {project: '/project/9400054800'},
models: ['userstory'],
autoLoad: true,
enableHierarchy: true
}).then({
success: this._onStoreBuilt,
scope: this
});
},
_onStoreBuilt: function(store) {
this.down('#rallyDiv').add({
xtype: 'rallytreegrid',
context: this.getContext(),
store: store,
columnCfgs: [
'Name',
'ScheduleState',
'Owner'
]
});
}
});
Rally.launchApp('Rally.example.HierarchicalGrid', {
name: 'Hierarchical Grid Example',
});
});
</script>
</head>
<body>
<div id="rallyDiv"></div>
</body>
</html>
Thanks!
Apps are designed to fill an entire window and use a Viewport object to do so- this is why it's filling the screen. Is it possible instead in confluence to just create an iframe of the appropriate size and link to your App-external.html served elsewhere?
Otherwise you should be able to add a small override at the top of your App.js to change the behavior of Rally.launchApp to do what you want:
Ext.override('Rally.sdk.Bootstrapper', {
_launchAppInViewport: function (className, settings, timeboxScope) {
this._wireIoHeaderHandlers();
this.app = this._createApp(className, settings, timeboxScope);
//this is the code that launches the app in the viewport
//Ext.create('Ext.Viewport', {
// layout: 'fit',
// items: [ this.app ]
//});
//instead, just render it to your target div
this.app.render('myElement');
}
});
This isn't ideal but should work for you. I'll submit a feature request to better support rendering apps in non-fullscreen environments.

Magnific-popup: how to get image url from <img src="...">?

Is it possible to force magnific-popup to get image url from 'src' attribute of img tag? This way there would be no need to wrap img with a tags.
I tried the code below, but it doesn't work. Returned error is 'undefined' url.
<script type="text/javascript">
$(document).ready(function(){
$('div.gallery').magnificPopup({delegate: 'img'.attr('src') , type: 'image', gallery:{enabled:true}
});
});
</script>
Anyways, is there any option to do with 'img' only, without 'a' tags?
Thanks!
<script type="text/javascript">
$(document).ready(function(){
$('div.gallery').magnificPopup({delegate: 'img' , type: 'image', gallery:{enabled:true},
callbacks: {
elementParse: function() { this.item.src = this.item.el.attr('src'); }
}
});
});
</script>
elementParse http://dimsemenov.com/plugins/magnific-popup/documentation.html#api
I actually have not worked, and I found how to do .
Now the script when clicking pictures increases and creates a gallery of them .
<script type="text/javascript">
$(document).ready(function() {
$('#text').magnificPopup({
delegate: 'img',
type: 'image',
gallery: {
enabled: true
},
callbacks: {
elementParse: function(qw) {
qw.src = qw.el.attr('src');
}
}
});
});
</script>
With magnificPopup 1.1.0
now you have to do like this if you want it to work.
$(document).ready(function() {
$('.myClass').magnificPopup({
type: 'image',
callbacks: {
elementParse: function(item) {
item.src = item.el.attr('src');
}
}
});
});
The accepted answer didn't work for me, either. I ended up using the data-mfp-src attribute, which overrides the value in the href one (as mentioned here: http://dimsemenov.com/plugins/magnific-popup/documentation.html#content-types).
Instead of adding the attribute manually (duplicating the src of the image), I just copied the src value in data-mfp-src attributes for all images before the magnificPopup call. Something like this:
var popupImages = $('div.withPopups img');
popupImages.each(function(){
$(this).attr('data-mfp-src', $(this).attr('src'));
});
popupImages.magnificPopup({type: 'image'});