mirror of
https://github.com/objective-see/TaskExplorer.git
synced 2026-03-22 07:02:39 +00:00
dylibs and files in bottom pane are now sorted
errSecCSBadResource is ignored when checking for apple-signed files 'show file' fixed in bottom pane tree view (re)fixed and sorted based on PID tree view logic combined in single file
This commit is contained in:
Vendored
+3
-2
@@ -36,7 +36,8 @@
|
||||
- (NSEnumerator *)reverseKeyEnumerator;
|
||||
-(void)reverse;
|
||||
|
||||
//sort, by object key
|
||||
-(void)sort:(NSString*)sortKey;
|
||||
//sort
|
||||
// ->by pid, name, etc
|
||||
-(void)sort:(NSUInteger)sortBy;
|
||||
|
||||
@end
|
||||
|
||||
Vendored
+21
-6
@@ -21,6 +21,7 @@
|
||||
// distribution.
|
||||
//
|
||||
|
||||
#import "Consts.h"
|
||||
#import "OrderedDictionary.h"
|
||||
|
||||
NSString *DescriptionForObject(NSObject *object, id locale, NSUInteger indent)
|
||||
@@ -133,17 +134,31 @@ NSString *DescriptionForObject(NSObject *object, id locale, NSUInteger indent)
|
||||
array = [[[array reverseObjectEnumerator] allObjects] mutableCopy];
|
||||
}
|
||||
|
||||
//sort, by object key
|
||||
-(void) :(NSString*)sortKey
|
||||
//sort
|
||||
// ->by pid, name, etc
|
||||
-(void)sort:(NSUInteger)sortBy
|
||||
{
|
||||
//task sorted by name
|
||||
NSArray* sortedTasks = nil;
|
||||
|
||||
//sort task by binary name
|
||||
sortedTasks = [[dictionary allValues] sortedArrayUsingSelector:@selector(compare:)];
|
||||
//
|
||||
if(SORT_BY_PID == sortBy)
|
||||
{
|
||||
[array sortUsingComparator:^NSComparisonResult(id obj1, id obj2) {
|
||||
return [obj1 compare:obj2];
|
||||
}];
|
||||
}
|
||||
else if(SORT_BY_NAME == sortBy)
|
||||
{
|
||||
//get array of tasks, sorted by binary name
|
||||
// ->invokes Task class's compare method
|
||||
sortedTasks = [[dictionary allValues] sortedArrayUsingSelector:@selector(compare:)];
|
||||
|
||||
//extract sorted pids into array
|
||||
array = [[sortedTasks valueForKey:@"pid"] mutableCopy];
|
||||
|
||||
}
|
||||
|
||||
//extract pids into array
|
||||
array = [[sortedTasks valueForKey:@"pid"] mutableCopy];
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
+5
-2
@@ -12,7 +12,6 @@
|
||||
#import "Filter.h"
|
||||
#import "VirusTotal.h"
|
||||
#import "TaskTableController.h"
|
||||
#import "TreeViewController.h"
|
||||
|
||||
#import "AboutWindowController.h"
|
||||
#import "PrefsWindowController.h"
|
||||
@@ -49,11 +48,15 @@
|
||||
@property (nonatomic, retain)TaskTableController *taskTableController;
|
||||
|
||||
//tree (outline) controller
|
||||
@property (nonatomic, retain)TreeViewController* treeViewController;
|
||||
//@property (nonatomic, retain)TreeViewController* treeViewController;
|
||||
|
||||
//array to hold binary objects that are in array
|
||||
//@property (nonatomic, retain)NSMutableArray *tableContents;
|
||||
|
||||
//current task view format
|
||||
// ->flat or tree
|
||||
@property NSUInteger taskViewFormat;
|
||||
|
||||
//drop-down view selector
|
||||
|
||||
@property (weak) IBOutlet NSPopUpButton *viewSelector;
|
||||
|
||||
+37
-11
@@ -31,7 +31,7 @@
|
||||
@synthesize bottomViewController;
|
||||
@synthesize currentTask;
|
||||
@synthesize requestRootWindowController;
|
||||
|
||||
@synthesize taskViewFormat;
|
||||
|
||||
@synthesize scannerThread;
|
||||
@synthesize versionString;
|
||||
@@ -39,7 +39,7 @@
|
||||
|
||||
@synthesize topPane;
|
||||
@synthesize taskEnumerator;
|
||||
@synthesize treeViewController;
|
||||
//@synthesize treeViewController;
|
||||
@synthesize currentViewController;
|
||||
@synthesize viewSelector;
|
||||
|
||||
@@ -144,10 +144,12 @@
|
||||
}
|
||||
*/
|
||||
|
||||
//set default top pane view to flat
|
||||
self.taskViewFormat = FLAT_VIEW;
|
||||
|
||||
//set initial view for top pane
|
||||
// ->default is flat (non-tree) view
|
||||
[self changeViewController:FLAT_VIEW];
|
||||
[self changeViewController];
|
||||
|
||||
//alloc/init bottom pane controller
|
||||
self.bottomViewController = [[TaskTableController alloc] initWithNibName:@"FlatView" bundle:nil];
|
||||
@@ -312,7 +314,7 @@
|
||||
|
||||
//change top pane
|
||||
// ->switch between either flat (default) or tree-based (hierachical) view
|
||||
-(void)changeViewController:(NSInteger)whichViewTag
|
||||
-(void)changeViewController
|
||||
{
|
||||
//remove old view
|
||||
if([self.currentViewController view] != nil)
|
||||
@@ -321,7 +323,7 @@
|
||||
[[self.currentViewController view] removeFromSuperview];
|
||||
}
|
||||
|
||||
switch (whichViewTag)
|
||||
switch(self.taskViewFormat)
|
||||
{
|
||||
case FLAT_VIEW:
|
||||
{
|
||||
@@ -337,11 +339,11 @@
|
||||
case TREE_VIEW:
|
||||
{
|
||||
//alloc/init
|
||||
treeViewController = [[TreeViewController alloc] initWithNibName:@"TreeView" bundle:nil];
|
||||
if(self.treeViewController != nil)
|
||||
taskTableController = [[TaskTableController alloc] initWithNibName:@"TreeView" bundle:nil];
|
||||
if(self.taskTableController != nil)
|
||||
{
|
||||
//update iVar
|
||||
self.currentViewController = self.treeViewController;
|
||||
self.currentViewController = self.taskTableController;
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -616,6 +618,22 @@ bail:
|
||||
// invoke custom refresh method on main thread
|
||||
-(void)reloadTaskTable
|
||||
{
|
||||
//sort tasks
|
||||
// ->flat view, sort by name
|
||||
if(FLAT_VIEW == self.taskViewFormat)
|
||||
{
|
||||
//sort
|
||||
[self.taskEnumerator.tasks sort:SORT_BY_NAME];
|
||||
}
|
||||
//sort tasks
|
||||
// ->tree view, sort by pid
|
||||
else
|
||||
{
|
||||
//sort
|
||||
[self.taskEnumerator.tasks sort:SORT_BY_PID];
|
||||
}
|
||||
|
||||
|
||||
//when exec'ing on background thread
|
||||
// ->exec on main thread
|
||||
if(YES != [NSThread isMainThread])
|
||||
@@ -634,8 +652,10 @@ bail:
|
||||
// ->just refresh
|
||||
else
|
||||
{
|
||||
//TODO: currentViewCont?!?
|
||||
//refresh
|
||||
[(id)self.taskTableController refresh];
|
||||
//[(id)self.taskTableController refresh];
|
||||
[(id)self.currentViewController refresh];
|
||||
}
|
||||
|
||||
return;
|
||||
@@ -1342,8 +1362,14 @@ bail:
|
||||
// ->invoke helper function to change view
|
||||
-(IBAction)switchView:(id)sender
|
||||
{
|
||||
//switch (top) view
|
||||
[self changeViewController: [[sender selectedCell] tag]];
|
||||
//save selected view
|
||||
self.taskViewFormat = [[sender selectedCell] tag];
|
||||
|
||||
//switch (top) view/pane
|
||||
[self changeViewController];
|
||||
|
||||
//reload top pane
|
||||
[self reloadTaskTable];
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -293,6 +293,12 @@
|
||||
//connected socket
|
||||
#define SOCKET_ESTABLISHED @"connected"
|
||||
|
||||
//sort by pid
|
||||
#define SORT_BY_PID 0x0
|
||||
|
||||
//sort by name
|
||||
#define SORT_BY_NAME 0x1
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -328,6 +328,13 @@ bail:
|
||||
//alloc array for new dylibs
|
||||
newDylibs = [NSMutableArray array];
|
||||
|
||||
//sync
|
||||
@synchronized(self.dylibs)
|
||||
{
|
||||
//reset existing dylibs
|
||||
[self.dylibs removeAllObjects];
|
||||
}
|
||||
|
||||
//invoke XPC service (running as r00t)
|
||||
// ->will enumerate dylibs, then invoke reply block to save into iVar
|
||||
[[xpcConnection remoteObjectProxy] enumerateDylibs:self.pid withReply:^(NSMutableArray* dylibPaths) {
|
||||
@@ -393,6 +400,18 @@ bail:
|
||||
}
|
||||
}
|
||||
|
||||
//sync to sort
|
||||
@synchronized(self.dylibs)
|
||||
{
|
||||
//sort by name
|
||||
self.dylibs = [[self.dylibs sortedArrayUsingComparator:^NSComparisonResult(id a, id b)
|
||||
{
|
||||
//sort
|
||||
return [[(Binary*)a name] compare:[(Binary*)b name] options:NSCaseInsensitiveSearch];
|
||||
|
||||
}] mutableCopy];
|
||||
}
|
||||
|
||||
//reload bottom pane now
|
||||
// ->this will only reload if new task is the currently selected one, etc
|
||||
[((AppDelegate*)[[NSApplication sharedApplication] delegate]) reloadBottomPane:self itemView:DYLIBS_VIEW];
|
||||
@@ -406,7 +425,7 @@ bail:
|
||||
}
|
||||
|
||||
//any new dylibs?
|
||||
// ->reload bottom pane
|
||||
// ->reload bottom pane to update signing info, etc
|
||||
if(0 != newDylibs.count)
|
||||
{
|
||||
//reload
|
||||
@@ -435,6 +454,13 @@ bail:
|
||||
//alloc array for new files
|
||||
newFiles = [NSMutableArray array];
|
||||
|
||||
//sync
|
||||
@synchronized(self.files)
|
||||
{
|
||||
//reset existing files
|
||||
[self.files removeAllObjects];
|
||||
}
|
||||
|
||||
//invoke XPC service (running as r00t)
|
||||
// ->will enumerate files, then invoke reply block so can save into iVar
|
||||
[[xpcConnection remoteObjectProxy] enumerateFiles:self.pid withReply:^(NSMutableArray* fileDescriptors) {
|
||||
@@ -455,9 +481,13 @@ bail:
|
||||
//next
|
||||
continue;
|
||||
}
|
||||
|
||||
//add to task's files
|
||||
[self.files addObject:file];
|
||||
|
||||
//sync
|
||||
@synchronized(self.files)
|
||||
{
|
||||
//add to task's files
|
||||
[self.files addObject:file];
|
||||
}
|
||||
|
||||
//save new files
|
||||
// ->will be processed below
|
||||
@@ -468,6 +498,18 @@ bail:
|
||||
}
|
||||
}
|
||||
|
||||
//sync to sort
|
||||
@synchronized(self.files)
|
||||
{
|
||||
//sort by name
|
||||
self.files = [[self.files sortedArrayUsingComparator:^NSComparisonResult(id a, id b)
|
||||
{
|
||||
//sort
|
||||
return [[(File*)a name] compare:[(File*)b name] options:NSCaseInsensitiveSearch];
|
||||
|
||||
}] mutableCopy];
|
||||
}
|
||||
|
||||
//reload bottom pane
|
||||
[((AppDelegate*)[[NSApplication sharedApplication] delegate]) reloadBottomPane:self itemView:FILES_VIEW];
|
||||
|
||||
|
||||
+1
-6
@@ -138,9 +138,7 @@
|
||||
|
||||
}//add new tasks
|
||||
|
||||
//sort by name!
|
||||
|
||||
//reload table
|
||||
//reload task table
|
||||
[((AppDelegate*)[[NSApplication sharedApplication] delegate]) reloadTaskTable];
|
||||
|
||||
//now generate signing info
|
||||
@@ -261,9 +259,6 @@
|
||||
//add kernel task
|
||||
[allTasks setObject:task forKey:@0];
|
||||
|
||||
//sort all tasks alphabetically
|
||||
[allTasks sort:@"name"];
|
||||
|
||||
//bail
|
||||
bail:
|
||||
|
||||
|
||||
@@ -29,7 +29,6 @@
|
||||
CD3F4CFF1AF72BC4002A2647 /* TaskInfoWindow.xib in Resources */ = {isa = PBXBuildFile; fileRef = CD3F4CFE1AF72BC4002A2647 /* TaskInfoWindow.xib */; };
|
||||
CD3F4D141AF85088002A2647 /* FlatView.xib in Resources */ = {isa = PBXBuildFile; fileRef = CD3F4D131AF85088002A2647 /* FlatView.xib */; };
|
||||
CD3F4D161AF89066002A2647 /* TreeView.xib in Resources */ = {isa = PBXBuildFile; fileRef = CD3F4D151AF89066002A2647 /* TreeView.xib */; };
|
||||
CD3F4D1C1AFADD36002A2647 /* TreeViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = CD3F4D1B1AFADD36002A2647 /* TreeViewController.m */; };
|
||||
CD4D53CA1B20296E00008030 /* unknown.png in Resources */ = {isa = PBXBuildFile; fileRef = CD4D53C91B20296E00008030 /* unknown.png */; };
|
||||
CD4D53D01B23ED3900008030 /* connectedIcon.png in Resources */ = {isa = PBXBuildFile; fileRef = CD4D53CF1B23ED3900008030 /* connectedIcon.png */; };
|
||||
CD4D53D21B23ED4300008030 /* listeningIcon.png in Resources */ = {isa = PBXBuildFile; fileRef = CD4D53D11B23ED4300008030 /* listeningIcon.png */; };
|
||||
@@ -164,8 +163,6 @@
|
||||
CD3F4CFE1AF72BC4002A2647 /* TaskInfoWindow.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; name = TaskInfoWindow.xib; path = UI/TaskInfoWindow.xib; sourceTree = "<group>"; };
|
||||
CD3F4D131AF85088002A2647 /* FlatView.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; name = FlatView.xib; path = UI/FlatView.xib; sourceTree = "<group>"; };
|
||||
CD3F4D151AF89066002A2647 /* TreeView.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; name = TreeView.xib; path = UI/TreeView.xib; sourceTree = "<group>"; };
|
||||
CD3F4D1A1AFADD36002A2647 /* TreeViewController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TreeViewController.h; sourceTree = "<group>"; };
|
||||
CD3F4D1B1AFADD36002A2647 /* TreeViewController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = TreeViewController.m; sourceTree = "<group>"; };
|
||||
CD4D53C91B20296E00008030 /* unknown.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = unknown.png; path = images/unknown.png; sourceTree = SOURCE_ROOT; };
|
||||
CD4D53CF1B23ED3900008030 /* connectedIcon.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = connectedIcon.png; path = images/connectedIcon.png; sourceTree = SOURCE_ROOT; };
|
||||
CD4D53D11B23ED4300008030 /* listeningIcon.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = listeningIcon.png; path = images/listeningIcon.png; sourceTree = SOURCE_ROOT; };
|
||||
@@ -465,8 +462,6 @@
|
||||
children = (
|
||||
CDA5F6C21B16E20E003CE340 /* RequestRootWindowController.h */,
|
||||
CDA5F6C31B16E20E003CE340 /* RequestRootWindowController.m */,
|
||||
CD3F4D1A1AFADD36002A2647 /* TreeViewController.h */,
|
||||
CD3F4D1B1AFADD36002A2647 /* TreeViewController.m */,
|
||||
CD6E54FD1B1162B5007953AB /* ItemView.h */,
|
||||
CD6E54FE1B1162B5007953AB /* ItemView.m */,
|
||||
CD02195F1AD39A83005148A2 /* ResultsWindowController.h */,
|
||||
@@ -697,7 +692,6 @@
|
||||
CDA81D7B1A95D29B009790E2 /* TaskTableController.m in Sources */,
|
||||
CDF08CCA1AC4C678009B3423 /* PrefsWindowController.m in Sources */,
|
||||
CDA81DEA1A997BF1009790E2 /* InfoWindowController.m in Sources */,
|
||||
CD3F4D1C1AFADD36002A2647 /* TreeViewController.m in Sources */,
|
||||
CD02195C1AD38823005148A2 /* kkRowCell.m in Sources */,
|
||||
CDF08CE61AC89FE1009B3423 /* HyperlinkTextField.m in Sources */,
|
||||
CDA81D4F1A95B492009790E2 /* AppDelegate.m in Sources */,
|
||||
|
||||
+88
-56
@@ -20,11 +20,11 @@
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "Task.m"
|
||||
timestampString = "455934659.769831"
|
||||
timestampString = "456217349.500536"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "509"
|
||||
endingLineNumber = "509"
|
||||
startingLineNumber = "551"
|
||||
endingLineNumber = "551"
|
||||
landmarkName = "-enumerateNetworking:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
@@ -36,27 +36,11 @@
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "Task.m"
|
||||
timestampString = "455934659.769831"
|
||||
timestampString = "456217349.500536"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "319"
|
||||
endingLineNumber = "319"
|
||||
landmarkName = "-enumerateDylibs:allDylibs:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
</BreakpointProxy>
|
||||
<BreakpointProxy
|
||||
BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
|
||||
<BreakpointContent
|
||||
shouldBeEnabled = "No"
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "Task.m"
|
||||
timestampString = "455934659.769831"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "402"
|
||||
endingLineNumber = "402"
|
||||
startingLineNumber = "421"
|
||||
endingLineNumber = "421"
|
||||
landmarkName = "-enumerateDylibs:allDylibs:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
@@ -68,11 +52,11 @@
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "AppDelegate.m"
|
||||
timestampString = "455870793.890474"
|
||||
timestampString = "456302892.352739"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "406"
|
||||
endingLineNumber = "406"
|
||||
startingLineNumber = "408"
|
||||
endingLineNumber = "408"
|
||||
landmarkName = "-reloadBottomPane:itemView:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
@@ -84,11 +68,11 @@
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "AppDelegate.m"
|
||||
timestampString = "455871607.2373"
|
||||
timestampString = "456302892.352739"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "413"
|
||||
endingLineNumber = "413"
|
||||
startingLineNumber = "415"
|
||||
endingLineNumber = "415"
|
||||
landmarkName = "-reloadBottomPane:itemView:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
@@ -100,11 +84,11 @@
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "AppDelegate.m"
|
||||
timestampString = "455913381.256009"
|
||||
timestampString = "456303370.767322"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "1354"
|
||||
endingLineNumber = "1354"
|
||||
startingLineNumber = "1380"
|
||||
endingLineNumber = "1380"
|
||||
landmarkName = "-selectBottomPaneContent:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
@@ -116,11 +100,11 @@
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "AppDelegate.m"
|
||||
timestampString = "455927034.93809"
|
||||
timestampString = "456303370.767322"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "1375"
|
||||
endingLineNumber = "1375"
|
||||
startingLineNumber = "1401"
|
||||
endingLineNumber = "1401"
|
||||
landmarkName = "-selectBottomPaneContent:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
@@ -132,11 +116,11 @@
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "AppDelegate.m"
|
||||
timestampString = "455927034.93809"
|
||||
timestampString = "456303370.767322"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "1378"
|
||||
endingLineNumber = "1378"
|
||||
startingLineNumber = "1404"
|
||||
endingLineNumber = "1404"
|
||||
landmarkName = "-selectBottomPaneContent:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
@@ -189,22 +173,6 @@
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
</BreakpointProxy>
|
||||
<BreakpointProxy
|
||||
BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
|
||||
<BreakpointContent
|
||||
shouldBeEnabled = "No"
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "TaskTableController.m"
|
||||
timestampString = "456129885.389119"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "995"
|
||||
endingLineNumber = "995"
|
||||
landmarkName = "-showInfo:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
</BreakpointProxy>
|
||||
<BreakpointProxy
|
||||
BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
|
||||
<BreakpointContent
|
||||
@@ -276,14 +244,78 @@
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "Task.m"
|
||||
timestampString = "456131801.925009"
|
||||
timestampString = "456217349.500536"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "532"
|
||||
endingLineNumber = "532"
|
||||
startingLineNumber = "574"
|
||||
endingLineNumber = "574"
|
||||
landmarkName = "-compare:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
</BreakpointProxy>
|
||||
<BreakpointProxy
|
||||
BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
|
||||
<BreakpointContent
|
||||
shouldBeEnabled = "No"
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "TreeViewController.m"
|
||||
timestampString = "456305223.712479"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "63"
|
||||
endingLineNumber = "63"
|
||||
landmarkName = "-outlineView:isItemExpandable:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
</BreakpointProxy>
|
||||
<BreakpointProxy
|
||||
BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
|
||||
<BreakpointContent
|
||||
shouldBeEnabled = "No"
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "TreeViewController.m"
|
||||
timestampString = "456305223.712479"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "82"
|
||||
endingLineNumber = "82"
|
||||
landmarkName = "-outlineView:child:ofItem:"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
</BreakpointProxy>
|
||||
<BreakpointProxy
|
||||
BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
|
||||
<BreakpointContent
|
||||
shouldBeEnabled = "No"
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "TaskTableController.m"
|
||||
timestampString = "456305690.622084"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "40"
|
||||
endingLineNumber = "40"
|
||||
landmarkName = "-awakeFromNib"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
</BreakpointProxy>
|
||||
<BreakpointProxy
|
||||
BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
|
||||
<BreakpointContent
|
||||
shouldBeEnabled = "Yes"
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "TreeViewController.m"
|
||||
timestampString = "456305705.729474"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "13"
|
||||
endingLineNumber = "13"
|
||||
landmarkName = "-awakeFromNib"
|
||||
landmarkType = "5">
|
||||
</BreakpointContent>
|
||||
</BreakpointProxy>
|
||||
</Breakpoints>
|
||||
</Bucket>
|
||||
|
||||
+262
-40
@@ -41,6 +41,18 @@
|
||||
{
|
||||
self.selectedRow = -1;
|
||||
|
||||
//for outline (tree) view
|
||||
// ->expand
|
||||
if(YES == [self.itemView isKindOfClass:[NSOutlineView class]])
|
||||
{
|
||||
[(NSOutlineView*)self.itemView expandItem:nil expandChildren:YES];
|
||||
|
||||
//TODO: do this in IB?
|
||||
//[itemView setTarget:self];
|
||||
}
|
||||
|
||||
NSLog(@"item view: %@", self.itemView);
|
||||
|
||||
/*
|
||||
NSString *title = @"[ all tasks ]";
|
||||
NSTableColumn *yourColumn = self.itemView.tableColumns.lastObject;
|
||||
@@ -96,40 +108,7 @@
|
||||
|
||||
return rows;
|
||||
|
||||
/*
|
||||
|
||||
|
||||
|
||||
//plugin object
|
||||
PluginBase* selectedPluginObj = nil;
|
||||
|
||||
//set selected plugin
|
||||
selectedPluginObj = ((AppDelegate*)[[NSApplication sharedApplication] delegate]).selectedPlugin;
|
||||
|
||||
//invoke helper function to get array
|
||||
// ->then grab count
|
||||
rows = [[self getTableItems] count];
|
||||
|
||||
//if not items have been found
|
||||
// ->display 'not found' msg
|
||||
if( (0 == rows) &&
|
||||
(nil != selectedPluginObj) )
|
||||
{
|
||||
//set string (to include plugin's name)
|
||||
[self.noItemsLabel setStringValue:[NSString stringWithFormat:@"no %@ found", [selectedPluginObj.name lowercaseString]]];
|
||||
|
||||
//show label
|
||||
self.noItemsLabel.hidden = NO;
|
||||
}
|
||||
else
|
||||
{
|
||||
//hide label
|
||||
self.noItemsLabel.hidden = YES;
|
||||
}
|
||||
|
||||
return rows;
|
||||
*/
|
||||
}
|
||||
|
||||
//automatically invoked when user selects row
|
||||
// ->only care about for top pane, trigger load bottom view
|
||||
@@ -958,16 +937,44 @@ bail:
|
||||
// ->open Finder to show item
|
||||
-(IBAction)showInFinder:(id)sender
|
||||
{
|
||||
//task
|
||||
Task* task = nil;
|
||||
//item
|
||||
// ->task, dylib, file, etc
|
||||
id item = nil;
|
||||
|
||||
//get task
|
||||
//TODO: this used to be called w/ nil
|
||||
task = [self taskForRow:sender];
|
||||
//path to binary
|
||||
NSString* path = nil;
|
||||
|
||||
//for top pane
|
||||
// ->get task
|
||||
if(YES != self.isBottomPane)
|
||||
{
|
||||
//get task
|
||||
item = [self taskForRow:sender];
|
||||
|
||||
//get path
|
||||
path = ((Task*)item).binary.path;
|
||||
}
|
||||
|
||||
//bottom pane
|
||||
else
|
||||
{
|
||||
//get item
|
||||
item = [self itemForRow:sender];
|
||||
|
||||
//get path
|
||||
path = ((Binary*)item).path;
|
||||
}
|
||||
|
||||
//sanity check
|
||||
if(nil == path)
|
||||
{
|
||||
//bail
|
||||
goto bail;
|
||||
}
|
||||
|
||||
//open Finder
|
||||
// ->will reveal binary
|
||||
[[NSWorkspace sharedWorkspace] selectFile:task.binary.path inFileViewerRootedAtPath:nil];
|
||||
[[NSWorkspace sharedWorkspace] selectFile:path inFileViewerRootedAtPath:nil];
|
||||
|
||||
//bail
|
||||
bail:
|
||||
@@ -976,7 +983,7 @@ bail:
|
||||
}
|
||||
|
||||
//automatically invoked when user clicks the 'info' icon
|
||||
// ->create/configure/display info window
|
||||
// ->create/configure/display info window for task/dylib/file/etc
|
||||
-(IBAction)showInfo:(id)sender
|
||||
{
|
||||
//item
|
||||
@@ -1068,4 +1075,219 @@ bail:
|
||||
}
|
||||
|
||||
|
||||
//OUTLINE VIEW STUFFZ
|
||||
|
||||
-(NSInteger)outlineView:(NSOutlineView *)outlineView numberOfChildrenOfItem:(id)item
|
||||
{
|
||||
//tasks
|
||||
OrderedDictionary* tasks = nil;
|
||||
|
||||
//grab tasks
|
||||
tasks = ((AppDelegate*)[[NSApplication sharedApplication] delegate]).taskEnumerator.tasks;
|
||||
|
||||
//number of children
|
||||
NSUInteger numberOfChildren = 0;
|
||||
|
||||
//when item is nil
|
||||
// ->count is number of root items children
|
||||
if(nil == item)
|
||||
{
|
||||
//kids
|
||||
numberOfChildren = ((Task*)[tasks objectForKey:@0]).children.count;
|
||||
}
|
||||
//otherwise
|
||||
// ->give number of item's kids
|
||||
else
|
||||
{
|
||||
//kids
|
||||
numberOfChildren = [((Task*)item).children count];
|
||||
}
|
||||
|
||||
return numberOfChildren;
|
||||
}
|
||||
|
||||
-(BOOL)outlineView:(NSOutlineView *)outlineView isItemExpandable:(id)item
|
||||
{
|
||||
//only no for leafs
|
||||
// ->items w/o kids
|
||||
if( (nil != item) &&
|
||||
(0 == [[item children] count]) )
|
||||
{
|
||||
return NO;
|
||||
}
|
||||
else
|
||||
{
|
||||
return YES;
|
||||
}
|
||||
//return !item ? YES : [[item children] count] != 0;
|
||||
}
|
||||
|
||||
//TODO: sort children!!!
|
||||
|
||||
//return child
|
||||
-(id)outlineView:(NSOutlineView *)outlineView child:(NSInteger)index ofItem:(id)item
|
||||
{
|
||||
//tasks
|
||||
OrderedDictionary* tasks = nil;
|
||||
|
||||
//task
|
||||
Task* task = nil;
|
||||
|
||||
//grab all tasks
|
||||
tasks = ((AppDelegate*)[[NSApplication sharedApplication] delegate]).taskEnumerator.tasks;
|
||||
|
||||
//root item
|
||||
if(nil == item)
|
||||
{
|
||||
//root
|
||||
task = [tasks objectForKey:@0];
|
||||
}
|
||||
//non-root items
|
||||
// ->return *their* child!
|
||||
else
|
||||
{
|
||||
task = [tasks objectForKey:[(Task*)item children][index]];
|
||||
}
|
||||
|
||||
return task;
|
||||
}
|
||||
|
||||
|
||||
//TODO: combine logic - and make taskForRow method work for flat and tree views :)
|
||||
- (void)outlineViewSelectionDidChange:(NSNotification *)notification
|
||||
{
|
||||
//tasks
|
||||
__block OrderedDictionary* tasks = nil;
|
||||
|
||||
//task
|
||||
Task* task = nil;
|
||||
|
||||
//newly selected row (index)
|
||||
__block NSInteger newlySelectedRow = -1;
|
||||
|
||||
//selected row cell
|
||||
NSTableCellView* selectedView = nil;
|
||||
|
||||
//ignore events for bottom-pane
|
||||
if(YES == self.isBottomPane)
|
||||
{
|
||||
//ignore
|
||||
goto bail;
|
||||
}
|
||||
|
||||
//get index of newly selected row
|
||||
newlySelectedRow = [self.itemView selectedRow];
|
||||
|
||||
//get row that's about to be selected
|
||||
selectedView = [self.itemView viewAtColumn:0 row:newlySelectedRow makeIfNecessary:YES];
|
||||
|
||||
//grab task
|
||||
task = [self taskForRow:nil];
|
||||
|
||||
//check if task is dead
|
||||
if(YES != isAlive([task.pid intValue]))
|
||||
{
|
||||
//make it red
|
||||
((kkRowCell*)selectedView).color = [NSColor redColor];
|
||||
|
||||
//draw
|
||||
[selectedView setNeedsDisplay:YES];
|
||||
|
||||
//make hide it after 1/4th second
|
||||
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(.25 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
|
||||
|
||||
//reset color
|
||||
((kkRowCell*)selectedView).color = nil;
|
||||
|
||||
//get tasks
|
||||
tasks = ((AppDelegate*)[[NSApplication sharedApplication] delegate]).taskEnumerator.tasks;
|
||||
|
||||
//remove (now dead) task
|
||||
[tasks removeObjectForKey:task.pid];
|
||||
|
||||
//reload table
|
||||
[self.itemView reloadData];
|
||||
|
||||
//sanity check
|
||||
// ->make sure removed task wasn't last
|
||||
if(tasks.count <= newlySelectedRow)
|
||||
{
|
||||
//reset to (new) last
|
||||
newlySelectedRow = tasks.count - 1;
|
||||
}
|
||||
//sanity check
|
||||
// ->reset to first item on other errors
|
||||
else if(-1 == newlySelectedRow)
|
||||
{
|
||||
//set to first
|
||||
newlySelectedRow = 0;
|
||||
}
|
||||
|
||||
//re-select
|
||||
[self.itemView selectRowIndexes:[NSIndexSet indexSetWithIndex:newlySelectedRow] byExtendingSelection:NO];
|
||||
|
||||
});
|
||||
|
||||
//bail
|
||||
goto bail;
|
||||
|
||||
}
|
||||
|
||||
//ignore if row selection didn't change
|
||||
if([self.itemView selectedRow] == self.selectedRow)
|
||||
{
|
||||
//ignore
|
||||
goto bail;
|
||||
}
|
||||
|
||||
//save newly selected row index
|
||||
self.selectedRow = [self.itemView selectedRow];
|
||||
|
||||
//save currently selected task
|
||||
((AppDelegate*)[[NSApplication sharedApplication] delegate]).currentTask = task;
|
||||
|
||||
//reload bottom pane
|
||||
[((AppDelegate*)[[NSApplication sharedApplication] delegate]) selectBottomPaneContent:nil];
|
||||
|
||||
|
||||
//bail
|
||||
bail:
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
//table delegate method
|
||||
// ->return cell for row
|
||||
-(NSView *)outlineView:(NSOutlineView *)outlineView viewForTableColumn:(NSTableColumn *)tableColumn item:(id)item
|
||||
{
|
||||
return createItemView(outlineView, self, (Task*)item);
|
||||
}
|
||||
|
||||
//automatically invoked
|
||||
// ->create custom (sub-classed) NSTableRowView
|
||||
-(NSTableRowView *)outlineView:(NSOutlineView *)outlineView rowViewForItem:(id)item
|
||||
{
|
||||
//row view
|
||||
KKRow* rowView = nil;
|
||||
|
||||
//row ID
|
||||
static NSString* const kRowIdentifier = @"RowView";
|
||||
|
||||
//try grab existing row view
|
||||
rowView = [outlineView makeViewWithIdentifier:kRowIdentifier owner:self];
|
||||
|
||||
//make new if needed
|
||||
if(nil == rowView)
|
||||
{
|
||||
//create new
|
||||
// ->size doesn't matter
|
||||
rowView = [[KKRow alloc] initWithFrame:NSZeroRect];
|
||||
|
||||
//set row ID
|
||||
rowView.identifier = kRowIdentifier;
|
||||
}
|
||||
|
||||
return rowView;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@@ -1,46 +0,0 @@
|
||||
/*-
|
||||
* Copyright 2009, Mac OS X Internals. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without modification, are
|
||||
* permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this list of
|
||||
* conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
|
||||
* of conditions and the following disclaimer in the documentation and/or other materials
|
||||
* provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY Mac OS X Internals ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL Mac OS X Internals OR
|
||||
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* The views and conclusions contained in the software and documentation are those of the
|
||||
* authors and should not be interpreted as representing official policies, either expressed
|
||||
* or implied, of Mac OS X Internals.
|
||||
*/
|
||||
|
||||
#import <Cocoa/Cocoa.h>
|
||||
|
||||
#import "3rdParty/OrderedDictionary.h"
|
||||
|
||||
@interface TreeViewController : NSViewController
|
||||
{
|
||||
|
||||
}
|
||||
@property (weak) IBOutlet NSOutlineView *itemView;
|
||||
|
||||
|
||||
|
||||
//tasks
|
||||
// ->updated by task enumerator
|
||||
//@property(nonatomic, retain)OrderedDictionary* tasks;
|
||||
|
||||
|
||||
@end
|
||||
@@ -1,305 +0,0 @@
|
||||
/*-
|
||||
* Copyright 2009, Mac OS X Internals. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without modification, are
|
||||
* permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this list of
|
||||
* conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
|
||||
* of conditions and the following disclaimer in the documentation and/or other materials
|
||||
* provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY Mac OS X Internals ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL Mac OS X Internals OR
|
||||
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* The views and conclusions contained in the software and documentation are those of the
|
||||
* authors and should not be interpreted as representing official policies, either expressed
|
||||
* or implied, of Mac OS X Internals.
|
||||
*/
|
||||
|
||||
#import "Task.h"
|
||||
#import "AppDelegate.h"
|
||||
#import "TreeViewController.h"
|
||||
#import "ItemView.h"
|
||||
#import "KKRow.h"
|
||||
|
||||
|
||||
@implementation TreeViewController
|
||||
|
||||
|
||||
@synthesize itemView;
|
||||
|
||||
-(void)awakeFromNib
|
||||
{
|
||||
//auto-expand everything
|
||||
//
|
||||
[itemView expandItem:nil expandChildren:YES];
|
||||
|
||||
//TODO: do this in IB?
|
||||
[itemView setTarget:self];
|
||||
//[outlineView setDoubleAction:@selector(onDoubleAction:)];
|
||||
}
|
||||
|
||||
//reload + row selection intact
|
||||
-(void)refresh
|
||||
{
|
||||
//TODO: add logic to ensure selected row stays selected
|
||||
[self.itemView reloadData];
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
-(void)showProcessInfo
|
||||
{
|
||||
NSArray *processes = [arrayController selectedObjects];
|
||||
if ([processes count] > 0) {
|
||||
ProcessInfo *pInfo = [processes objectAtIndex:0];
|
||||
if (pInfo.processState != -1 ) {
|
||||
TaskInfoController *taskInfoController = [TaskInfoController taskInfoController:pInfo];
|
||||
[taskInfoController showInfo];
|
||||
}
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
/*
|
||||
-(void)onDoubleAction:(NSEvent*)theEvent;
|
||||
{
|
||||
[self showProcessInfo];
|
||||
}
|
||||
|
||||
-(NSArray*)sortDescriptors
|
||||
{
|
||||
return [NSArray arrayWithObject:[NSSortDescriptor sortDescriptorWithKey:@"name" ascending:YES]];
|
||||
}
|
||||
|
||||
-(IBAction)menuItemAction:(id)sender
|
||||
{
|
||||
NSInteger clickedRow = [sender tag];
|
||||
}
|
||||
|
||||
-(TasksInfoManager*)tasksInfoManager
|
||||
{
|
||||
return [TasksInfoManager instance];
|
||||
}
|
||||
|
||||
-(NSString*)selectedAppName
|
||||
{
|
||||
NSString *result;
|
||||
NSArray *processes = [arrayController selectedObjects];
|
||||
|
||||
if ([processes count] > 0) {
|
||||
ProcessInfo *pInfo = [processes objectAtIndex:0];
|
||||
result = pInfo.name;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
*/
|
||||
|
||||
/*
|
||||
-(void)outlineView:(NSOutlineView *)outlineView willDisplayCell:(NSCell *)cell forTableColumn:(NSTableColumn *)tableColumn item:(id)item
|
||||
{
|
||||
//Task* *task = [item representedObject];
|
||||
Task* task = (Task*)item;
|
||||
|
||||
//item cell
|
||||
NSTableCellView *itemCell = nil;
|
||||
|
||||
|
||||
itemCell = (NSTableCellView*)cell;
|
||||
|
||||
//set main text
|
||||
// ->name
|
||||
[itemCell.textField setStringValue:task.path];
|
||||
|
||||
|
||||
|
||||
|
||||
//[imageAndTextCell setImage:pInfo.icon_small];
|
||||
|
||||
|
||||
/*
|
||||
if ([[Settings instance] highlightProcesses] == YES) {
|
||||
if (pInfo.processState == 0) { // process
|
||||
[(NSTextFieldCell*)cell setTextColor:[NSColor blackColor]];
|
||||
}
|
||||
else if (pInfo.processState == 1) { // new process
|
||||
[(NSTextFieldCell*)cell setTextColor:[NSColor greenColor]];
|
||||
}
|
||||
else if (pInfo.processState == -1) { // ended process
|
||||
[(NSTextFieldCell*)cell setTextColor:[NSColor redColor]];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
return;
|
||||
}
|
||||
*/
|
||||
|
||||
-(NSInteger)outlineView:(NSOutlineView *)outlineView numberOfChildrenOfItem:(id)item
|
||||
{
|
||||
//tasks
|
||||
OrderedDictionary* tasks = nil;
|
||||
|
||||
//grab tasks
|
||||
tasks = ((AppDelegate*)[[NSApplication sharedApplication] delegate]).taskEnumerator.tasks;
|
||||
|
||||
//NSLog(@"task: %@", ((Task*)item).path);
|
||||
|
||||
//count
|
||||
NSUInteger children = 0;
|
||||
|
||||
//when item is nil
|
||||
// ->count is all children
|
||||
if(nil == item)
|
||||
{
|
||||
//all
|
||||
children = ((Task*)[tasks objectForKey:@0]).children.count;
|
||||
}
|
||||
//otherwise
|
||||
// ->give number of item's kids
|
||||
else
|
||||
{
|
||||
//NSLog(@"task: %@", ((Task*)item).path);
|
||||
|
||||
//
|
||||
children = [((Task*)item).children count];
|
||||
|
||||
//NSLog(@"..has %lu kids", (unsigned long)children);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
return children;
|
||||
}
|
||||
|
||||
-(BOOL)outlineView:(NSOutlineView *)outlineView isItemExpandable:(id)item
|
||||
{
|
||||
//only no for leafs
|
||||
// ->items w/o kids
|
||||
if( (nil != item) &&
|
||||
(0 == [[item children] count]) )
|
||||
{
|
||||
return NO;
|
||||
}
|
||||
else
|
||||
{
|
||||
return YES;
|
||||
}
|
||||
//return !item ? YES : [[item children] count] != 0;
|
||||
}
|
||||
|
||||
//return child
|
||||
-(id)outlineView:(NSOutlineView *)outlineView child:(NSInteger)index ofItem:(id)item
|
||||
{
|
||||
//tasks
|
||||
OrderedDictionary* tasks = nil;
|
||||
|
||||
//task
|
||||
Task* task = nil;
|
||||
|
||||
//grab tasks
|
||||
tasks = ((AppDelegate*)[[NSApplication sharedApplication] delegate]).taskEnumerator.tasks;
|
||||
|
||||
|
||||
//get task object
|
||||
// ->by index to get key, then by key
|
||||
//task = self.tasks[[self.tasks keyAtIndex:index]];
|
||||
|
||||
task = [tasks objectForKey:@0];
|
||||
|
||||
//NSLog(@"root item: %@", self.tasks[[self.tasks objectForKey:@1]]);
|
||||
|
||||
//root item
|
||||
// ->child at index
|
||||
if(nil == item)
|
||||
{
|
||||
return task;//[self.tasks objectForKey:@1];
|
||||
}
|
||||
|
||||
//other items
|
||||
// ->return *their* child!
|
||||
else
|
||||
{
|
||||
return [tasks objectForKey:[(Task*)item children][index]];
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//table delegate method
|
||||
// ->return cell for row
|
||||
-(NSView *)outlineView:(NSOutlineView *)outlineView viewForTableColumn:(NSTableColumn *)tableColumn item:(id)item
|
||||
{
|
||||
return createItemView(outlineView, self, (Task*)item);
|
||||
}
|
||||
|
||||
//automatically invoked
|
||||
// ->create custom (sub-classed) NSTableRowView
|
||||
-(NSTableRowView *)outlineView:(NSOutlineView *)outlineView rowViewForItem:(id)item
|
||||
{
|
||||
//row view
|
||||
KKRow* rowView = nil;
|
||||
|
||||
//row ID
|
||||
static NSString* const kRowIdentifier = @"RowView";
|
||||
|
||||
//try grab existing row view
|
||||
rowView = [outlineView makeViewWithIdentifier:kRowIdentifier owner:self];
|
||||
|
||||
//make new if needed
|
||||
if(nil == rowView)
|
||||
{
|
||||
//create new
|
||||
// ->size doesn't matter
|
||||
rowView = [[KKRow alloc] initWithFrame:NSZeroRect];
|
||||
|
||||
//set row ID
|
||||
rowView.identifier = kRowIdentifier;
|
||||
}
|
||||
|
||||
return rowView;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
//person object
|
||||
- (id)outlineView:(NSOutlineView *)outlineView objectValueForTableColumn:(NSTableColumn *)tableColumn byItem:(id)item
|
||||
{
|
||||
//NSLog(@"column name: %@", [tableColumn identifier]);
|
||||
|
||||
// if ([[tableColumn identifier] isEqualToString:@"name"])
|
||||
return [item path];
|
||||
|
||||
// return @"Nobody's Here!";
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
|
||||
/*
|
||||
- (NSString *)outlineView:(NSOutlineView *)outlineView toolTipForCell:(NSCell *)cell rect:(NSRectPointer)rect tableColumn:(NSTableColumn *)tc item:(id)item mouseLocation:(NSPoint)mouseLocation
|
||||
{
|
||||
ProcessInfo *pInfo = [item representedObject];
|
||||
NSNumber *id_table;
|
||||
NSString *id_column;
|
||||
id *cell_data;
|
||||
|
||||
NSString *descr = pInfo.description;
|
||||
|
||||
return (descr);
|
||||
}
|
||||
*/
|
||||
|
||||
@end
|
||||
+3
-3
@@ -6,7 +6,7 @@
|
||||
<plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="7706"/>
|
||||
</dependencies>
|
||||
<objects>
|
||||
<customObject id="-2" userLabel="File's Owner" customClass="TreeViewController">
|
||||
<customObject id="-2" userLabel="File's Owner" customClass="TaskTableController">
|
||||
<connections>
|
||||
<outlet property="itemView" destination="Wr1-No-lg2" id="74i-TW-N6D"/>
|
||||
<outlet property="view" destination="T1P-b9-TzF" id="pja-1o-aue"/>
|
||||
@@ -25,7 +25,7 @@
|
||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
||||
<subviews>
|
||||
<outlineView verticalHuggingPriority="750" allowsExpansionToolTips="YES" columnAutoresizingStyle="lastColumnOnly" alternatingRowBackgroundColors="YES" columnReordering="NO" columnResizing="NO" multipleSelection="NO" autosaveColumns="NO" rowHeight="40" rowSizeStyle="automatic" viewBased="YES" indentationPerLevel="16" outlineTableColumn="cLW-QZ-CYz" id="Wr1-No-lg2">
|
||||
<rect key="frame" x="0.0" y="0.0" width="1298" height="0.0"/>
|
||||
<rect key="frame" x="0.0" y="0.0" width="1304" height="0.0"/>
|
||||
<autoresizingMask key="autoresizingMask"/>
|
||||
<size key="intercellSpacing" width="3" height="2"/>
|
||||
<color key="backgroundColor" name="controlBackgroundColor" catalog="System" colorSpace="catalog"/>
|
||||
@@ -44,7 +44,7 @@
|
||||
</textFieldCell>
|
||||
<tableColumnResizingMask key="resizingMask" resizeWithTable="YES" userResizable="YES"/>
|
||||
<prototypeCellViews>
|
||||
<tableCellView identifier="ImageCell" id="7xB-nb-n5O" customClass="kkRowCell">
|
||||
<tableCellView identifier="TaskCell" id="7xB-nb-n5O" customClass="kkRowCell">
|
||||
<rect key="frame" x="1" y="1" width="1295" height="40"/>
|
||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
||||
<subviews>
|
||||
|
||||
+4
-3
@@ -260,10 +260,11 @@ BOOL isApple(NSString* path)
|
||||
goto bail;
|
||||
}
|
||||
|
||||
//check if file is signed by apple
|
||||
// ->i.e. it conforms to req string
|
||||
//check if file is signed by apple by checking if it conforms to req string
|
||||
// note: ignore 'errSecCSBadResource' as lots of signed apple files return this issue :/
|
||||
status = SecStaticCodeCheckValidity(staticCode, kSecCSDefaultFlags, requirementRef);
|
||||
if(STATUS_SUCCESS != status)
|
||||
if( (STATUS_SUCCESS != status) &&
|
||||
(errSecCSBadResource != status) )
|
||||
{
|
||||
//bail
|
||||
// ->just means app isn't signed by apple
|
||||
|
||||
Reference in New Issue
Block a user