2017-01-16 2 views
0

Я использую @media print { для настройки моего вида печати. Проблема с моими диаграммами заключается в том, что размер их печати зависит от размера окна браузера. Поэтому, когда мой браузер большой, холст будет слишком большим для страницы (я использую отзывчивые диаграммы)Изменить размер chart.js холст для печати

Я попытался переопределить размер холста внутри @media print { без успеха.

Каковы решения для получения согласованного размера диаграммы при печати (без влияния на вид моего браузера)?

enter image description here

ответ

5

Проблема в том, график не подходит новое измерение ширины печати. К счастью, мы можем выполнить перерисовку при начале печати.

Решение заключается в том, чтобы сделать вашу диаграмму изображением с использованием метода canvas.toDataURL() при печати, а затем переключить его обратно на холст-диаграмму после печати. More on toDataURL().

Чтобы определить, когда вызывать ваши функции WebKit обеспечивает метод window.matchMedia('print') (который будет true во время печати или false впоследствии снова) в то время как другие браузеры используют window.onbeforeprint и window.onafterprint. More on print methods.

Все, что осталось сделать, это обеспечить, чтобы изображение реагировало с использованием CSS, то есть масштабирования до 100% ширины.

+3

Каждый знает, где есть рабочий пример этого? – Rodney

0

Я использовал свой стиль печати для холста с пользовательским правым дополнением:

@media print { 
    .chartCanvas { 
    padding-right: 1cm; 
    } 
} 
+1

Не знаете, как это решает проблему. Полотно все еще не изменяется, потому что вы добавляете дополнение. – perry

+0

Это действительно исправить мою проблему, спасибо! – mfink

0

После ссылки и пример Реджей Пинкхов, я был в состоянии сделать эту работу в угловом 2. Пример находится в машинописи, но читатель должен уметь адаптировать это к регулярному javascript довольно легко, чтобы работать в других проектах. Примечание. Я тестировал это только в последней версии chrome на linux-боксе, так как это нормально для моего внутреннего проекта компании.

// imports left out here 
export class ScaleChartComponent implements OnInit { 
private chart:Chart; 
private chartNode:HTMLCanvasElement; 
private chartImage:HTMLImageElement; 
private mediaQueryListener:MediaQueryListListener; 

// el is a reference to the root node of my angular html component think of it as just a div container. 
constructor(private el:ElementRef) { } 
ngOnDestroy() { 
    this.chart.clear(); 
    this.chart.destroy(); 
    this.chart = null; 
    this.cleanupPrint(); 
} 

ngAfterViewInit() { 
    this.drawChart(); 
    this.setupPrint(); 
} 
// need to setup the event listeners here and hold a reference to cleanup afterwards. 
public setupPrint() { 
    if (!window.matchMedia) { 
    return; 
    } 

    var mediaQueryList = window.matchMedia('print'); 
    this.mediaQueryListener = this.handlePrintMediaChange.bind(this); 
    mediaQueryList.addListener(this.mediaQueryListener); 
} 
// make sure to cleanup the reference after the fact. 
public cleanupPrint() { 
    if (!window.matchMedia) { 
    return; 
    } 
    var mediaQueryList = window.matchMedia('print'); 
    mediaQueryList.removeListener(this.mediaQueryListener); 
    this.mediaQueryListener = null; 
} 

// here's where the magic happens. I first grab the image 
// then 
public handlePrintMediaChange(mql) { 
    if (mql.matches) { 
    let dataUrl = this.chartNode.toDataURL('image/png'); 

    if (this.chartNode && this.chartNode.parentNode) { 
     this.chartImage = new Image(); 
     this.chartImage.src = dataUrl; 
     this.chartNode.parentNode.appendChild(this.chartImage); 
     this.chartService.destroyChart(this.chart); 
     this.chartNode.parentNode.removeChild(this.chartNode); 
    } 

    } else { 
    // here is where we switch back to non print mode. 
    if (this.chartImage) { 
     if (this.chartImage.parentNode) { 
     this.chartImage.parentNode.removeChild(this.chartImage); 
     } 
     this.chartImage = null; 
    } 
    // go through and recreate the entire chart again. 
    this.drawChart(); 
    } 
} 

public drawChart() { 
    var chartData = {}; // setup your chart data here. 
    this.chartNode = this.createChartNode(); 
    if (this.chartNode) { 
    this.chart = ; // execute your chart.js draw commands here. 
    } 
} 
private createChartNode() { 
    let componentElement = this.el.nativeElement as Element; 
    let element = componentElement.querySelector(".scale-chart-container"); 
    if (!element) { 
    console.error("could not find element with class .scale-chart-container"); 
    return null; 
    } 

    let chartNode = document.createElement("canvas") as HTMLCanvasElement; 
    element.appendChild(chartNode); 
    chartNode = chartNode; 
    return chartNode; 

} 

}

Обратите внимание, что я ушел из chart.js команды и данные, которые будут варьироваться в зависимости от человека. У меня есть внешняя служба, которая касается того, что я забыл.

Надеюсь, это поможет любому, кто почесывает голову, как уйти от ответа Реджи.

1

Если ваши графики просты, попробуйте использовать только с помощью CSS

@media print { 
    canvas.chart-canvas { 
     min-height: 100%; 
     max-width: 100%; 
     max-height: 100%; 
     height: auto!important; 
     width: auto!important; 
    } 
} 
Смежные вопросы