How to use content slide with RECORD objects in typoscript - slide

On one of my sites, content (Videos) is inherited from the levels above if the content column is empty (in this case: colPos=3 / Border)
To create the output, I use
temp.myObject < styles.content.getBorder
temp.myObject {
slide = -1
}
Easy, because this is taken from a CONTENT object and slide is a built-in function.
Due to our system setup I need to do something similar with the RECORDS object. But the following typoscript doesn't work - it generates empty output:
temp.myObject = RECORDS
temp.myObject {
tables = tt_content
source.cObject = CONTENT
source.cObject {
slide = -1
table = tt_content
renderObj = TEXT
renderObj.field = uid
}
}
The same happens with this snippet:
temp.myObject = RECORDS
temp.myObject {
tables = tt_content
source.cObject = CONTENT
source.cObject {
table = tt_content
select {
pidInList.data = leveluid:-1,slide
}
renderObj = TEXT
renderObj.field = uid
}
}
[Note: The complicated source part above provides the ID of a content element from where we extract an image file from the flexform xml]
Can somebody help me to achieve a contentslide solution based on the RECORDS object?
If there are any problems understanding the questions, please ask.

CONTENT object doesn't have "slide" property.
Try simulate slide using stdWrap.ifEmpty.cObject.... for Your RECORDS object, as it could be done for slide simulation for TYPO3 3.8.x.
Example on TYPO3 wiki :
http://wiki.typo3.org/wiki/Content_Slide#Content_Sliding_in_TYPO3_3.8.x_by_TS_only

Related

How to get Header / Footer parts from Excel Document

I'm trying to get the header / footer parts from an excel document so that I can do something with their contents, however I cannot seem to get anything from them.
I thought this would be pretty simple... Consider this code:
using (SpreadsheetDocument spreadsheet = SpreadsheetDocument.Open(filePath, true))
{
var headers = spreadsheet.GetPartsOfType<HeaderPart>().ToList();
foreach (var header in headers)
{
//do something
}
}
Even with a file that contains a header, headers will always be empty. I've tried drilling down into the workbook -> worksheets -> etc but i get nothing back. My testing excel file definitely has a header (headers are ghastly in excel!).
Annoyingly the api's for excel in openxml seem to be worse as in a docx you can get the header by calling:
using (WordprocessingDocument wordDoc = WordprocessingDocument.Open(filePath, true))
{
MainDocumentPart documentPart = wordDoc.MainDocumentPart;
var headerParts = wordDoc.MainDocumentPart.HeaderParts.ToList();
foreach (var headerPart in headerParts)
{
//do something
}
}
I've seen some people on google saying that I should query the worksheet's descendants (code from this link):
HeaderFooter hf = ws.Descendants<HeaderFooter>().FirstOrDefault();
if (hf != null)
{
//here you can add your code
//I just try to append here for demo
hf = new HeaderFooter();
ws.AppendChild<HeaderFooter>(hf);
}
But I cannot see any way of querying the workbook/sheet/anything with .Descendants and obviously none of the code examples on google show how they got ws 🙃.
Any ideas? Thanks
HeaderFooter, as per your second example, is the correct way to read a Header or Footer from a Spreadsheet using OpenXML. The ws in your example refers to a Worksheet.
The following is an example that reads the HeaderFooter and dumps the InnerText to the console.
using (SpreadsheetDocument document = SpreadsheetDocument.Open(filePath, false))
{
WorkbookPart workbookPart = document.WorkbookPart;
WorksheetPart worksheetPart = workbookPart.WorksheetParts.First();
Worksheet ws = worksheetPart.Worksheet;
HeaderFooter hf = ws.Descendants<HeaderFooter>().FirstOrDefault();
if (hf != null)
{
Console.WriteLine(hf.InnerText);
}
}
I would highly recommend that you read the documentation for the HeaderFooter element as it's more complex than you might imagine. The documentation can be found in section 18.3.1.46 of the Fifth Edition of the Ecma Office Open XML Part 1 - Fundamentals And Markup Language Reference which can be found here.

Adding an image to only one node within a Tree View

I'm currently working on modifying a Tree View control (Telerik MVC Extensions) for a customer request. Their request is a simple one: if an item within the tree has an Attachment, add a paperclip beside the node to identify it.
I have so far been able to do so but, found a small hiccup with this. I can add the image to certain nodes that have an Attachment, however, all nodes that don't should have no image (by that, I mean they should appear normal within the tree). Instead though, I find that the tree places a blank the size of the paperclip image.
Is there a way to dynamically turn off this blank (aka not add an Image Url if unnecessary)? Below is my code where I'm executing this process (is done on the expansion method of the tree due that only the bottom level shows the Attachments).
Navigation Controller
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult GetNextTreeViewLevel(TreeViewItem node)
{
...
//If bottom layer, then execute the following
var data = _TreeRepo.GetProcessesByParcel(int.Parse(values[1]), cntTreeList);
nodes = from item in data
select new TreeViewItem
{
Text = item.strProcess,
Value = "PR" + "," + item.cntProcess.ToString(),
LoadOnDemand = false,
Enabled = true,
Selected = SelectedSearchResult.ToString().Length > 0
&& SelectedSearchResult.ToString().Split('~').Length > 3
&& decimal.Parse(SelectedSearchResult.ToString()
.Split('~')
.Last()
.Substring(2)) == item.cntProcess
ImageUrl = item.ysnHasAttachment.HasValue && item.ysnHasAttachment.Value == 1
? #"/Content/NewImages/attachment.png"
: string.Empty
};
return new JsonResult { Data = nodes };
}
Screen shots of what it looks like without/with code for Image Url:
I at long last came up with a solution to this issue. The problem was how I was getting my data added to the nodes. The original logic was doing a Linq query after fetching the data to get an IEnumerable object.
Because of that, every node was trying to add an image (even if there was none). Hence the weird looking space. Below is how I reworked this logic to correctly get my data.
var processNodes = new List<TreeViewItem>();
var data = _TreeRepo.GetProcessesByParcel(int.Parse(values[1]), cntTreeList);
foreach (var item in data)
{
#region Process has at least one Attachment
if (item.ysnHasAttachment.HasValue && item.ysnHasAttachment.Value == 1)
processNodes.Add(new TreeViewItem
{
Text = item.strProcess,
Value = "PR" + "," + item.cntProcess.ToString(),
LoadOnDemand = false,
Enabled = true,
Selected = SelectedSearchResult.ToString().Length > 0
&& SelectedSearchResult.ToString().Split('~').Length > 3
&& decimal.Parse(SelectedSearchResult.ToString()
.Split('~')
.Last()
.Substring(2)) == item.cntProcess,
ImageUrl = "/Content/NewImages/smallAttachment.png"
});
#endregion
#region Process has no Attachments
else
processNodes.Add(new TreeViewItem
{
Text = item.strProcess,
Value = "PR" + "," + item.cntProcess.ToString(),
LoadOnDemand = false,
Enabled = true,
Selected = SelectedSearchResult.ToString().Length > 0
&& SelectedSearchResult.ToString().Split('~').Length > 3
&& decimal.Parse(SelectedSearchResult.ToString()
.Split('~')
.Last()
.Substring(2)) == item.cntProcess
}
#endregion
}
nodes = processNodes;
At this point, you can now return the nodes. Those that should have had an Attachment icon will, and those that shouldn't won't. Funny how 4 months later, you can come up with something off the cuff.

How to give data dynamically in a dialog box using visual c++

How can I send data to a dialog box dynamically?
In a previous project I used edit boxes (e.g for 3 conductors) and gave those data separately for each conductor. Now I have to give them dynamically and I don't have standard number of conductors and I can't use edit box again.
Could you please give me an idea or a good link describing step by step how to create a table in a dialog box dynamically?
I have created a dialog box in which I insert data about conductors (resistivity, permeability, diameter etc (electric power systems Smile | :) )) in edit boxes but I have done it only for 3 conductors. I have to insert-edit the number of conductors and then edit their characteristics. But I can't use again edit boxes because this is static. I want something like a dynamic table which will have rows=number of conductors and columns about is characteristic (resistivity, permeability, diameter)and edit them in dialog box. I don't know how to upload my executable to male clear what I have done but here is a part of my code for the static case of three conductors Smile | :) I want another dynamic way to edit data :/
void CInputView::OnLinefeaturesFeatures()
{
// TODO: Add your command handler code here
CInputDoc* pDoc = GetDocument();
CFeaturesDialog DialogWindow;
DialogWindow.m_DialogCon = m_NumCond;
DialogWindow.m_DialogLayers = m_Layers;
DialogWindow.m_DialogPermeability = m_AirPermeability;
DialogWindow.m_DialogAirConductivity = m_AirConductivity;
DialogWindow.m_DialogAirPermittivity = m_AirPermittivity;
DialogWindow.m_DialogEarthPermeability1 = m_EarthPermeability1;
DialogWindow.m_DialogEarthConductivity1 = m_EarthConductivity1;
DialogWindow.m_DialogEarthPermittivity1 = m_EarthPermittivity;
DialogWindow.m_DialogDepth = m_depth;
DialogWindow.m_DialogEarthPermeability2 = m_EarthPermeability2;
DialogWindow.m_DialogEarthConductivity2 = m_EarthConductivity2;
DialogWindow.m_DialogEarthPermittivity2 = m_EarthPermittivity2;
DialogWindow.m_Dialogfrequency = m_frequency;
if (DialogWindow.DoModal() == IDOK)
{
m_NumCond = DialogWindow.m_DialogCon;
m_Layers = DialogWindow.m_DialogLayers;
m_AirPermeability = DialogWindow.m_DialogPermeability;
m_AirConductivity = DialogWindow.m_DialogAirConductivity;
m_AirPermittivity = DialogWindow.m_DialogAirPermittivity;
m_EarthPermeability1 = DialogWindow.m_DialogEarthPermeability1;
m_EarthConductivity1 = DialogWindow.m_DialogEarthConductivity1;
m_EarthPermittivity = DialogWindow.m_DialogEarthPermittivity1;
m_depth = DialogWindow.m_DialogDepth;
m_EarthPermeability2 = DialogWindow.m_DialogEarthPermeability2;
m_EarthConductivity2 = DialogWindow.m_DialogEarthConductivity2;
m_EarthPermittivity2 = DialogWindow.m_DialogEarthPermittivity2;
m_frequency = DialogWindow.m_Dialogfrequency;
}
}

Insert image into a specified location

I have a Google Apps script which replaces placeholders in a copy of a template document with some text by calling body.replaceText('TextA', 'TextB');.
Now I want to extend it to contain images. Does anybody have idea how to do this?
Thank you,
Andrey
EDIT: Just to make it clear what my script does. I have a Google form created in a spreadsheet. I've created a script which runs upon form submission, traverses a sheet corresponding to the form, find unprocessed rows, takes values from corresponding cells and put them into a copy of a Google document.
Some fields in the Google form are multi-line text fields, that's where '\r\r' comes from.
Here's a workaround I've come up with by now, not elegant, but it works so far:
// replace <IMG src="URL"> with the image fetched from URL
function processIMG_(Doc) {
var totalElements = Doc.getNumChildren();
for( var j = 0; j < totalElements; ++j ) {
var element = Doc.getChild(j);
var type = element.getType();
if (type =='PARAGRAPH'){
var par_text = element.getText();
var start = par_text.search(new RegExp('<IMG'));
var end = par_text.search(new RegExp('>'));
if (start==-1)
continue;
// Retrieve an image from the web.
var url = getURL_(par_text.substring(start,end));
if(url==null)
continue;
// Before image
var substr = par_text.substring(0,start);
var new_par = Doc.insertParagraph(++j, substr);
// Insert image
var resp = UrlFetchApp.fetch(url);
new_par.appendInlineImage(resp.getBlob());
// After image
var substr = par_text.substring(end+1);
Doc.insertParagraph(++j, substr);
element.removeFromParent();
j -= 2; // one - for latter increment; another one - for increment in for-loop
totalElements = Doc.getNumChildren();
}
}
}
Here is a piece of code that does (roughly) what you want.
(there are probably other ways to do that and it surely needs some enhancements but the general idea is there)
I have chosen to use '###" in the doc to mark the place where the image will be inserted, the image must be in your google drive (or more accurately in 'some' google drive ).
The code below uses a document I shared and an image I shared too so you can try it.
here is the link to the doc, don't forget to remove the image and to put a ### somewhere before testing (if ever someone has run the code before you ;-)
function analyze() { // just a name, I used it to analyse docs
var Doc = DocumentApp.openById('1INkRIviwdjMC-PVT9io5LpiiLW8VwwIfgbq2E4xvKEo');
var image = DocsList.getFileById('0B3qSFd3iikE3cF8tSTI4bWxFMGM')
var totalElements = Doc.getNumChildren();
var el=[]
for( var j = 0; j < totalElements; ++j ) {
var element = Doc.getChild(j);
var type = element.getType();
Logger.log(j+" : "+type);// to see doc's content
if (type =='PARAGRAPH'){
el[j]=element.getText()
if(el[j]=='###'){element.removeFromParent();// remove the ###
Doc.insertImage(j, image);// 'image' is the image file as blob
}
}
}
}
EDIT : for this script to work the ### string MUST be alone in its paragraph, no other character before nor after... remember that each time one forces a new line with ENTER the Document creates a new paragraph.

How to get a value out of an Excel workbook stored in a SharePoint document library?

I have some data that's currently stored in an Excel workbook. It makes sense for the data to be in Excel (in that it's easy to manage, easy to extend, do calcs, etc.) but some of the data there is required by an automated process, so from that point of view it would be more convenient if it were in a database.
To give the information more visibility, workflow, etc. I'm thinking of moving it to SharePoint. Actually turning it into a SharePoint form would be tedious & time-consuming, and then the flexibility/convenience would be lost; instead, I'm thinking of simply storing the current Excel file within a SharePoint library.
My problem then would be: how can the automated process extract the values it needs from the Excel workbook that now lives within the SharePoint library? Is this something that Excel Services can be used for? Or is there another/better way? And even if it can be done, is it a sensible thing to do?
Having gone through something similar, I can tell you it actually isn't that bad getting values out of an Excel file in a document library. I ended up writing a custom workflow action (used within a SharePoint Designer workflow) that reads values out of the Excel file for processing. I ended up choosing NPOI to handle all of the Excel operations.
Using NPOI, you can do something like this:
// get the document in the document library
SPList myList = web.Lists[listGuid];
SPListItem myItem = myList.GetItemById(ListItem);
SPFile file = myItem.File;
using (Stream stream = file.OpenBinaryStream())
{
HSSFWorkbook workbook = new HSSFWorkbook(stream);
HSSFSheet sheet = workbook.GetSheet("Sheet1");
CellReference c = new CellReference("A1");
HSSFRow row = sheet.GetRow(c.Row);
HSSFCell cell = row.GetCell(c.Col);
string cellValue = cell.StringCellValue;
// etc...
}
You could easily put this in a console application as well.
Yes, I am trying to extract a range of cells on several sheets within a workbook. I was able to use some of the code below in a console application and view the data within the command window. Now I need to dump the data to a SQL Table and was looking for some examples on how to accomplish this and make sure I am going down the correct coding path.
Here is a snapshot of the code I am using.
protected override ActivityExecutionStatus Execute(ActivityExecutionContext executionContext)
{
using (SPSite site = new SPSite(SPContext.Current.Site.Url))
{
using (SPWeb web = site.RootWeb)
{
SPList docList = web.Lists[__ListId];
SPListItem docItem = docList.GetItemById(__ListItem);
SPFile docFile = docItem.File;
using (Stream stream = docFile.OpenBinaryStream())
{
HSSFWorkbook wb = new HSSFWorkbook(stream);
//loop through each sheet in file, ignoring the first sheet
for (int i = 1; i < 0; i++)
{
NPOI.SS.UserModel.Name name = wb.GetNameAt(i);
String sheet = wb.GetSheetName(i);
NPOI.SS.UserModel.Name nameRange = wb.CreateName();
nameRange.NameName = ("DispatchCells");
//start at a specific area on the sheet
nameRange.RefersToFormula = (sheet + "!$A$11:$AZ$100");
}
wb.Write(stream);
}
}
}
return ActivityExecutionStatus.Closed;
}

Resources