diff --git a/src/building.js b/src/building.js index fa0a80b..756d23b 100644 --- a/src/building.js +++ b/src/building.js @@ -214,7 +214,7 @@ class Building { // Filter to all ways var parts = this.fullXmlData.getElementsByTagName('way'); for (const xmlPart of parts) { - if (xmlPart.querySelector('[k="building:part"]')) { + if (xmlPart.querySelector('[k="building:part"]:not([v="no"])')) { const id = xmlPart.getAttribute('id'); const part = new BuildingPart(id, this.fullXmlData, this.nodelist, this.outerElement.options); if (this.partIsInside(part)) { @@ -225,7 +225,7 @@ class Building { // Filter all relations parts = this.fullXmlData.getElementsByTagName('relation'); for (let i = 0; i < parts.length; i++) { - if (parts[i].querySelector('[k="building:part"]')) { + if (parts[i].querySelector('[k="building:part"]:not([v="no"])')) { const id = parts[i].getAttribute('id'); try { this.parts.push(new MultiBuildingPart(id, this.fullXmlData, this.nodelist, this.outerElement.options)); diff --git a/src/buildingpart.js b/src/buildingpart.js index 25d4838..eecb463 100644 --- a/src/buildingpart.js +++ b/src/buildingpart.js @@ -337,8 +337,8 @@ class BuildingPart { } else if (this.way.querySelector('[k="building:levels"]') !== null) { // if not, use building:levels and 3 meters per level. height = 3 * this.way.querySelector('[k="building:levels"]').getAttribute('v') + this.options.roof.height; - } else if (this.way.querySelector('[k="building:part"]') !== null) { - if (this.way.querySelector('[k="building:part"]').getAttribute('v') === 'roof') { + } else if (this.way.querySelector('[k="building:part"]:not([v="no"])') !== null) { + if (this.way.querySelector('[k="building:part"]:not([v="no"])').getAttribute('v') === 'roof') { // a roof has no building part by default. height = this.options.roof.height; } diff --git a/test/building.test.js b/test/building.test.js index c14e08f..4b66b1a 100644 --- a/test/building.test.js +++ b/test/building.test.js @@ -487,6 +487,64 @@ test('Part must be within outline', () => { expect(new Building('11', data).parts.length).toBe(0); }); +test('Outline with building:part=no is not added to parts', () => { + const data = ` + + + + + + + + + + + + + + + + + + + + +`; + const building = new Building('11', data); + expect(building.parts.map((part) => part.id)).toStrictEqual(['22']); +}); + +test('Outline with building:part=no is not added to parts (multipolygon)', () => { + const data = ` + + + + + + + + + + + + + + + + + + + + + + + + +`; + const building = new Building('42', data); + expect(building.parts.map((part) => part.id)).toStrictEqual(['22']); +}); + window.printError = printError; var errors = [];