/* ====================================================================
   Licensed to the Apache Software Foundation (ASF) under one or more
   contributor license agreements.  See the NOTICE file distributed with
   this work for additional information regarding copyright ownership.
   The ASF licenses this file to You under the Apache License, Version 2.0
   (the "License"); you may not use this file except in compliance with
   the License.  You may obtain a copy of the License at

       http://www.apache.org/licenses/LICENSE-2.0

   Unless required by applicable law or agreed to in writing, software
   distributed under the License is distributed on an "AS IS" BASIS,
   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   See the License for the specific language governing permissions and
   limitations under the License.
==================================================================== */

package org.apache.poi.xssf.usermodel.examples;

import java.io.FileOutputStream;
import java.util.Date;

import org.apache.poi.ss.usermodel.*;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

/**
 * Illustrates how to create cell and set values of different types.
 */
public class CreateCell {


	public static void main(String[]args) throws Exception {
        Workbook wb = new XSSFWorkbook(); //or new HSSFWorkbook();
        CreationHelper creationHelper = wb.getCreationHelper();
        Sheet sheet = wb.createSheet("new sheet");

        // Create a row and put some cells in it. Rows are 0 based.
        Row row = sheet.createRow((short)0);
        // Create a cell and put a value in it.
        Cell cell = row.createCell((short)0);
        cell.setCellValue(1);

        //numeric value
        row.createCell(1).setCellValue(1.2);

        //plain string value
        row.createCell(2).setCellValue("This is a string cell");

        //rich text string
        RichTextString str = creationHelper.createRichTextString("Apache");
        Font font = wb.createFont();
        font.setItalic(true);
        font.setUnderline(Font.U_SINGLE);
        str.applyFont(font);
        row.createCell(3).setCellValue(str);

        //boolean value
        row.createCell(4).setCellValue(true);

        //formula
        row.createCell(5).setCellFormula("SUM(A1:B1)");

        //date
        CellStyle style = wb.createCellStyle();
        style.setDataFormat(creationHelper.createDataFormat().getFormat("m/d/yy h:mm"));
        cell = row.createCell(6);
        cell.setCellValue(new Date());
        cell.setCellStyle(style);

        //hyperlink
        row.createCell(7).setCellFormula("SUM(A1:B1)");
        cell.setCellFormula("HYPERLINK(\"http://google.com\",\"Google\")");


        // Write the output to a file
        FileOutputStream fileOut = new FileOutputStream("ooxml-cell.xlsx");
        wb.write(fileOut);
        fileOut.close();
	}
}
